C++/CLI 方法调用本地方法修改 int - 需要 pin_ptr?
C++/CLI method calls native method to modify int - need pin_ptr?
我有一个 C++/CLI 方法,ManagedMethod
,其中一个输出参数将由本机方法修改:
// file: test.cpp
#pragma unmanaged
void NativeMethod(int& n)
{
n = 123;
}
#pragma managed
void ManagedMethod([System::Runtime::InteropServices::Out] int% n)
{
pin_ptr<int> pinned = &n;
NativeMethod(*pinned);
}
void main()
{
int n = 0;
ManagedMethod(n);
// n is now modified
}
一旦 ManagedMethod
returns,n
的值已按我的预期进行了修改。到目前为止,我能够编译它的唯一方法是在 ManagedMethod
中使用 pin_ptr
,那么固定实际上是 correct/only 的方法吗?或者是否有更优雅的方式将 n
传递给 NativeMethod
?
是的,这是正确的做法。在 CLR 内部进行了高度优化,该变量获得了 [pinned] 属性,因此 CLR 知道它存储了一个指向不应移动的对象的内部指针。与 GCHandle::Alloc() 不同,pin_ptr<> 可以在不创建另一个句柄的情况下完成。在table中报告说编译方法时会产生抖动,GC使用table知道在哪里寻找对象根。
只有当垃圾收集发生在 NativeMethod() 运行 的同一时间时,这才是重要的。在实践中不会经常发生,您必须在程序中使用线程。 YMMV.
还有另一种方法,不需要固定但需要更多的机器代码:
void ManagedMethod(int% n)
{
int copy = n;
NativeMethod(copy);
n = copy;
}
之所以可行,是因为局部变量具有堆栈存储空间,因此不会被垃圾收集器移动。没有赢得任何风格的优雅点,但我通常自己使用,估计固定的副作用并不那么容易。但是,真的,不要害怕 pin_ptr<>。
我有一个 C++/CLI 方法,ManagedMethod
,其中一个输出参数将由本机方法修改:
// file: test.cpp
#pragma unmanaged
void NativeMethod(int& n)
{
n = 123;
}
#pragma managed
void ManagedMethod([System::Runtime::InteropServices::Out] int% n)
{
pin_ptr<int> pinned = &n;
NativeMethod(*pinned);
}
void main()
{
int n = 0;
ManagedMethod(n);
// n is now modified
}
一旦 ManagedMethod
returns,n
的值已按我的预期进行了修改。到目前为止,我能够编译它的唯一方法是在 ManagedMethod
中使用 pin_ptr
,那么固定实际上是 correct/only 的方法吗?或者是否有更优雅的方式将 n
传递给 NativeMethod
?
是的,这是正确的做法。在 CLR 内部进行了高度优化,该变量获得了 [pinned] 属性,因此 CLR 知道它存储了一个指向不应移动的对象的内部指针。与 GCHandle::Alloc() 不同,pin_ptr<> 可以在不创建另一个句柄的情况下完成。在table中报告说编译方法时会产生抖动,GC使用table知道在哪里寻找对象根。
只有当垃圾收集发生在 NativeMethod() 运行 的同一时间时,这才是重要的。在实践中不会经常发生,您必须在程序中使用线程。 YMMV.
还有另一种方法,不需要固定但需要更多的机器代码:
void ManagedMethod(int% n)
{
int copy = n;
NativeMethod(copy);
n = copy;
}
之所以可行,是因为局部变量具有堆栈存储空间,因此不会被垃圾收集器移动。没有赢得任何风格的优雅点,但我通常自己使用,估计固定的副作用并不那么容易。但是,真的,不要害怕 pin_ptr<>。