我正在使用SWI-Prolog library(http/http_open)
。根据{{3}},"在[http_open(Url, Stream, [])
]成功后,可以从Stream中读取数据。"因此,我想也许我可以使用phrase_from_stream/2
中的library(pure_input)
来装配一个简单的声明性谓词来解析URL中的短语:
phrase_from_url(Url, Phrase) :-
http_open(Url, In, []),
phrase_from_stream(Phrase, In),
close(In).
但我怀疑http_open/3
提供的流的种类有一些细微差别;我收到以下错误:
ERROR: set_stream_position/2: stream `<stream>(0x7feebbf5c810)' does not exist (Device not configured)
(我已针对library(http/http_open)
文档中提供的示例测试了相同的网址,该文档使用copy_stream_data/2
将输出通过管道传输到user_output
,并且它有效。所以我知道网址没有错。)
我了解到我可以将网址中的数据下载到字符串,代码列表或文本文件中,然后使用我们的堂兄phrase/n
。但我希望有人可以帮我通知......
phrase_from_stream/2
,因为人们可能会天真地希望。答案 0 :(得分:1)
目前,library(pure_input)
不支持支持非重新定位流。这就是问题所在。
一种解决方案是阅读所有内容,然后使用正常的phrase
。这当然与承诺的“懒惰阅读”不同。
至于“从URL解析数据”,请记住,SWI-Prolog拥有您在网络上找到的许多内容的库:SGML/XML/HTML; JSON; RDF
要从html页面中挑选文本,请参阅示例this simple scraper。相关代码位于scrape/3
及其帮助谓词中。它使用SWI-Prolog SGML / XML解析器和library(xpath)
。
同时,如果你想使用DCG从非重新定位的流中解析,那就太难了。 library(pure_input)
甚至不能处理标准输入。根据您的数据结构的不同,您可以使用read_line_to_codes/3
(参见示例),如果您的输入按行排列,或read_pending_input/3
(如果不是),请阅读一个缓冲区。
答案 1 :(得分:1)
正如Boris所指出的,非重新定位流不能与库(pure_input)一起使用。 read_stream_to_codes / 2,后跟短语/ 2,将为您提供一种实用的方法来测试您的语法与真实数据。
但是,'真实世界'HTML 非常难以解析(即使有内置SGML解析器的支持),因为错误处理不佳。因此,调试DCG可能是一场噩梦,即使是表现良好的语法也是如此。