如何使用Prolog中的读取谓词读取.txt文件中的所有Assembly谓词?

时间:2018-12-04 17:11:26

标签: prolog

这是文件.txt,具有汇编谓词:

brz END //comment
sub ONE
sta SECOND
lda RESULT //comment
add FIRST
bra LOOP

我们必须加载并读取.txt文件,并且必须删除注释并创建如下所示的指令列表:

L=[brz END,sub ONE,...]

1 个答案:

答案 0 :(得分:4)

在像Python这样的常规语言中,您很想用以下方法解决此问题:

result = []
for line in open('file.txt'):
   line = re.replace(line, '//.*', '')
   result.append(line)

在Prolog中,您会发现,为输入内容编写完整的DCG就像语法一样简单。内核中拥有更强大的解析框架,这在某种程度上阻止了Prolog开发大型复杂的字符串和字符敲打功能套件。因此,我希望即使您做了解析为字符串的操作,您也都会再次陷入困境,但是由于缺少正则表达式库或将字符串切分和切块的方法而已。< / p>

与Prolog中的所有内容一样,它比您以前惯用的要冗长得多,但是有些优势从一开始就可能并不明显。这是我为您的玩具问题准备的代码(花了我大约15分钟)。

:- use_module(library(pio)).
:- use_module(library(dcg/basics)).

comment --> "//", string_without("\n", _).
comment --> [].

optarget(A) --> string(S), { atom_codes(A, S) }.

instruction(inst(Op, Target)) --> optarget(Op), " ", whites, 
                                  optarget(Target), whites, comment, "\n".

instructions([Inst|Rest]) --> instruction(Inst), instructions(Rest).
instructions([]) --> [].

这会将您的示例解析为如下内容:

?- phrase_from_file(instructions(Inst), "test.txt").
Inst = [inst(brz, 'END'), inst(sub, 'ONE'), inst(sta, 'SECOND'), 
        inst(lda, 'RESULT'), inst(add, 'FIRST'), inst(bra, 'LOOP')] .

您不应该通过将dcg / basics用于与HTTP不相关的事情而感到自己在“滥用” dcg / basics。该库是由于其通用性而在不久前提取的。

  • 我在这里使用whites来放弃空格,但是由于它不会成功,因此在两个optarget调用之间需要一个明确的空格
  • 除了optarget//1以外,您还可以做其他有趣的事情,例如仅解析您的真实指令或真实参数,但我不知道它们是什么,所以您在这里得到了原子
  • 事实证明,您的指令接受了更多参数,您可以添加其他instruction//1规则来分别处理它们。反正那可能就是我要做的
  • 如果您意识到不同的表示形式对下游处理更有利,那么通过更改instruction//1instructions//1来实现它应该很容易