c++ 将结构的非托管数组封送为托管数组

inn6fuwd  于 2023-02-06  发布在  其他
关注(0)|答案(1)|浏览(171)

我想干净高效地将一个自定义的着色点结构从C应用程序传输到C#应用程序中。
实际上,自定义结构体是由浮点数组成的。因此,之前,我会将内容分解为一个浮点数组,然后在执行Marshal.Copy之后重新构建结构体,但这并不干净,也不是很容易维护。我希望能够执行类似的批量复制,但是同时填充我的C#数组的元素,我已经开始沿着这条路走了,通过把我的C
数组序列化到一个字节缓冲区,这个缓冲区有一个已知的点数,然后把它传递过去,下面的代码可以工作,但是在每个内存地址调用Marshal.PtrToStructure,这太慢了。
C#代码

protected override void TransferPoints( IntPtr points, int count )
    {
        PointXYZRGB[] colorPoints = new PointXYZRGB[ count ];

        for( int i = 0; i < count; i++)
        {
            // Works but is too slow
            colorPoints[i] = (PointXYZRGB) System.Runtime.InteropServices.Marshal.PtrToStructure(points + (32 * i), typeof(PointXYZRGB));
        }
    }

着色点

[StructLayout(LayoutKind.Sequential, Pack=16)]
    public struct PointXYZRGB 
    {
        public Vector3Data Position;

        public Color3Data Color;
    }

Vector3Data和Color3Data都是仅由三个浮点数组成的结构体
一个二个一个一个
C++函数模板如下所示

void TransferPoints( uint8_t* buffer, int32_t counts );

当我尝试像这样一次复制所有的东西时,我没有得到任何值。

protected override void TransferPoints( IntPtr points, int count )
        {
            PointXYZRGB[] colorPoints = new PointXYZRGB[ count ];

            System.Runtime.InteropServices.Marshal.PtrToStructure(points, colorPoints);
        }

我将非常感谢您的任何建议!

    • 编辑**更多上下文:我的C#代码订阅点列表,它是通过TransferPoints委托来完成的
public class ManagedPointWrapper
{
    [DllImport("example.so")]
    public static extern IntPtr newPointXYZRGBSubscriber( IntPtr transferPoints );
}

创建订阅者

ManagedPointWrapper.newPointXYZRGBSubscriber(System.Runtime.InteropServices.Marshal.GetFunctionPointerForDelegate( transferXYZRGBPointsCallback ) );

委托如下所示:

/// Delegate declaration for the callback to be passed into the c++ interop layer
    /// </summary>
    [UnmanagedFunctionPointer(CallingConvention.Cdecl)]
    public delegate void TransferXYZRGBPointsDelegate(IntPtr xyzrgb, Int32 count);
yyyllmsg

yyyllmsg1#

如果目标运行时/平台允许,请考虑使用泛型重载以提高性能:

///<summary>[Supported in the .NET Framework 4.5.1 and later versions]
  ///Marshals data from an unmanaged block of memory to a managed object of the specified type.</summary>
  ///<param name="ptr">A pointer to an unmanaged block of memory.</param>
  ///<param name="structure">The object to which the data is to be copied.</param>
  ///<typeparam name="T">The type of <paramref name="structure" />. This must be a formatted class.</typeparam>
  ///<exception cref="T:System.ArgumentException">Structure layout is not sequential or explicit.</exception>
  static member PtrToStructure<'T> : ptr: nativeint * structure: 'T -> unit

相关问题