1

我再次通过 UDP 从 C++ 程序接收结构,现在我将结构移植到 C#,例如:

[Serializable]
struct sample
{
public int in;
public byte[] arr;
public int[] arr2;
public float fl;
}

好的,那么解串器如何知道一个数组何时结束而另一个数组何时开始?可以以某种方式指定数组有多大?我不想使用fixed,因为这使我的代码不安全,而且我也不能使用构造函数,因为不允许结构包含没有参数的构造函数。

有什么建议么?

//编辑:

已知阵列的长度为 32 和 4。问题是我不知道如何将此信息传递给反序列化器

然后发件人是 C++ 一个像这样的作品:

char* pr = &sample;
int i=0;
while (i<sizeof(sample))
{
 udp.send(*(pr+i))
 i++;
}
4

3 回答 3

3

既然您已经告诉我们长度是预定义的长度,那么下面的陈述就变得更清楚了:

我不知道如何将此信息传递给反序列化器

事实上,它变得毫无意义。没有预定义的序列化程序可以在这里为您提供帮助。你有两个选择:

A:编写您自己的序列化程序,并在您知道格式后处理数据 - 可能使用BinaryReader

using(var reader = new BinaryReader(source)) {

    int in = reader.ReadInt32();
    byte[] arr = reader.ReadBytes(32);
    int[] arr2 = new int[4];
    for(int i = 0 ; i < 4 ; i++) arr2[i] = reader.ReadInt32();
    float fl = reader.ReadSingle();

    var obj = /* something involving ^^^ */
}

B:缓冲 56 字节,并使用非常讨厌的unsafe//fixed指针碰撞代码

我强烈建议第一个。特别是,如果需要,这也将允许您解决字节顺序问题。

以对你来说神圣的一切的名义,不要这样做:

using System;
using System.Runtime.InteropServices;
[StructLayout(LayoutKind.Explicit)]
unsafe struct sample
{
    [FieldOffset(0)] public int @in;
    [FieldOffset(4)] public fixed byte arr[32];
    [FieldOffset(36)] public fixed int arr2[4];
    [FieldOffset(52)] public float fl;    
}

static class Program
{
    unsafe static void Main()
    {
        byte[] buffer = new byte[56];
        new Random().NextBytes(buffer); // some data...

        sample result;
        fixed(byte* tmp = buffer)
        {
            sample* ptr = (sample*) tmp;
            result = ptr[0];
        }

        Console.WriteLine(result.@in);
        Console.WriteLine(result.fl);
    }    
}

对于较大的缓冲区,您可以将ptr其视为一个不安全的 multiple 数组sample,按索引访问:

int @in = ptr[i].@in;

(ETC)

但老实说......有很多“邪恶”的东西,我真的不知道从哪里开始......只是......除非你绝对知道那里的每一行都在做什么,以前做过,而且了解所有的陷阱...不要想它

于 2012-06-26T10:26:40.600 回答
1

这取决于用于通过线路传递结构的格式。

如果说是json,那么每个字段都会有一个key,数组会被[]包围。

如果说它是 xml,那么您会期望一个带有子节点的 arr 节点。

如果是任意格式,则需要知道格式。

反序列化器有一些默认行为,但如果传递的数据不是默认格式,您需要准确地告诉他们如何反序列化。

于 2012-06-26T08:18:15.633 回答
1

以及如何记录原始数据?我希望这里能告诉你一些事情,例如,我可能希望它说格式是(纯粹是一个例子)

  • 4 字节 NBO Int32 ( in)
  • 4 字节 NBO Int32(长度为arr
  • len 个字节 ( arr)
  • 4 字节 NBO(长度为arr2
  • 4 * len 个字节(arr2每个在 NBO Int32 中)
  • 4 字节 IEEE-754 ( fl)

你需要知道格式。

编辑:如果 C++ 数组具有已知的固定长度,那么您只需要提前知道这些长度。

于 2012-06-26T08:19:40.307 回答