2013-05-17 138 views
23

在我的c#应用程序中,我收到指向回调/委托中的C++结构体的指针。我不知道如果class可以做的伎俩,但只是将C++指针转换为适当的c#结构工作正常,所以我使用c#结构来存储数据。通过c#结构参考?

现在我想通过参考结构作进一步处理

  • 我不能使用class,因为它可能不会“地图”完美的C++结构。
  • 我不想更好的延迟复制结构

我怎么能这样做?


这个例子表明,结构是按值传递,而不是参考:

using System; 

namespace TestStruct 
{ 
    struct s 
    { 
     public int a; 
    } 

    class Program 
    { 
     static void Main(string[] args) 
     { 
      s s1 = new s 
         { 
          a = 1 
         }; 
      Foo(s1); 
      Console.WriteLine("outer a = " + s1.a); 
     } 

     private static void Foo(s s1) 
     { 
      s1.a++; 
      Console.WriteLine("inner a = " + s1.a); 
     } 

    } 
} 

输出是:

inner a = 2 
outer a = 1 
+4

要小心你关于struct的结构:C++中的'struct'与class完全一样(禁止默认的可访问性),而在C#中它们完全不同 - 值和引用类型。机会是你真的会更好用C#中的类 - 至少读和理解'struct'在C#中的行为如何。 –

+0

大量的互操作类实际上是类而不是结构。如果您正确设置编组(并且通常默认编组工作),那么您可以使用一个类。如果有疑问,我会先与班级一起尝试。 –

回答

40

这听起来像你只是想用ref传递结构参考:

private static void Foo(ref s s1) 
{ 
    s1.a++; 
    Console.WriteLine("inner a = " + s1.a); 
} 

,并在调用点:

Foo(ref s1); 

见我article on parameter passing in C#了解更多详情。

请注意,除了interop之外,我通常会强烈推荐针对使用这样的可变结构。我可以理解这里的好处。

+8

+1。注意:必须非常小心地编写代码处理'struct',因为几乎所有使用'struct'的操作都会创建副本(数组除外,您仍然可以获取元素的'ref')。 –

+0

为什么强烈建议不要通过'ref'传递结构?据我所知,这与在C++中通过引用传递(例如'std :: string&')是一样的,并且它可以消除潜在的大型结构的不必要的复制。 –

+1

@cmbasnett:我强烈建议不要使用可变结构。通过ref传递一个结构是可以的,但是a)我会建议反对大型结构; b)我会反对*可变*结构(如微软设计指南),因为它们可能会导致一些意外。 –