从文件或流中读取

时间:2014-09-23 21:57:06

标签: io prolog

我可以像以前一样使用Java来处理文件吗?假设我有一个包含3行的文件,如下所示:

 This is hello world.
 This is not hello world.
 This is a story of a young boy.

现在我怎样才能在程序中使用这三行作为字符串?

1 个答案:

答案 0 :(得分:0)

首先评论一下:如果你在Prolog中编程,最好是尝试使用像Prolog一样处理文件的文件,而不是像以前那样使用Java。

并提出建议:阅读文档。这是第一次疼,但你会学会喜欢它。 SWI-Prolog在其网站上提供了非常完整且易于搜索的文档。

现在:您真的需要更好地了解您实际上正在尝试使用这些文件。这对于您将用于阅读它们并在程序中表示它们的方法很重要。

具体来说:您可以在Prolog中将“文本”表示为:

  • 原子
  • 字符代码列表
  • 单字符原子列表
  • 如果您使用SWI-Prolog 7(作为其中一个标签建议),字符串对象,Prolog的仅SWI扩展

列表继续,但这些是最开始的。每种方法都有其优势,您使用哪种方法实际上取决于您的应用。

无论如何,这只是第一步。根据您对文件内容的处理方式,首先将其标记为原子或更复杂的术语可能很有用。

这个答案的其余部分在某种程度上是特定于SWI-Prolog的。

如果您正在阅读文件,使用Pure I/O library和DCG可能会很有用。这种方法有两个问题:您需要了解DCG是什么;如果您尝试从非重新定位流中读取它(例如,它不能与标准输入一起使用),它将无法正常工作。但是,如果需要实际解析,可以随时读取整个文件并使用DCG。毫无疑问,这是最通用的方法。您可以查看here以有效读取整个文件。

如果您正在阅读实际的Prolog术语,则可能需要term reading and writing predicates

如果您按行阅读,使用library(readutil)会很有帮助。

您可以随时使用input/output primitives,但这非常繁琐且通常没必要。

阅读完毕后,您可以convert to atoms or lists of one-char atomsstrings。请记住,如果你决定使用字符串,你将会被SWI-Prolog所困扰(至少目前是这样),但是你将能够使用一些漂亮的谓词来直接从流中读取字符串。

阅读和写作意味着您需要open and close files。您还可以使用别名user_inputuser_output等立即访问标准输入和输出流。这些或您打开的流/文件是许多读写的参数谓词链接在上面。

现在,一个小例子:使用library(readutil)读取文件并收集字符代码列表中的每一行:

file_to_lines(Filename, Lines) :-
    setup_call_cleanup(
        open(Filename, read, In),
        stream_to_lines(In, Lines),
        close(In)
    ).

stream_to_lines(In, Lines) :-
    read_line_to_codes(In, Codes),
    stream_to_lines_rest(Codes, In, Lines).

stream_to_lines_rest(end_of_file, _In, []) :- !.
stream_to_lines_rest(This, In, [This|Rest]) :-
    read_line_to_codes(In, Next),
    stream_to_lines_rest(Next, In, Rest).

如果将其保存在名为rf.pl的文件中:

?- [rf].
true.

?- file_to_lines('rf.pl', Lines), forall(member(L, Lines), format("~s~n", [L])).
file_to_lines(Filename, Lines) :-
    setup_call_cleanup(
        open(Filename, read, In),
        stream_to_lines(In, Lines),
        close(In)
    ).

stream_to_lines(In, Lines) :-
    read_line_to_codes(In, Codes),
    stream_to_lines_rest(Codes, In, Lines).

stream_to_lines_rest(end_of_file, _In, []) :- !.
stream_to_lines_rest(This, In, [This|Rest]) :-
    read_line_to_codes(In, Next),
    stream_to_lines_rest(Next, In, Rest).

Lines = [[102, 105, 108, 101, 95, 116, 111, 95|...], [32, 32, 32, 32, 115, 101, 116|...], [32, 32, 32, 32, 32, 32|...], [32, 32, 32, 32, 32|...], [32, 32, 32, 32|...], [32, 32, 32|...], [], [115|...], [...|...]|...].
相关问题