【问题标题】:Type conversion issue in C#C#中的类型转换问题
【发布时间】:2016-01-27 08:11:44
【问题描述】:

我正在尝试有关 C# 控制台项目上的堆和指针的一些东西(最初来自 here)。我的程序是这样的:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Runtime.InteropServices;

public class Win32
{
[DllImport("user32.dll", CharSet = CharSet.Auto)]
public static extern IntPtr malloc(int size);

[DllImport("user32.dll", CharSet = CharSet.Auto)]
public static extern int free(IntPtr region); //Change IntPtr befroe free method to int ---update---
}

public class Program
{
    public unsafe void Heap()
    {
        int* num1, num2, answer;
        num1 = Win32.malloc(sizeof(int));
        *num1 = 999; // 999 should be the value stored at where pointer num1 refers to

        num2 = Win32.malloc(sizeof(int));
        *num2 = 1; // 1 should be the value stored at where pointer num2 refers to

        answer = Win32.malloc(sizeof(int));
        *answer = *num1 + *num2; // 1000 should be the value of pointer answer's reference

        Console.WriteLine(*answer); // 1000?
        Win32.free(num1);
        Win32.free(num2);
        Win32.free(answer);
    }
}

调试后,得到错误信息:

错误 1 ​​无法将类型“System.IntPtr”隐式转换为“int*”。一个 存在显式转换(您是否缺少演员表?)

error CS1502: The best overloaded method match for 'Win32.free(System.IntPtr)' has some invalid arguments

error CS1503: Argument 1: cannot convert from 'int*' to 'System.IntPtr'

我的问题是为什么我不能在 malloc 和 free 之前使用 IntPtr,因为这两种方法都返回 void?我应该对我的代码进行哪些更改? 谢谢你的帮助。

---更新---

更改:public static extern IntPtr free(int hWnd); 为公共静态 extern int free(IntPtr region);free(*num)free(num)

给出额外的“CS1502”和“CS1503”两个错误。

---第二次更新--- C# 自动处理堆的东西。 C# 中没有 malloc 的等价物。这是一个死胡同。 T_T

【问题讨论】:

  • are you missing a cast?
  • @Rob 问题是我不认为我错过了一个演员表。而且我不知道如何将 void 转换为 int。

标签: c# pointers


【解决方案1】:

几个错误:

在 C/C++ 中

void * malloc(int sizeToAllocate);
int free(void * region);

您将malloc 返回的值传递给free。因此,您的导入应该是:

[DllImport("user32.dll", CharSet = CharSet.Auto)]
public static extern IntPtr malloc(int size); 

[DllImport("user32.dll", CharSet = CharSet.Auto)]
public static extern int free(IntPtr region); 

因此你的释放代码应该变成:

 var num1Ptr = Win32.malloc(sizeof(int));
 int * num1 = (int*) num1Ptr.ToPointer();

 ...

 var num2Ptr = Win32.malloc(sizeof(int));
 int * num2 = (int*) num2Ptr.ToPointer();

 ...

 var answerPtr = Win32.malloc(sizeof(int));
 int * answer = (int*) answerPtr.ToPointer();

 ...

 Win32.free(num1Ptr);
 Win32.free(num2Ptr);
 Win32.free(answerPtr);

【讨论】:

  • 感谢您的帖子。它帮助我更好地理解 Platform Invoke 的工作方式,以及我关于 free(pointer) 而不是 free(value) 的错误。但是,它给出了额外的两个错误'CS1502:'Win32.free(System.IntPtr)'的最佳重载方法匹配有一些无效参数'和'CS1503:参数1:无法从'int *'转换为'System.IntPtr ''。
  • 你说得对,你可以简单地做一个简单的Win32.free(IntPtr(num1));,但更严格的方法是更新的解决方案。
  • 我发现了我的问题,在 user32.dll 或其他参考中找不到 malloc,它在 C# 中没有任何等效项。当我陷入死胡同并不断将头撞在墙上时,我很愚蠢。 T_T。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-08-19
  • 2011-11-17
相关资源
最近更新 更多