كيفية P/استدعاء عندما تكون المؤشرات متضمنة

StackOverflow https://stackoverflow.com/questions/1422701

  •  07-07-2019
  •  | 
  •  

سؤال

في محاولة لتعلم كيفية استخدام PInvoc في C#، لست متأكدًا بعض الشيء من كيفية التعامل مع الحالات المختلفة باستخدام المؤشرات التي تتضمن أنواع قيم بسيطة.

أقوم باستيراد الوظيفتين التاليتين من ملف DLL غير مُدار:

public int USB4_Initialize(short* device);
public int USB4_GetCount(short device, short encoder, unsigned long* value);

تستخدم الوظيفة الأولى المؤشر كمدخل، والثانية كمخرج.استخدامها بسيط إلى حد ما في C++:

// Pointer as an input
short device = 0; // Always using device 0.
USB4_Initialize(&device);

// Pointer as an output
unsigned long count;
USB4_GetCount(0,0,&count); // count is output

محاولتي الأولى في C# تؤدي إلى P/Invoces التالية:

[DllImport("USB4.dll")]
public static extern int USB4_Initialize(IntPtr deviceCount); //short*

[DllImport("USB4.dll")]
public static extern int USB4_GetCount(short deviceNumber, short encoder, IntPtr value); //ulong*

كيف يمكنني استخدام هذه الوظائف في C# بنفس طريقة استخدام كود C++ أعلاه؟ هل هناك طريقة أفضل للإعلان عن هذه الأنواع، ربما باستخدام MarshalAs?

هل كانت مفيدة؟

المحلول

إذا كان المؤشر يشير إلى نوع بدائي واحد وليس مصفوفة، فاستخدم ref / out لوصف المعلمة

[DllImport("USB4.dll")]
public static extern int USB4_Initialize(ref short deviceCount);

[DllImport("USB4.dll")]
public static extern int USB4_GetCount(short deviceNumber, short encoder, ref uint32 value)

في هذه الأمثلة ربما يكون الأمر أكثر ملاءمة ولكن أيًا منهما سيعمل.

نصائح أخرى

يمكن لوقت تشغيل .NET إجراء الكثير من هذا التحويل (يُشار إليه باسم "التنظيم") نيابةً عنك.على الرغم من أن IntPtr الصريح سيفعل دائمًا ما تطلبه منه بالضبط، فمن المحتمل أنه يمكنك استبدال ref الكلمة الأساسية لمؤشر من هذا القبيل.

[DllImport("USB4.dll")]
public static extern int USB4_Initialize(ref short deviceCount); //short*

[DllImport("USB4.dll")]
public static extern int USB4_GetCount(short deviceNumber, short encoder, ref short value); //ulong*

يمكنك بعد ذلك الاتصال بهم بهذه الطريقة:

short count = 0;

USB4_Initialize(ref count);

// use the count variable now.
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top