【问题标题】:Trying to Read Strings from a Binary File尝试从二进制文件中读取字符串
【发布时间】:2013-02-13 01:53:16
【问题描述】:

这是一个简单的程序,我只是尝试将几个变量写入二进制文件,然后再读回来。

我试图弄清楚如何从二进制文件中读取字符串。它写对了。但是每次我尝试读取它(在这个例子中它是 4 个字节)时,结果都很奇怪,这会把所有东西都扔掉。 b = "jump",但无论我如何尝试阅读和转换,最终结果都会变得很奇怪。然后在它之后读取的变量 b 也变得很奇怪。

从二进制文件中读取字符串的正确方法是什么?无论如何,我的所有字符串都是固定长度的,15 个字符。有没有办法在不转换为 char 数组的情况下做到这一点?

我也尝试了 .ReadCharArrays() 方法,然后是 toString(),但我仍然没有读取正确的变量。

string path = ".//..//..//..//";

FileStream mfs = new FileStream(path + "test.bin", FileMode.OpenOrCreate, FileAccess.ReadWrite);
BinaryReader br = new BinaryReader(mfs);
BinaryWriter bw = new BinaryWriter(mfs);

short a = 2;
short b = 3;
string c = "JUMP";
bw.Write(a);
bw.Write(c);
bw.Write(b);

Console.WriteLine("Done writing to binary file");
br.BaseStream.Seek(0, SeekOrigin.Begin); //Apprantly you have to seek to beginning

a = br.ReadInt16();
c = br.ReadBytes(4).toString();
b = br.ReadInt16();

Console.WriteLine(""+a);
Console.WriteLine(""+c);
Console.WriteLine("");
Console.WriteLine("" +b); 

【问题讨论】:

标签: c# string binaryfiles msdn


【解决方案1】:

是什么让你觉得“JUMP”占用了4个字节?

BinaryWriter.Write(字符串):

以 BinaryWriter 的当前编码向该流写入一个带长度前缀的字符串,

【讨论】:

  • 这真的更像是一个评论,不是吗?
  • 其实是指向答案的指针。我不喜欢用勺子喂。我要补充一点 br.ReadString 是正确的 api,但正如 @500 所做的那样,已经没有什么意义了。
  • 我仍然对一个字符串有多少字节感到有些困惑。我认为字符串中的每个字符本质上是 1 个字节,所以 8 个字符的字符串将是 8 个字节,等等。
  • 这可能适用于单字节编码,例如 ascii。但是,其他编码中的许多字符并非如此。在这种使用 UTF8 的情况下,它可能是 4 个字节......但是长度前缀呢?你忘记了。通过添加长度字段,这意味着在使用 BR.ReadString 读取字符串之前,您不必知道字符串的长度。明白了吗?
  • @user2066820,据我所知,字符串被写为长度可变长度整数,后跟正确编码的字符(默认 UTF8),所以在“JUMP”的情况下,它应该是 5 个字节。
【解决方案2】:

您应该使用 BinaryReader.ReadString() 来读回字符串 - ReadBytes 读取字节数组,默认情况下字符串在 .NET 中是 unicode。

【讨论】:

  • 谢谢,我不知道 C# 存在 .ReadString()。
  • +1。 @user2066820,考虑使用 Visual Studio 编辑 CS 文件并注意智能建议 - 当您键入“br.Read”时,它应该向您显示 ReadString 作为选项。
【解决方案3】:

BinaryReader.ReadString()。我刚刚测试了您的代码,它似乎工作正常:

a = br.ReadInt16();
string d = br.ReadString(); // store in another variable just to be sure..
b = br.ReadInt16();

Console.WriteLine("" + a);
Console.WriteLine("" + d); // JUMP
Console.WriteLine("");
Console.WriteLine("" + b);

【讨论】:

  • 是的,它确实有效!现在只需要弄清楚它将有多少字节。一个短是 2 个字节。这很重要,因为稍后我将做直接地址(当然是在一个更大的项目中)。
  • @user2066820 你真的需要发明一种新的二进制格式吗?将二进制序列化作为替代方案可能会更好。
猜你喜欢
  • 2014-06-18
  • 2012-09-05
  • 2020-10-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多