我怀疑这个简单的Prolog程序如何从文件中读取字符并将这些字符放入列表中。
代码运作良好,如下:
readFile(FileInput, TextList):- open(FileInput, read, Stream),
readCharacter(Stream, TextList),
close(Stream),
!.
readCharacter(Stream,[]):- at_end_of_stream(Stream). % Exit condition
readCharacter(Stream,[Char|Tail]):- get0(Stream,Char),
readCharacter(Stream,Tail).
当 readFile / 2 谓词被调用时:输入传递的文件在读取模式下打开,并且该文件与流相关联。
然后调用 readCharacter / 2 谓词,该谓词将与我的输入文件(要读取的文件)关联的Stream和 TextList 作为放置文件的列表内容。
readCharacter / 2 谓词它分为两种情况:
1)使用 at_end_of_stream(Stream)谓词的退出条件,该谓词在Stream的最后一个字符(因此文件中的最后一个字符)之后成功读取。在这种情况下,什么也不做, readCharacter 谓词结束
2)第二种情况是这个规则添加一个读取字符并将其添加到我的 TextList :
readCharacter(Stream,[Char|Tail]):- get0(Stream,Char),
readCharacter(Stream,Tail).
在这里我有一个疑问:它使用 get0 读取Stream中的一个字符并将其放在列表的头部(作为列表的第一个元素)...所以......为什么列表不包含文件内容的反转?
即
我有一个名为 myFile.txt 的文件,其中包含以下文字: abc
所以 readCharacter 首先从Stream中读取一个字符并将其放在列表的头部,这样我就有了:
TextList = [a]
然后 readCharacter 从Stream中读取 b 字符并将其放入我所拥有的列表的头部:
TextList = [b,a]
然后 readCharacter 从Stream中读取 c 字符并将其放入我所拥有的列表的头部:
TextList = [c,b,a]
如果是这样,TextList应该包含myFile.txt文件的反向内容,但在我看来,TextList包含相同顺序的myFile.txt文件的相同内容。
为什么呢?我错过了什么?我的推理出了什么问题?
答案 0 :(得分:1)
readCharacter(Stream,[Char|Tail]):-
get0(Stream,Char),
readCharacter(Stream,Tail).
所以你拥有了 Stream ,你可以从中获得一个角色并将其与 Char 统一起来。您在 Tail 中有一个尚未初始化的列表。然后,您将 Stream (其中一个字符已消失)和 Tail 传递给readCharacter
的递归调用。冲洗并重复,直到 Stream 处于文件末尾。
重点是:[Char|Tail]
表示 Char 是结果列表的头部,换句话说,之前列表中的其他内容
如果你跟踪这一点,你会看到 Char 如何与你文件中的字符代码统一,按照文件中的顺序,调用get0(Char)
,但在递归调用readCharacter
时消失。
然后,当你离开递归时,你从get0
得到的字符代码在readCharacter
的第二个参数中,在它们被读取的调用的退出处神奇地重新出现,每个在 Tail 中的所有内容之前 Char (根据[Char|Tail]
,应该如此。
基本上,你的推理(这里和其他问题)的错误在于你太过努力将期望强加于你所看到的而不是接受和试图认识到你观察到的逻辑。像所有其他人造物一样,Prolog在大多数情况下遵循某种逻辑。