在C++中是否有一个BinaryReader来读取C#中从BinaryWriter写入的数据?

Chr*_*ris 1 c# c++ file-io binaryfiles binaryreader

我已经用C#中的BinaryWriter写了几个整数,char []和其他数据文件.使用BinaryReader读回(在C#中)文件,我可以完美地重新创建文件的所有部分.

但是,试图用C++重新读取它们会产生一些可怕的结果.我正在使用fstream尝试回读数据并且数据未正确读取.在C++中,我设置了一个fstream ios::in|ios::binary|ios::ate并使用seekg来定位我的位置.然后我读取接下来的四个字节,它们写成整数"16"(并正确读入C#).这在C++中读作1244780(不是内存地址,我检查过).为什么会这样?在C++中是否有与BinaryReader相同的东西?我注意到它在msdn上提到过,但是对我来说,Visual C++和intellisense看起来并不像c ++.

编写文件的示例代码(C#):

    public static void OpenFile(string filename)
    {
        fs = new FileStream(filename, FileMode.Create);
        w = new BinaryWriter(fs);

    }

    public static void WriteHeader()
    {
        w.Write('A');
        w.Write('B');
    }

    public static byte[] RawSerialize(object structure)
    {
        Int32 size = Marshal.SizeOf(structure);
        IntPtr buffer = Marshal.AllocHGlobal(size);
        Marshal.StructureToPtr(structure, buffer, true);
        byte[] data = new byte[size];
        Marshal.Copy(buffer, data, 0, size);
        Marshal.FreeHGlobal(buffer);
        return data;
    }

    public static void WriteToFile(Structures.SomeData data)
    {
        byte[] buffer = Serializer.RawSerialize(data);
        w.Write(buffer);
    }
Run Code Online (Sandbox Code Playgroud)

我不确定如何向您显示数据文件.

读取数据的示例(C#):

        BinaryReader reader = new BinaryReader(new FileStream("C://chris.dat", FileMode.Open));
        char[] a = new char[2];
        a = reader.ReadChars(2);
        Int32 numberoffiles;
        numberoffiles = reader.ReadInt32();
        Console.Write("Reading: ");
        Console.WriteLine(a);
        Console.Write("NumberOfFiles: ");
        Console.WriteLine(numberoffiles);
Run Code Online (Sandbox Code Playgroud)

我想用c ++执行.初始尝试(第一个整数失败):

 fstream fin("C://datafile.dat", ios::in|ios::binary|ios::ate);
 char *memblock = 0;
 int size;
 size = 0;
 if (fin.is_open())
 {
  size = static_cast<int>(fin.tellg());
  memblock = new char[static_cast<int>(size+1)];
  memset(memblock, 0, static_cast<int>(size + 1));

  fin.seekg(0, ios::beg);
  fin.read(memblock, size);
  fin.close();
  if(!strncmp("AB", memblock, 2)){ 
   printf("test. This works."); 
  }
  fin.seekg(2); //read the stream starting from after the second byte.
  int i;
  fin >> i;
Run Code Online (Sandbox Code Playgroud)

编辑:似乎无论我使用"seekg"到哪个位置,我都会得到完全相同的值.

Yac*_*oby 5

您意识到C#中的字符是16位而不是C中的8位.这是因为C#中的char设计用于处理Unicode文本而不是原始数据.因此,使用BinaryWriter编写字符将导致写入Unicode而不是原始字节.

这可能会导致您错误地计算整数的偏移量.我建议您在十六进制编辑器中查看该文件,如果您无法解决问题,请在此处发布文件和代码.

EDIT1
关于您的C++代码,请不要使用>>运算符来读取二进制流.将read()与要读取的int的地址一起使用.

int i;
fin.read((char*)&i, sizeof(int));
Run Code Online (Sandbox Code Playgroud)

EDIT2
从封闭流中读取也会导致未定义的行为.你不能调用fin.close()然后仍然希望能够从中读取.