Проблема при чтении обратной косой черты в Прологе - PullRequest
2 голосов
/ 16 мая 2010

Я пишу лексер в Прологе, который будет использоваться как часть функционального интерпретатора языка. Спецификация языка позволяет использовать такие выражения, как, например, let \x = x + 2;. Что я хочу, чтобы lexer сделал для такого ввода, так это "return":

[tokLet, tokLambda, tokVar(x), tokEq, tokVar(x), tokPlus, tokNumber(2), tokSColon] 

и проблема в том, что Пролог, похоже, игнорирует символ \ и «возвращает» строку, написанную выше, за исключением tokLambda.

Один из подходов к решению этой проблемы состоит в том, чтобы каким-то образом добавить второй обратный слеш перед / после каждого вхождения этого кода в программный код (поскольку все работает нормально, если я изменяю исходный ввод на let \\x = x + 2;), но мне это не очень нравится. ,

Есть идеи?

EDIT: Если у кого-то должны быть похожие проблемы, я так решил:

main(File) :-
  open(File,read,Stream),
  read_stream_to_codes(Stream, Codes),
  lexer(X,Codes,[]),
    ... invoke other methods

1 Ответ

1 голос
/ 16 мая 2010

Откуда вы взяли строку let \x = x + 2;?

  • Если это в вашей программе Prolog: да, вы должны удвоить обратную косую черту.
  • Если это из внешнего файла: как вы читаете оттуда? Возможно, этот предикат специально интерпретирует обратную косую черту.

Я был вдохновлен этой проблемой и написал немного кода, который должен быть переносим на все реализации Prolog:

% readline(-Line)
%
% Reads one line from the current input. The line is then returned as a list
% of one-character atoms, excluding the newline character.
% The returned line doesn't tell you whether the end of input has been reached
% or not.
readline(Line) :-
    'readline:read'([], Reversed),
    reverse(Line, Reversed).

'readline:read'(Current, Out) :-
    get_char(C), 'readline:append'(C, Current, Out).

'readline:append'(-1, Current, Current) :- !.
'readline:append'('\n', Current, Current) :- !.
'readline:append'(C, Current, Line) :-
    'readline:read'([C | Current], Line).

Я попробовал, и у меня это сработало.

Конечно, как объясняется в вопросе 1846199 , вы также можете использовать read_line_to_codes/2.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...