为什么Peek和Read使用整数来警告你文件结尾而不是异常来检查C#中streamreader的结尾?

时间:2014-10-21 18:43:46

标签: c# streamreader

我写了一个非常简单的C#类来读取UTF8文件的所有字符。

对于主循环,检测文件结尾的条件是:

while (!fin.EndOfStream) 
{
    int c = fin.Read();
    <some text processing>
}

但我至少知道另外两种方法:

while (fin.Peek() >= 0)
{
    int c = fin.Read();
    <some text processing>
}

int c = 0;
while ((c = fin.Read()) >= 0) 
{
   <some text processing>
}

对我来说,第一种形式是最好的:更短,更清晰,条件很容易理解,当你到达结束时你不必知道Read()或Peek()返回-1文件。

除了第二和第三种形式不遵循信息隐藏原则(维基百科引用): Information Hiding principle.

我的问题是:

为什么有这么多方法来检查文件的结尾?

为什么花时间和资源设计,编码,测试和维护这么多方法来检查文件的结尾?

编辑:

Read and Peek警告你文件的结尾,你可以用它们来完成EndOfStream的工作。我的意思是:Read和Peek正在做他们自己的工作和EndOfStream的工作,所以Read和Peek正在做更多他们的名字建议的工作。每当到达文件末尾时,都可以使用异常而不是整数。

2 个答案:

答案 0 :(得分:2)

你的问题的前提是错误的。

所有这些功能都有不同的语义,不同的目的。仅仅因为它们在一个上下文中是可互换的,并不意味着您可以在每种情况下自由地进行。其中只有一种方法专门用于检查流的结尾 - fin.EndOfStream

仅仅因为人们使用棒球棒击打其他人,这并不意味着棒球棒是多余的和无用的,因为还有其他(甚至更好)的方法。它们的目的在不同的背景下。

实际上可能会争论(至少在我看来),fin.EndOfStream可能是(fin.Peek() >= 0)多余的,或者语言设计者可能做到这一点,但是他们决定允许程序在语义上清洁。检查流的结尾感觉比下一个预期出错的字符更自然。

您谈论的每种方法和财产的存在都是合理的。

答案 1 :(得分:0)

Peek等于Read而不影响流的状态,因此我不会将其视为“替代”。还有一些其他类提供PeekRead选项。

还有其他类使用Read来读取和通知流的结尾,XmlReader例如返回bool而不是数字。

我同意你的意见,使用号码作为指示是否到达终点是奇数。顺便说一下,流末尾的Read的返回值是0,而不是-1,当数据不可用时,流被记录为阻塞,直到数据可用(因为如果它返回0,则意味着流的结束)。他们本可以选择bool TryRead(..., out int bytes)

我不知道如何做出有关Stream的决定,但如果它满足了您的问题,我们可以假装他们完全按照您的意思行事,并为那些没有做过的人{39}创建了EndOfStream财产; t喜欢其他方法。一种证据就是Stream的实施者不必实施EndOfStream,因为它只代表最后一次Read操作的状态。