Prolog 中的简单聊天机器人 - 将 python 翻译成序言

Simple Chatbot in Prolog - translate python to prolog

我正在尝试在 prolog 中做一个简单的聊天机器人,它基本上可以完成此 python 脚本的功能...有人可以帮助我吗?

question = input('Hello, can i help you?')

questions = ["what is ipv4", "what is router", "what is osi"]

answers = [
    "Internet Protocol version 4 is the fourth version of the Internet Protocol.",
    "A router is a device that forwards data packets between computer networks."
    "The OSI Model is an ISO reference computer network model divided into layers of functions."
]

question = question.lower().replace("?", "").strip()

idx = questions.index(question) if question in questions else -1
response = answers[idx] if idx > -1 else "Sorry, answer not found."

print(response)

我在这里被屏蔽了:

:- initialization(main).


list_of_questions(['what is ipv4', 'what is router']).


in_list_of_questions(X) :- 
    list_of_questions(L),
    member(X, L).
    
Res :- in_my_list_of_elements('what is ipv4 ?').

%write(list_of_questions).

main :- write(Res).

这行不通:(

这个怎么样。

注意以下几点:

这是针对 SWI-Prolog 的。

  • 它有谓词read_line_to_codes/2。如果使用另一个 Prolog,则可能必须找到一个替代谓词。
  • SWI-Prolog 区分 strings ("foo") 和 atoms ('foo' or foo).字符串应该用于“文本元素”而不是“类似标识符”的元素。在这种情况下,我们始终使用原子,尽管例如答案和问题是字符串的用例。
  • 我注意到没有 trim/2 谓词 trim 一个原子(即从原子的开始和结束中删除空白)。所以我加了一个。由于 append/3 生成候选人的方式,它不是很有效,但对于短原子来说已经足够好了。 (SWI-Prolog 是将所有内容转换为字符串然后应用特定形式的 split_string/4 的首选方法吗?我希望尽快添加 trim/2。)
  • 原子的处理可以通过将它们转换为“代码列表”来完成,如此处(代码是 SWI-Prolog 中的 Unicode 代码点,这是唯一明智的决定,但其他 Prolog 可能不同)。或者,原子的处理可以通过将它们转换为“字符列表”来完成,即长度为 1 的原子列表,这是在 trimming 谓词中完成的。
question_answer('what is ipv4'   , 'Internet Protocol version 4 is the fourth version of the Internet Protocol.').
question_answer('what is router' , 'A router is a device that forwards data packets between computer networks.').
question_answer('what is osi'    , 'The OSI Model is an ISO reference computer network model divided into layers of functions.').

main :-
   format('Hello, can i help you?~n',[]),
   read_line_to_codes(user_input,QCodes1),
   exclude(=(0'?),QCodes1,QCodes2),   
   atom_codes(QAtom1,QCodes2),
   downcase_atom(QAtom1,QAtom2),
   trim(QAtom2,TrimmedAtom),
   (
      question_answer(TrimmedAtom,Answer) 
      -> 
      format('~s~n',[Answer])
      ;
      format('~s~n',['Sorry, answer not found'])
   ),
   !,
   main.


% That additional
% trim(Chars,TrimmedChars)

is_blank(X) :- 
   memberchk(X,[' ','\n','\r','\t']). % should be extended to the whole unicode "blank" class

trim(Atom,TrimmedAtom) :-
   atom_chars(Atom,Chars),
   trim_chars(Chars,TrimmedChars),
   atom_chars(TrimmedAtom,TrimmedChars).

trim_chars(Chars,TrimmedChars) :- 
   append([Prefix,TrimmedChars,Suffix],Chars),
   forall(member(X,Prefix),is_blank(X)),
   forall(member(X,Suffix),is_blank(X)),
   (
      TrimmedChars == [];
      (TrimmedChars = [First|_], \+is_blank(First), last(TrimmedChars,Last), \+is_blank(Last))
   ).

测试运行:

?- [q].
true.

?- main.
Hello, can i help you?
|:     What is IPv4 ?
Internet Protocol version 4 is the fourth version of the Internet Protocol.
Hello, can i help you?
|: What is ROUTER
A router is a device that forwards data packets between computer networks.
Hello, can i help you?
|: Who is Iwakura Lain?
Sorry, answer not found
Hello, can i help you?
|: ^Dfalse.