From 9322052b1877c5768a80552e6354a690e000c1b8 Mon Sep 17 00:00:00 2001 From: Adrian Date: Tue, 14 Jun 2022 12:57:51 +0200 Subject: [PATCH] update --- .../AJN_final (1)-checkpoint.ipynb | 426 +++++++++ AJN_final (1).ipynb | 466 ++-------- chatbot.ipynb | 140 ++- .../Elza_chatbot_as.ipynb | 0 eliza.py => eliza/eliza.py | 0 .../eliza_po_polsku.py | 872 +++++++++--------- modules/AJN.py | 70 +- modules/DST.py | 16 +- modules/NLG.py | 45 +- 9 files changed, 1129 insertions(+), 906 deletions(-) create mode 100644 .ipynb_checkpoints/AJN_final (1)-checkpoint.ipynb rename Elza_chatbot_as.ipynb => eliza/Elza_chatbot_as.ipynb (100%) rename eliza.py => eliza/eliza.py (100%) rename eliza_po_polsku.py => eliza/eliza_po_polsku.py (96%) diff --git a/.ipynb_checkpoints/AJN_final (1)-checkpoint.ipynb b/.ipynb_checkpoints/AJN_final (1)-checkpoint.ipynb new file mode 100644 index 0000000..aae09e0 --- /dev/null +++ b/.ipynb_checkpoints/AJN_final (1)-checkpoint.ipynb @@ -0,0 +1,426 @@ +{ + "cells": [ + { + "cell_type": "code", + "execution_count": null, + "id": "explicit-slovak", + "metadata": {}, + "outputs": [], + "source": [ + "%%writefile ./grammar/hello.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar hello;\n", + "\n", + "public = ;\n", + "\n", + " = czesc | hej | witaj | hey | hello | dzień dobry | siema | siemanko;" + ] + }, + { + "cell_type": "code", + "execution_count": 16, + "id": "upset-brunswick", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Writing ./grammar/bye.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/bye.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar bye;\n", + "\n", + "public = ;\n", + "\n", + " = do usłyszenia | do widzenia | do zobaczenia | na razie | bye | zegnaj | nara | musze juz isc;\n" + ] + }, + { + "cell_type": "code", + "execution_count": 26, + "id": "amateur-format", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/repertuar.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/repertuar.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar repertuar;\n", + "\n", + "public = [aktualny | obecny | aktualnie | obecnie | teraz] [repertuar];\n", + "\n", + " = prosze podac | podaj | jaki jest | co [teraz] gracie | co leci | jakie sa filmy | jakie filmy gracie;\n", + "\n", + "\n" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "dressed-judge", + "metadata": {}, + "outputs": [], + "source": [ + "%%writefile ./grammar/cancel.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar cancel;\n", + "\n", + "public = ;\n", + "\n", + " = chce | chcialbym | chcialabym | prosze;\n", + "\n", + " = odwolac | zrezygnowac | anulowac ([bilety]|[bilet]|[z biletow]|[rezerwacje]|[z rezerwacji]);" + ] + }, + { + "cell_type": "code", + "execution_count": 25, + "id": "automated-friendship", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/book.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/book.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar book;\n", + "\n", + "public = [] [] [] [];\n", + "\n", + " = (chce | chcialbym | chcialabym | poprosze) [zarezerwowac];\n", + "\n", + " = {ilosc} (bilety | biletow | bilet);\n", + "\n", + " = jeden | dwa | trzy | cztery | piec | szesc | siedem | osiem | dziewiec | dziesiec |1|2|3|4|5|6|7|8|9|10;\n", + "\n", + " = na [film] {tytul};\n", + "\n", + " = Batman | Batmana | Uncharted | Pitbull | Ambulans | Bunkier strachu | Corka | Corke | Inni ludzie | Śmierć na Nilu | Skarb Mikołajka;\n", + "\n", + " = na {dzien};\n", + "\n", + " = (dzisiaj | jutro | poniedziałek | wtorek | srode | czwartek | piatek | sobotę | niedziele) | ;\n", + "\n", + " = (8|9|10|11|12|13|14|15) [czerwca]; \n", + "\n", + " = na [godzinę] {godzina};\n", + "\n", + " = [];\n", + "\n", + " = 10|11|12|13|14|15|16|17|18|19|20|21|22|23 | dziesiata | jedenasta | dwunasta | trzynasta | czternasta | pietnasta | szesnasta | siedemnasta | osiemnasta | dziewietnasta | dwudziesta;\n", + "\n", + " = pietnaście | trzydzieści | czterdziesci piec| 15 | 30 | 45;" + ] + }, + { + "cell_type": "code", + "execution_count": 15, + "id": "attended-portugal", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/ilosc_bil.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/ilosc_bil.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar ilosc_bil;\n", + "\n", + "public = [] [];\n", + "\n", + " = (chce | chcialbym | chcialabym | poprosze) [zarezerwowac];\n", + "\n", + " = {ilosc} [(bilety | biletow | bilet)];\n", + "\n", + " = jeden | dwa | trzy | cztery | piec | szesc | siedem | osiem | dziewiec | dziesiec |1|2|3|4|5|6|7|8|9|10;\n" + ] + }, + { + "cell_type": "code", + "execution_count": 24, + "id": "floating-lender", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/tyt_filmu.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/tyt_filmu.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar tyt_filmu;\n", + "\n", + "public = [] [];\n", + "\n", + " = (chce | chcialbym | chcialabym | poprosze) [zarezerwowac];\n", + "\n", + " = [na] [film] {tytul};\n", + "\n", + " = Batman | Batmana | Uncharted | Pitbull | Ambulans | Bunkier strachu | Corka | Corke | Inni ludzie | Śmierć na Nilu | Skarb Mikołajka;" + ] + }, + { + "cell_type": "code", + "execution_count": 1, + "id": "indirect-edward", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/dni.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/dni.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar dni;\n", + "\n", + "public = [] [];\n", + "\n", + " = (chce | chcialbym | chcialabym | poprosze) [zarezerwowac];\n", + "\n", + " = na {dzien};\n", + "\n", + " = (dzisiaj | jutro | poniedziałek | wtorek | srode | czwartek | piatek | sobotę | niedziele) | ;\n", + "\n", + " = (15|16|17|18|19|20|21|22|23|24|25|26|27|28|29|30) [czerwca]; \n" + ] + }, + { + "cell_type": "code", + "execution_count": 18, + "id": "continental-syria", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/godziny.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/godziny.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar godziny;\n", + "\n", + "public = [] ;\n", + "\n", + " = (chce | chcialbym | chcialabym | poprosze) [zarezerwowac];\n", + "\n", + " = na [godzine] {godzina};\n", + "\n", + " = [];\n", + "\n", + " = 10|11|12|13|14|15|16|17|18|19|20|21|22|23 | dziesiata | jedenasta | dwunasta | trzynasta | czternasta | pietnasta | szesnasta | siedemnasta | osiemnasta | dziewietnasta | dwudziesta;\n", + "\n", + " = pietnaście | trzydzieści | czterdziesci piec| 15 | 30 | 45;" + ] + }, + { + "cell_type": "code", + "execution_count": 7, + "id": "everyday-sullivan", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/miejsca.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/miejsca.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar miejsca;\n", + "\n", + "public = [z | na | w] {miejsce};\n", + "\n", + " = dole | gorze | srodku | tylu | blizej | przodu;\n" + ] + }, + { + "cell_type": "code", + "execution_count": 12, + "id": "unexpected-vietnamese", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/nr_tel.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/nr_tel.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar numer;\n", + "\n", + "public = {numer};\n", + "\n", + " = +;\n", + "\n", + " = 0|1|2|3|4|5|6|7|8|9\n" + ] + }, + { + "cell_type": "code", + "execution_count": 15, + "id": "annual-bridge", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/bye.jsgf\n" + ] + } + ], + "source": [] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "warming-pharmaceutical", + "metadata": {}, + "outputs": [], + "source": [] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "upset-inclusion", + "metadata": {}, + "outputs": [], + "source": [ + "!jupyter nbconvert --to script MST.ipynb" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "absolute-banana", + "metadata": {}, + "outputs": [], + "source": [ + "!jupyter nbconvert --to script AJN_final.ipynb" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "static-science", + "metadata": {}, + "outputs": [], + "source": [] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "loose-championship", + "metadata": {}, + "outputs": [], + "source": [] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "emerging-conviction", + "metadata": {}, + "outputs": [], + "source": [] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "polished-identification", + "metadata": {}, + "outputs": [], + "source": [] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "unexpected-quarter", + "metadata": {}, + "outputs": [], + "source": [] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "minus-archive", + "metadata": {}, + "outputs": [], + "source": [] + } + ], + "metadata": { + "kernelspec": { + "display_name": "Python 3 (ipykernel)", + "language": "python", + "name": "python3" + }, + "language_info": { + "codemirror_mode": { + "name": "ipython", + "version": 3 + }, + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.9.7" + } + }, + "nbformat": 4, + "nbformat_minor": 5 +} diff --git a/AJN_final (1).ipynb b/AJN_final (1).ipynb index fd39208..aae09e0 100644 --- a/AJN_final (1).ipynb +++ b/AJN_final (1).ipynb @@ -3,7 +3,7 @@ { "cell_type": "code", "execution_count": null, - "id": "completed-luxury", + "id": "explicit-slovak", "metadata": {}, "outputs": [], "source": [ @@ -17,10 +17,35 @@ " = czesc | hej | witaj | hey | hello | dzień dobry | siema | siemanko;" ] }, + { + "cell_type": "code", + "execution_count": 16, + "id": "upset-brunswick", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Writing ./grammar/bye.jsgf\n" + ] + } + ], + "source": [ + "%%writefile ./grammar/bye.jsgf\n", + "#JSGF V1.0 UTF-8 pl;\n", + "\n", + "grammar bye;\n", + "\n", + "public = ;\n", + "\n", + " = do usłyszenia | do widzenia | do zobaczenia | na razie | bye | zegnaj | nara | musze juz isc;\n" + ] + }, { "cell_type": "code", "execution_count": 26, - "id": "stable-teacher", + "id": "amateur-format", "metadata": {}, "outputs": [ { @@ -47,7 +72,7 @@ { "cell_type": "code", "execution_count": null, - "id": "broken-typing", + "id": "dressed-judge", "metadata": {}, "outputs": [], "source": [ @@ -66,7 +91,7 @@ { "cell_type": "code", "execution_count": 25, - "id": "moving-dictionary", + "id": "automated-friendship", "metadata": {}, "outputs": [ { @@ -113,7 +138,7 @@ { "cell_type": "code", "execution_count": 15, - "id": "democratic-vietnamese", + "id": "attended-portugal", "metadata": {}, "outputs": [ { @@ -142,7 +167,7 @@ { "cell_type": "code", "execution_count": 24, - "id": "valid-provincial", + "id": "floating-lender", "metadata": {}, "outputs": [ { @@ -170,8 +195,8 @@ }, { "cell_type": "code", - "execution_count": 23, - "id": "declared-vessel", + "execution_count": 1, + "id": "indirect-edward", "metadata": {}, "outputs": [ { @@ -196,13 +221,13 @@ "\n", " = (dzisiaj | jutro | poniedziałek | wtorek | srode | czwartek | piatek | sobotę | niedziele) | ;\n", "\n", - " = (8|9|10|11|12|13|14|15) [czerwca]; \n" + " = (15|16|17|18|19|20|21|22|23|24|25|26|27|28|29|30) [czerwca]; \n" ] }, { "cell_type": "code", - "execution_count": 21, - "id": "animated-guarantee", + "execution_count": 18, + "id": "continental-syria", "metadata": {}, "outputs": [ { @@ -219,11 +244,11 @@ "\n", "grammar godziny;\n", "\n", - "public = [] [];\n", + "public = [] ;\n", "\n", " = (chce | chcialbym | chcialabym | poprosze) [zarezerwowac];\n", "\n", - " = na [godzinę] {godzina};\n", + " = na [godzine] {godzina};\n", "\n", " = [];\n", "\n", @@ -235,7 +260,7 @@ { "cell_type": "code", "execution_count": 7, - "id": "registered-product", + "id": "everyday-sullivan", "metadata": {}, "outputs": [ { @@ -259,8 +284,8 @@ }, { "cell_type": "code", - "execution_count": 8, - "id": "neutral-thumbnail", + "execution_count": 12, + "id": "unexpected-vietnamese", "metadata": {}, "outputs": [ { @@ -279,130 +304,39 @@ "\n", "public = {numer};\n", "\n", - " = 123456789 | 123123123 | 123456123;\n" + " = +;\n", + "\n", + " = 0|1|2|3|4|5|6|7|8|9\n" ] }, + { + "cell_type": "code", + "execution_count": 15, + "id": "annual-bridge", + "metadata": {}, + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Overwriting ./grammar/bye.jsgf\n" + ] + } + ], + "source": [] + }, { "cell_type": "code", "execution_count": null, - "id": "confirmed-quantum", + "id": "warming-pharmaceutical", "metadata": {}, "outputs": [], "source": [] }, - { - "cell_type": "code", - "execution_count": 9, - "id": "looking-alias", - "metadata": {}, - "outputs": [], - "source": [ - "import jsgf\n", - "from os import listdir\n", - "from os.path import isfile, join\n", - "\n", - "mypath = \"./grammar/\"\n", - "onlyfiles = [f for f in listdir(mypath) if isfile(join(mypath, f))]\n", - "\n", - "grammars = []\n", - "\n", - "for grammarFile in onlyfiles:\n", - " grammar = jsgf.parse_grammar_file(mypath + grammarFile)\n", - " grammars.append(grammar)\n", - " \n", - "\n", - "def get_dialog_act(rule):\n", - " slots = []\n", - " get_slots(rule.expansion, slots)\n", - " return {'act': rule.grammar.name, 'slots': slots}\n", - "\n", - "def get_slots(expansion, slots):\n", - " if expansion.tag != '':\n", - " slots.append((expansion.tag, expansion.current_match))\n", - " return\n", - "\n", - " for child in expansion.children:\n", - " get_slots(child, slots)\n", - "\n", - " if not expansion.children and isinstance(expansion, jsgf.NamedRuleRef):\n", - " get_slots(expansion.referenced_rule.expansion, slots)\n", - "\n", - "def nlu(utterance):\n", - " matched = None\n", - " for grammar in grammars:\n", - " matched = grammar.find_matching_rules(utterance)\n", - " if matched:\n", - " break\n", - "\n", - " if matched:\n", - " return get_dialog_act(matched[0])\n", - " else:\n", - " return {'act': 'null', 'slots': []}\n", - "\n", - " \n", - "def ajn(text):\n", - " frame = nlu(text)\n", - " return frame\n" - ] - }, - { - "cell_type": "code", - "execution_count": 4, - "id": "statutory-falls", - "metadata": {}, - "outputs": [], - "source": [ - "ajn = Ajn()" - ] - }, - { - "cell_type": "code", - "execution_count": 5, - "id": "through-function", - "metadata": {}, - "outputs": [ - { - "data": { - "text/plain": [ - ">" - ] - }, - "execution_count": 5, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [ - "ajn.nlu" - ] - }, - { - "cell_type": "code", - "execution_count": 7, - "id": "fantastic-yemen", - "metadata": {}, - "outputs": [ - { - "ename": "TypeError", - "evalue": "nlu() takes 1 positional argument but 2 were given", - "output_type": "error", - "traceback": [ - "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m", - "\u001b[0;31mTypeError\u001b[0m Traceback (most recent call last)", - "\u001b[0;32m\u001b[0m in \u001b[0;36m\u001b[0;34m\u001b[0m\n\u001b[0;32m----> 1\u001b[0;31m \u001b[0mresult\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0majn\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mnlu\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m'Chcialabym zarezerwowac 10 biletow na film corke na 16 45'\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 2\u001b[0m \u001b[0mresult\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n", - "\u001b[0;31mTypeError\u001b[0m: nlu() takes 1 positional argument but 2 were given" - ] - } - ], - "source": [ - "result = ajn.nlu('Chcialabym zarezerwowac 10 biletow na film corke na 16 45')\n", - "result" - ] - }, { "cell_type": "code", "execution_count": null, - "id": "chemical-athens", + "id": "upset-inclusion", "metadata": {}, "outputs": [], "source": [ @@ -412,7 +346,7 @@ { "cell_type": "code", "execution_count": null, - "id": "quantitative-proposition", + "id": "absolute-banana", "metadata": {}, "outputs": [], "source": [ @@ -422,235 +356,7 @@ { "cell_type": "code", "execution_count": null, - "id": "based-action", - "metadata": {}, - "outputs": [], - "source": [] - }, - { - "cell_type": "code", - "execution_count": 1, - "id": "cosmetic-beijing", - "metadata": {}, - "outputs": [], - "source": [ - "import jsgf\n", - "from os import listdir\n", - "from os.path import isfile, join\n", - "\n", - "mypath = \"./grammar/\"\n", - "onlyfiles = [f for f in listdir(mypath) if isfile(join(mypath, f))]\n", - "\n", - "grammars = []\n", - "\n", - "for grammarFile in onlyfiles:\n", - " grammar = jsgf.parse_grammar_file(mypath + grammarFile)\n", - " grammars.append(grammar)\n", - "\n", - " \n", - " \n", - "def get_dialog_act(rule):\n", - " slots = []\n", - " get_slots(rule.expansion, slots)\n", - " return {'act': rule.grammar.name, 'slots': slots}\n", - "\n", - "def get_slots(expansion, slots):\n", - " if expansion.tag != '':\n", - " slots.append((expansion.tag, expansion.current_match))\n", - " return\n", - "\n", - " for child in expansion.children:\n", - " get_slots(child, slots)\n", - "\n", - " if not expansion.children and isinstance(expansion, jsgf.NamedRuleRef):\n", - " get_slots(expansion.referenced_rule.expansion, slots)\n", - "\n", - "def nlu(utterance):\n", - " matched = None\n", - " for grammar in grammars:\n", - " matched = grammar.find_matching_rules(utterance)\n", - " if matched:\n", - " break\n", - "\n", - " if matched:\n", - " return get_dialog_act(matched[0])\n", - " else:\n", - " return {'act': 'null', 'slots': []}\n", - " \n", - "res = nlu('chcialbym zarezerwowac 2 bilety na corke na 16')" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "detected-crowd", - "metadata": {}, - "outputs": [], - "source": [ - "ajn = Ajn()" - ] - }, - { - "cell_type": "code", - "execution_count": 2, - "id": "technological-applicant", - "metadata": {}, - "outputs": [ - { - "data": { - "text/plain": [ - "{'act': 'book',\n", - " 'slots': [('ilosc', '2'),\n", - " ('tytul', 'Corke'),\n", - " ('dzien', None),\n", - " ('godzina', '16')]}" - ] - }, - "execution_count": 2, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [ - "res" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "acknowledged-measurement", - "metadata": {}, - "outputs": [], - "source": [] - }, - { - "cell_type": "code", - "execution_count": 3, - "id": "living-reservoir", - "metadata": {}, - "outputs": [], - "source": [ - "\n", - "class Dst:\n", - " \n", - " def __init__(self):\n", - " self.messages = []\n", - " self.checklist = {\n", - " \"ilosc\": None,\n", - " \"tytul\": None,\n", - " \"dzien\": None,\n", - " \"godzina\": None\n", - " }\n", - " self.history = []\n", - " \n", - " def store(self, message):\n", - " self.messages.append(message)\n", - "\n", - " def get_messages(self):\n", - " return self.messages\n", - "\n", - " def get_next_question(self):\n", - " for key, value in self.checklist.items():\n", - " if value == None:\n", - " return key\n", - "\n", - " def save_answer(self, slots):\n", - " for slot in slots:\n", - " self.checklist[slot[0]] = slot[1]\n", - "\n", - " self.messages.append(slots)\n", - " \n", - " def update(self, user_act=None):\n", - " for intent, domain, slot, value in user_act:\n", - " domain = domain.lower()\n", - " intent = intent.lower()\n", - " slot = slot.lower()\n", - " print(domain,intent,slot)" - ] - }, - { - "cell_type": "code", - "execution_count": 4, - "id": "organizational-overhead", - "metadata": {}, - "outputs": [], - "source": [ - "dst = Dst()" - ] - }, - { - "cell_type": "code", - "execution_count": 5, - "id": "flying-preliminary", - "metadata": {}, - "outputs": [], - "source": [ - "dst.save_answer(res['slots'])" - ] - }, - { - "cell_type": "code", - "execution_count": 6, - "id": "effective-arbitration", - "metadata": {}, - "outputs": [ - { - "data": { - "text/plain": [ - "[('ilosc', '2'), ('tytul', 'Corke'), ('dzien', None), ('godzina', '16')]" - ] - }, - "execution_count": 6, - "metadata": {}, - "output_type": "execute_result" - } - ], - "source": [ - "res['slots']" - ] - }, - { - "cell_type": "code", - "execution_count": 7, - "id": "warming-oracle", - "metadata": {}, - "outputs": [], - "source": [ - "next_question = dst.get_next_question()" - ] - }, - { - "cell_type": "code", - "execution_count": 8, - "id": "immune-conducting", - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "{'ilosc': '2', 'tytul': 'Corke', 'dzien': None, 'godzina': '16'}\n" - ] - } - ], - "source": [ - "print(dst.checklist)" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "therapeutic-ending", - "metadata": {}, - "outputs": [], - "source": [ - "user_act" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "clinical-removal", + "id": "static-science", "metadata": {}, "outputs": [], "source": [] @@ -658,31 +364,7 @@ { "cell_type": "code", "execution_count": null, - "id": "elder-complexity", - "metadata": {}, - "outputs": [ - { - "name": "stdout", - "output_type": "stream", - "text": [ - "dzien\n" - ] - } - ], - "source": [ - "next_question = dst.get_next_question()\n", - "while (next_question):\n", - " print(next_question)\n", - " response = input()\n", - " res = nlu(response)\n", - " dst.save_answer(res['slots'])\n", - " next_question = dst.get_next_question()" - ] - }, - { - "cell_type": "code", - "execution_count": null, - "id": "leading-gospel", + "id": "loose-championship", "metadata": {}, "outputs": [], "source": [] @@ -690,7 +372,7 @@ { "cell_type": "code", "execution_count": null, - "id": "cleared-malpractice", + "id": "emerging-conviction", "metadata": {}, "outputs": [], "source": [] @@ -698,7 +380,7 @@ { "cell_type": "code", "execution_count": null, - "id": "single-browser", + "id": "polished-identification", "metadata": {}, "outputs": [], "source": [] @@ -706,7 +388,15 @@ { "cell_type": "code", "execution_count": null, - "id": "sunrise-zoning", + "id": "unexpected-quarter", + "metadata": {}, + "outputs": [], + "source": [] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "minus-archive", "metadata": {}, "outputs": [], "source": [] @@ -714,7 +404,7 @@ ], "metadata": { "kernelspec": { - "display_name": "Python 3", + "display_name": "Python 3 (ipykernel)", "language": "python", "name": "python3" }, @@ -728,7 +418,7 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.7.3" + "version": "3.9.7" } }, "nbformat": 4, diff --git a/chatbot.ipynb b/chatbot.ipynb index ee3b22d..a12947e 100644 --- a/chatbot.ipynb +++ b/chatbot.ipynb @@ -2,101 +2,143 @@ "cells": [ { "cell_type": "code", - "execution_count": 2, - "id": "encouraging-december", + "execution_count": 1, + "id": "surgical-trainer", "metadata": {}, "outputs": [ - { - "name": "stdin", - "output_type": "stream", - "text": [ - ">>> chce 2 bilety\n" - ] - }, { "name": "stdout", "output_type": "stream", "text": [ - "tytul\n", - "{'ilosc': '2', 'tytul': None, 'dzien': None, 'godzina': None}\n", - "Na jaki film ma zostać dokonana rezerwacja?\n" + "Jeśli chcesz zresetować rozmowę wpisz \"reset\"\n" ] }, { "name": "stdin", "output_type": "stream", "text": [ - ">>> chce na film batman\n" + ">>> chce 2 bilety na batmana na jutro\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ - "ilosc\n", - "{'ilosc': None, 'tytul': 'Batman', 'dzien': None, 'godzina': None}\n", - "Ile biletów ma zostać zarezerwowanych?\n" + "godzina\n", + "{'ilosc': '2', 'tytul': 'Batmana', 'dzien': 'jutro', 'godzina': None, 'miejsce': None, 'numer': None}\n", + "[('ilosc', '2'), ('tytul', 'Batmana'), ('dzien', 'jutro'), ('godzina', None)]\n", + "book\n", + "Na którą godzinę ma być dokonana rezerwacja?\n" ] }, { "name": "stdin", "output_type": "stream", "text": [ - ">>> chce 2 bilety\n" + ">>> na 17\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ - "tytul\n", - "{'ilosc': '2', 'tytul': None, 'dzien': None, 'godzina': None}\n", - "Na jaki film ma zostać dokonana rezerwacja?\n" + "godzina\n", + "{'ilosc': '2', 'tytul': 'Batmana', 'dzien': '17', 'godzina': None, 'miejsce': None, 'numer': None}\n", + "[('dzien', '17')]\n", + "dni\n", + "Na którą godzinę ma być dokonana rezerwacja?\n" ] }, { "name": "stdin", "output_type": "stream", "text": [ - ">>> chce 2 bilety na film batman\n" + ">>> na godzine 17\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ - "dzien\n", - "{'ilosc': '2', 'tytul': 'Batman', 'dzien': None, 'godzina': None}\n", - "Na który dzień ma być dokonana rezerwacja?\n" + "miejsce\n", + "{'ilosc': '2', 'tytul': 'Batmana', 'dzien': '17', 'godzina': '17', 'miejsce': None, 'numer': None}\n", + "[('godzina', '17')]\n", + "godziny\n", + "Czy miejsca mają być z przodu, z tyłu czy na środku?\n" ] }, { "name": "stdin", "output_type": "stream", "text": [ - ">>> chce na jutro\n" + ">>> na środku\n" ] }, { "name": "stdout", "output_type": "stream", "text": [ - "ilosc\n", - "{'ilosc': None, 'tytul': None, 'dzien': 'jutro', 'godzina': None}\n", - "Ile biletów ma zostać zarezerwowanych?\n" + "numer\n", + "{'ilosc': '2', 'tytul': 'Batmana', 'dzien': '17', 'godzina': '17', 'miejsce': 'srodku', 'numer': None}\n", + "[('miejsce', 'srodku')]\n", + "miejsca\n", + "Na jaki numer telefonu ma zostać dokonana rezerwacja?\n" ] }, { - "ename": "KeyboardInterrupt", - "evalue": "Interrupted by user", - "output_type": "error", - "traceback": [ - "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m", - "\u001b[0;31mKeyboardInterrupt\u001b[0m Traceback (most recent call last)", - "\u001b[0;32m\u001b[0m in \u001b[0;36m\u001b[0;34m\u001b[0m\n\u001b[1;32m 12\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 13\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 14\u001b[0;31m \u001b[0mtext\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0minput\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m'>>>'\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 15\u001b[0m \u001b[0mframe\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0majn\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mtext\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 16\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n", - "\u001b[0;32m/usr/local/lib/python3.7/dist-packages/ipykernel/kernelbase.py\u001b[0m in \u001b[0;36mraw_input\u001b[0;34m(self, prompt)\u001b[0m\n\u001b[1;32m 849\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0m_parent_ident\u001b[0m\u001b[0;34m,\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 850\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0m_parent_header\u001b[0m\u001b[0;34m,\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m--> 851\u001b[0;31m \u001b[0mpassword\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0;32mFalse\u001b[0m\u001b[0;34m,\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 852\u001b[0m )\n\u001b[1;32m 853\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n", - "\u001b[0;32m/usr/local/lib/python3.7/dist-packages/ipykernel/kernelbase.py\u001b[0m in \u001b[0;36m_input_request\u001b[0;34m(self, prompt, ident, parent, password)\u001b[0m\n\u001b[1;32m 890\u001b[0m \u001b[0;32mexcept\u001b[0m \u001b[0mKeyboardInterrupt\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 891\u001b[0m \u001b[0;31m# re-raise KeyboardInterrupt, to truncate traceback\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m--> 892\u001b[0;31m \u001b[0;32mraise\u001b[0m \u001b[0mKeyboardInterrupt\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m\"Interrupted by user\"\u001b[0m\u001b[0;34m)\u001b[0m \u001b[0;32mfrom\u001b[0m \u001b[0;32mNone\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m 893\u001b[0m \u001b[0;32mexcept\u001b[0m \u001b[0mException\u001b[0m \u001b[0;32mas\u001b[0m \u001b[0me\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 894\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mlog\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mwarning\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m\"Invalid Message:\"\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mexc_info\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0;32mTrue\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n", - "\u001b[0;31mKeyboardInterrupt\u001b[0m: Interrupted by user" + "name": "stdin", + "output_type": "stream", + "text": [ + ">>> 1\n" + ] + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "numer\n", + "{'ilosc': '2', 'tytul': 'Batmana', 'dzien': '17', 'godzina': '17', 'miejsce': 'srodku', 'numer': None}\n", + "[('numer', '1')]\n", + "numer\n", + "Proszę podać poprawny numer telefonu.\n", + "Na jaki numer telefonu ma zostać dokonana rezerwacja?\n" + ] + }, + { + "name": "stdin", + "output_type": "stream", + "text": [ + ">>> 1212\n" + ] + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "numer\n", + "{'ilosc': '2', 'tytul': 'Batmana', 'dzien': '17', 'godzina': '17', 'miejsce': 'srodku', 'numer': None}\n", + "[('numer', '1 2 1 2')]\n", + "numer\n", + "Proszę podać poprawny numer telefonu.\n", + "Na jaki numer telefonu ma zostać dokonana rezerwacja?\n" + ] + }, + { + "name": "stdin", + "output_type": "stream", + "text": [ + ">>> 123123123\n" + ] + }, + { + "name": "stdout", + "output_type": "stream", + "text": [ + "None\n", + "{'ilosc': '2', 'tytul': 'Batmana', 'dzien': '17', 'godzina': '17', 'miejsce': 'srodku', 'numer': '123123123'}\n", + "[('numer', '1 2 3 1 2 3 1 2 3')]\n", + "numer\n", + "Rezerwacja została dokonana. Potwierdzenie rezerwacji zostanie niebawem przesłane wiadomością SMS. Proszę o przybycie 15 minut przed rozpoczęciem seansu w celu zakupu biletu, w innym przypadku rezerwacja przepada.\n" ] } ], @@ -111,19 +153,31 @@ " \n", " dst = Dst()\n", " next_question = dst.get_next_question()\n", + " print('Jeśli chcesz zresetować rozmowę wpisz \\\"reset\\\"')\n", + " \n", " while (next_question):\n", " \n", " \n", " text = input('>>>')\n", + " \n", + " \n", " frame = ajn(text)\n", " \n", + " dst.reset_if_needed(text)\n", + " \n", + " \n", + " \n", " dst.save_answer(frame['slots'])\n", " \n", " next_question = dst.get_next_question()\n", " print(next_question)\n", " print(dst.checklist)\n", - "# print(frame['act'])\n", - " nlg(next_question)\n", + " print(frame['slots'])\n", + " print(frame['act'])\n", + " nlg(next_question,frame,text)\n", + " \n", + " if text == \"exit\" or frame['act'] == \"bye\":\n", + " break;\n", "\n", " \n", " \n", @@ -133,10 +187,12 @@ { "cell_type": "code", "execution_count": null, - "id": "yellow-acquisition", + "id": "armed-classroom", "metadata": {}, "outputs": [], - "source": [] + "source": [ + "chce 2 bilety na batmana na jutro na 17 15" + ] } ], "metadata": { diff --git a/Elza_chatbot_as.ipynb b/eliza/Elza_chatbot_as.ipynb similarity index 100% rename from Elza_chatbot_as.ipynb rename to eliza/Elza_chatbot_as.ipynb diff --git a/eliza.py b/eliza/eliza.py similarity index 100% rename from eliza.py rename to eliza/eliza.py diff --git a/eliza_po_polsku.py b/eliza/eliza_po_polsku.py similarity index 96% rename from eliza_po_polsku.py rename to eliza/eliza_po_polsku.py index 7ecd2ab..c2e8cf9 100644 --- a/eliza_po_polsku.py +++ b/eliza/eliza_po_polsku.py @@ -1,437 +1,437 @@ -import nltk -import random -import re - -reflections = { - "ja jestem": "ty jesteś", - "ja byłem": "ty byłeś", - "ja": "ty", - "jestem": "jesteś", - "chciałbym": "chciałbyś", - "mam": "masz", - "będę": "będziesz", - "moje": "twoje", - "jesteś": "jestem", - "byłeś": "byłem", - "ty byłeś": "ja byłem", - "będziesz": "będę", - "nasze": "wasze", - "twoje": "moje", - "ty" : "ja", - "ja": "ty", - "my" : "wy", - "jesteśmy": "jesteście", -} - -class Chat: - def __init__(self, pairs, reflections={}): - - self._pairs = [(re.compile(x, re.IGNORECASE), y) for (x, y) in pairs] - self._reflections = reflections - self._regex = self._compile_reflections() - - - def _compile_reflections(self): - sorted_refl = sorted(self._reflections, key=len, reverse=True) - return re.compile( - r"\b({})\b".format("|".join(map(re.escape, sorted_refl))), re.IGNORECASE - ) - - def _substitute(self, str): - - return self._regex.sub( - lambda mo: self._reflections[mo.string[mo.start() : mo.end()]], str.lower() - ) - - def _wildcards(self, response, match): - pos = response.find("%") - while pos >= 0: - num = int(response[pos + 1 : pos + 2]) - response = ( - response[:pos] - + self._substitute(match.group(num)) - + response[pos + 2 :] - ) - pos = response.find("%") - return response - - def respond(self, str): - - # check each pattern - for (pattern, response) in self._pairs: - match = pattern.match(str) - - # did the pattern match? - if match: - resp = random.choice(response) # pick a random response - resp = self._wildcards(resp, match) # process wildcards - - # fix munged punctuation at the end - if resp[-2:] == "?.": - resp = resp[:-2] + "." - if resp[-2:] == "??": - resp = resp[:-2] + "?" - return resp - - - # Hold a conversation with a chatbot - def converse(self, quit="Do widzenia"): - user_input = "" - while user_input != quit: - user_input = quit - try: - user_input = input(">") - except EOFError: - print(user_input) - if user_input: - while user_input[-1] in "!.": - user_input = user_input[:-1] - print(self.respond(user_input)) - - -pairs = ( - ( - r"Potrzebuję (.*)", - ( - "Dlaczego potrzebujesz %1?", - "Czy jesteś pewny, że potrzebujesz %1?", - ), - ), - ( - r"Kto cię stworzył (.*)", - ( - "ELIZA została wynaleziona w 1966 roku przez Weizenbauma. Dlaczego %1?", - - ), - ), - ( - r"Dlaczego ty (.*)", - ( - "Czy naprawdę myślisz, że %1?", - "Być może w końcu będę %1.", - "Czy naprawdę chcesz, żebym %1?", - ), - ), - ( - r"Dlaczego ja (.*)", - ( - "Czy uważasz, że powinieneś być w stanie %1?", - "Gdybyś mógł %1, co byś zrobił?", - "Nie wiem -- dlaczego nie możesz %1?", - "Czy naprawdę próbowałeś?", - ), - ), - ( - r"Nie mogę (.*)", - ( - "Skąd wiesz, że nie możesz %1?", - "Być może mógłbyś, gdybyś spróbował.", - "Co byś musiał zrobić, żeby %1?", - ), - ), - ( - r"Jestem (.*)", - ( - "Przyszedłeś do mnie, bo jesteś %1?", - "Jak długo jesteś %1?", - "Co myślisz o tym, że jesteś %1?", - ), - ), - ( - r"Jestem (.*)", - ( - "Jak się czujesz z tym, że jesteś %1?", - "Czy lubisz być %1?", - "Dlaczego mówisz mi, że jesteś %1?", - "Dlaczego myślisz, że jesteś %1?", - ), - ), - ( - r"Czy jesteś (.*)", - ( - "Dlaczego to ma znaczenie, czy jestem %1?", - "Wolałbyś, gdybym nie była %1?", - "Być może wierzysz, że jestem %1.", - "Mogę być %1 - jak myślisz?", - ), - ), - ( - r"Co (.*)", - ( - "Dlaczego pytasz?", - "Jak pomogłaby ci odpowiedź na to?", - "Co myślisz?", - ), - ), - ( - r"Jak (.*)", - ( - "Jak ty sądzisz?", - "Perhaps you can answer your own question.", - "What is it you're really asking?", - ), - ), - ( - r"Ponieważ (.*)", - ( - "Czy to prawdziwy powód?", - "Jakie inne powody przychodzą Ci na myśl?”,", - "Czy ten powód dotyczy czegokolwiek innego?", - "Jeśli %1, co jeszcze musi być prawdą?", - ), - ), - ( - r"(.*) przepraszam (.*)", - ( - "Wiele razy przeprosiny nie są potrzebne.", - "Co czujesz kiedy przepraszasz?", - ), - ), - ( - r"Cześć(.*)", - ( - "Cześć... cieszę się, że mogłeś dzisiaj wpaść..", - "Cześć... jak się masz dzisiaj?", - "Cześć, jak się dzisiaj czujesz?", - ), - ), - ( - r"Myśle, że (.*)", - ( - "Czy wątpisz w %1?", - "Naprawdę tak myślisz?", - "Ale nie jesteś pewien, że %1?" - ), - ), - ( - r"(.*) przyjaciel (.*)", - ( - "Opowiedz mi więcej o swoich przyjaciołach.", - "Kiedy myślisz o przyjacielu, co przychodzi ci na myśl?", - "Dlaczego miałbyś nie opowiedzieć o przyjacielu z dzieciństwa?", - ), - ), - ( - r"Tak", - ( - "Wydajesz się całkiem pewien.", "OK, ale czy możesz trochę rozwinąć?" - ) - ), - ( - r"(.*) komputer(.*)", - ( - "Naprawdę mówisz o mnie?", - "Czy rozmowa z komputerem wydaje się dziwna?", - "Jak się czujesz przy komputerach?", - "Czy czujesz się zagrożony przez komputery?", - ), - ), - ( - r"To jest (.*)", - ( - "Czy myślisz, że to %1?", - "Może to %1 -- co myślisz?", - "Gdyby to był %1, co byś zrobił?", - "Może być tak, że %1.", - ), - ), - ( - r"Jest to (.*)", - ( - "Wydajesz się bardzo pewny.", - "Gdybym ci powiedziała, że prawdopodobnie nie jest to %1, co byś poczuł?", - ), - ), - ( - r"Czy możesz (.*)", - ( - "Dlaczego myślisz, że nie mogę %1?", - "Gdybym mógł %1, to co?", - "Dlaczego pytasz, czy mogę %1?", - ), - ), - ( - r"Czy mogę (.*)", - ( - "Być może nie chcesz %1.", - "Czy chcesz mieć możliwość %1?", - "Gdybyś mógł %1, czy byś?", - ), - ), - ( - r"Czy mogę (.*)", - ( - "Być może nie chcesz %1.", - "Czy chcesz mieć możliwość %1?", - "Gdybyś mógł %1, czy byś?", - ), - ), - ( - r"Ty jesteś (.*)", - ( - "Jak myślisz, dlaczego jestem %1?", - "Czy cieszy cię myśl, że jestem %1?", - "Być może chciałbyś, żebym był %1.", - "Może naprawdę mówisz o sobie?", - ), - ), - ( - r"Jesteś (.*)", - ( - "Dlaczego mówisz, że jestem %1?", - "Jak myślisz, dlaczego jestem %1?", - "Mówimy o tobie, czy o mnie?", - ), - ), - ( - r"Ja nie (.*)", - ("Czy naprawdę nie %1?", "Dlaczego nie %1?", "Czy chcesz %1?"), - ), - ( - r"Ja czuję (.*)", - ( - "Dobrze, powiedz mi więcej o tych uczuciach.", - "Czy często czujesz %1?", - "Kiedy zwykle czujesz %1?", - "Kiedy czujesz % 1, co robisz?", - ), - ), - ( - r"Mam (.*)", - ( - "Dlaczego mówisz mi, że masz %1?", - "Czy naprawdę masz %1?", - "Teraz, kiedy masz %1, co zrobisz dalej?", - ), - ), - ( - r"Ja chcę (.*)", - ( - "Czy możesz wyjaśnić, dlaczego chcesz %1?", - "Dlaczego %1?", - "Kto jeszcze wie, że chcesz %1?", - ), - ), - ( - r"Jest (.*)", - ( - "Myślisz, że jest %1?", - "Prawdopodobnie istnieje %1.", - "Czy chciałbyś, aby był %1?", - ), - ), - ( - r"Mój (.*)", - ( - "Rozumiem, twój %1.", - "Dlaczego mówisz, że twój %1?", - "Kiedy Twój %1, jak się czujesz?", - ), - ), - ( - r"Ty (.*)", - ( - "Powinniśmy rozmawiać o Tobie, nie o mnie.", - "Dlaczego tak o mnie mówisz?", - "Dlaczego obchodzi cię, czy ja %1?", - ), - ), - ( - r"Dlaczego (.*)", - ( - "Powiedz mi dlaczego %1?", - "Wydaje ci się że, %1?") - ), - ( - r"Ja chcę (.*)", - ( - "Co by dla ciebie znaczyło, gdybyś dostał %1?", - "Dlaczego chcesz %1?", - "Co byś zrobił, gdybyś dostał %1?", - "Jeśli masz %1, co byś zrobił?", - ), - ), - ( - r"(.*) mama(.*)", - ( - "Opowiedz mi więcej o twojej mamie.", - "Jaka była twoja relacja z mamą?", - "Co myślisz o swojej mamie?", - "Jak to się ma do twoich dzisiejszych uczuć?", - "Dobre relacje z rodziną są ważne.", - ), - ), - ( - r"(.*) tata(.*)", - ( - "Opowiedz mi więcej o twoim tacie.", - "Jakie uczucia wzbudzał w tobie twój tata?", - "Co myślisz o swoim tacie?", - "Czy twoja relacja z tatą ma wpływ na twoje dzisiejsze uczucia?", - "Czy masz problemy z okazywaniem uczuć swojej rodzinie?", - ), - ), - ( - r"(.*) dziecko(.*)", - ( - "Miałeś bliskich przyjaciół jako dziecko?", - "Jakie jest twoje ulubione wspomnienie z dzieciństwa?", - "Pamiętasz jakieś sny lub koszmary z dzieciństwa?", - "Czy inne dzieci czasem cię drażniły?", - "Jak myślisz, czy doświadczenia z dzieciństwa wpłynęły na twoje dzisiejsze uczucia?", - ), - ), - ( - r"(.*)\?", - ( - "Dlaczego o to pytasz?", - "Rozważ proszę, czy byłbyś w stanie odpowiedzieć na swoje pytanie.", - "Być może odpowiedź tkwi w tobie?", - "Dlaczego nie powiesz?", - ), - ), - ( - r"Do widzenia", - ( - "Dziękuję, że ze mną porozmawiałeś.", - "Do widzenia.", - "Dziękuję, miłego dnia!", - ), - ), - ( - r"(.*)", - ( - "Opowiedz mi więcej.", - "Zmieńmy trochę temat... Opowiedz mi o swojej rodzinie", - "Czy możesz to rozwinąć?", - "Dlaczego mówisz, że %1?", - "Rozumiem.", - "Bardzo interesujące.", - "%1.", - "Rozumiem, a co ci to mówi?", - "Jak się z tym czujesz?", - "Jak się czujesz, kiedy o tym mówisz?", - ), - ), -) - -eliza_chatbot = Chat(pairs, reflections) - - -def eliza_chat(): - print("Psycholog\n---------") - print("Porozmawiaj z programem, wpisując polskie słowa, używając") - print('dużych oraz małych liter i znaków interpunkcyjnych.') - print('Po zakończeniu wpisz „Do widzenia”') - print("=" * 75) - print("Dzień dobry. Nazywam się Eliza.\nJak się dzisiaj czujesz?") - - eliza_chatbot.converse() - - -def demo(): - eliza_chat() - - -if __name__ == "__main__": +import nltk +import random +import re + +reflections = { + "ja jestem": "ty jesteś", + "ja byłem": "ty byłeś", + "ja": "ty", + "jestem": "jesteś", + "chciałbym": "chciałbyś", + "mam": "masz", + "będę": "będziesz", + "moje": "twoje", + "jesteś": "jestem", + "byłeś": "byłem", + "ty byłeś": "ja byłem", + "będziesz": "będę", + "nasze": "wasze", + "twoje": "moje", + "ty" : "ja", + "ja": "ty", + "my" : "wy", + "jesteśmy": "jesteście", +} + +class Chat: + def __init__(self, pairs, reflections={}): + + self._pairs = [(re.compile(x, re.IGNORECASE), y) for (x, y) in pairs] + self._reflections = reflections + self._regex = self._compile_reflections() + + + def _compile_reflections(self): + sorted_refl = sorted(self._reflections, key=len, reverse=True) + return re.compile( + r"\b({})\b".format("|".join(map(re.escape, sorted_refl))), re.IGNORECASE + ) + + def _substitute(self, str): + + return self._regex.sub( + lambda mo: self._reflections[mo.string[mo.start() : mo.end()]], str.lower() + ) + + def _wildcards(self, response, match): + pos = response.find("%") + while pos >= 0: + num = int(response[pos + 1 : pos + 2]) + response = ( + response[:pos] + + self._substitute(match.group(num)) + + response[pos + 2 :] + ) + pos = response.find("%") + return response + + def respond(self, str): + + # check each pattern + for (pattern, response) in self._pairs: + match = pattern.match(str) + + # did the pattern match? + if match: + resp = random.choice(response) # pick a random response + resp = self._wildcards(resp, match) # process wildcards + + # fix munged punctuation at the end + if resp[-2:] == "?.": + resp = resp[:-2] + "." + if resp[-2:] == "??": + resp = resp[:-2] + "?" + return resp + + + # Hold a conversation with a chatbot + def converse(self, quit="Do widzenia"): + user_input = "" + while user_input != quit: + user_input = quit + try: + user_input = input(">") + except EOFError: + print(user_input) + if user_input: + while user_input[-1] in "!.": + user_input = user_input[:-1] + print(self.respond(user_input)) + + +pairs = ( + ( + r"Potrzebuję (.*)", + ( + "Dlaczego potrzebujesz %1?", + "Czy jesteś pewny, że potrzebujesz %1?", + ), + ), + ( + r"Kto cię stworzył (.*)", + ( + "ELIZA została wynaleziona w 1966 roku przez Weizenbauma. Dlaczego %1?", + + ), + ), + ( + r"Dlaczego ty (.*)", + ( + "Czy naprawdę myślisz, że %1?", + "Być może w końcu będę %1.", + "Czy naprawdę chcesz, żebym %1?", + ), + ), + ( + r"Dlaczego ja (.*)", + ( + "Czy uważasz, że powinieneś być w stanie %1?", + "Gdybyś mógł %1, co byś zrobił?", + "Nie wiem -- dlaczego nie możesz %1?", + "Czy naprawdę próbowałeś?", + ), + ), + ( + r"Nie mogę (.*)", + ( + "Skąd wiesz, że nie możesz %1?", + "Być może mógłbyś, gdybyś spróbował.", + "Co byś musiał zrobić, żeby %1?", + ), + ), + ( + r"Jestem (.*)", + ( + "Przyszedłeś do mnie, bo jesteś %1?", + "Jak długo jesteś %1?", + "Co myślisz o tym, że jesteś %1?", + ), + ), + ( + r"Jestem (.*)", + ( + "Jak się czujesz z tym, że jesteś %1?", + "Czy lubisz być %1?", + "Dlaczego mówisz mi, że jesteś %1?", + "Dlaczego myślisz, że jesteś %1?", + ), + ), + ( + r"Czy jesteś (.*)", + ( + "Dlaczego to ma znaczenie, czy jestem %1?", + "Wolałbyś, gdybym nie była %1?", + "Być może wierzysz, że jestem %1.", + "Mogę być %1 - jak myślisz?", + ), + ), + ( + r"Co (.*)", + ( + "Dlaczego pytasz?", + "Jak pomogłaby ci odpowiedź na to?", + "Co myślisz?", + ), + ), + ( + r"Jak (.*)", + ( + "Jak ty sądzisz?", + "Perhaps you can answer your own question.", + "What is it you're really asking?", + ), + ), + ( + r"Ponieważ (.*)", + ( + "Czy to prawdziwy powód?", + "Jakie inne powody przychodzą Ci na myśl?”,", + "Czy ten powód dotyczy czegokolwiek innego?", + "Jeśli %1, co jeszcze musi być prawdą?", + ), + ), + ( + r"(.*) przepraszam (.*)", + ( + "Wiele razy przeprosiny nie są potrzebne.", + "Co czujesz kiedy przepraszasz?", + ), + ), + ( + r"Cześć(.*)", + ( + "Cześć... cieszę się, że mogłeś dzisiaj wpaść..", + "Cześć... jak się masz dzisiaj?", + "Cześć, jak się dzisiaj czujesz?", + ), + ), + ( + r"Myśle, że (.*)", + ( + "Czy wątpisz w %1?", + "Naprawdę tak myślisz?", + "Ale nie jesteś pewien, że %1?" + ), + ), + ( + r"(.*) przyjaciel (.*)", + ( + "Opowiedz mi więcej o swoich przyjaciołach.", + "Kiedy myślisz o przyjacielu, co przychodzi ci na myśl?", + "Dlaczego miałbyś nie opowiedzieć o przyjacielu z dzieciństwa?", + ), + ), + ( + r"Tak", + ( + "Wydajesz się całkiem pewien.", "OK, ale czy możesz trochę rozwinąć?" + ) + ), + ( + r"(.*) komputer(.*)", + ( + "Naprawdę mówisz o mnie?", + "Czy rozmowa z komputerem wydaje się dziwna?", + "Jak się czujesz przy komputerach?", + "Czy czujesz się zagrożony przez komputery?", + ), + ), + ( + r"To jest (.*)", + ( + "Czy myślisz, że to %1?", + "Może to %1 -- co myślisz?", + "Gdyby to był %1, co byś zrobił?", + "Może być tak, że %1.", + ), + ), + ( + r"Jest to (.*)", + ( + "Wydajesz się bardzo pewny.", + "Gdybym ci powiedziała, że prawdopodobnie nie jest to %1, co byś poczuł?", + ), + ), + ( + r"Czy możesz (.*)", + ( + "Dlaczego myślisz, że nie mogę %1?", + "Gdybym mógł %1, to co?", + "Dlaczego pytasz, czy mogę %1?", + ), + ), + ( + r"Czy mogę (.*)", + ( + "Być może nie chcesz %1.", + "Czy chcesz mieć możliwość %1?", + "Gdybyś mógł %1, czy byś?", + ), + ), + ( + r"Czy mogę (.*)", + ( + "Być może nie chcesz %1.", + "Czy chcesz mieć możliwość %1?", + "Gdybyś mógł %1, czy byś?", + ), + ), + ( + r"Ty jesteś (.*)", + ( + "Jak myślisz, dlaczego jestem %1?", + "Czy cieszy cię myśl, że jestem %1?", + "Być może chciałbyś, żebym był %1.", + "Może naprawdę mówisz o sobie?", + ), + ), + ( + r"Jesteś (.*)", + ( + "Dlaczego mówisz, że jestem %1?", + "Jak myślisz, dlaczego jestem %1?", + "Mówimy o tobie, czy o mnie?", + ), + ), + ( + r"Ja nie (.*)", + ("Czy naprawdę nie %1?", "Dlaczego nie %1?", "Czy chcesz %1?"), + ), + ( + r"Ja czuję (.*)", + ( + "Dobrze, powiedz mi więcej o tych uczuciach.", + "Czy często czujesz %1?", + "Kiedy zwykle czujesz %1?", + "Kiedy czujesz % 1, co robisz?", + ), + ), + ( + r"Mam (.*)", + ( + "Dlaczego mówisz mi, że masz %1?", + "Czy naprawdę masz %1?", + "Teraz, kiedy masz %1, co zrobisz dalej?", + ), + ), + ( + r"Ja chcę (.*)", + ( + "Czy możesz wyjaśnić, dlaczego chcesz %1?", + "Dlaczego %1?", + "Kto jeszcze wie, że chcesz %1?", + ), + ), + ( + r"Jest (.*)", + ( + "Myślisz, że jest %1?", + "Prawdopodobnie istnieje %1.", + "Czy chciałbyś, aby był %1?", + ), + ), + ( + r"Mój (.*)", + ( + "Rozumiem, twój %1.", + "Dlaczego mówisz, że twój %1?", + "Kiedy Twój %1, jak się czujesz?", + ), + ), + ( + r"Ty (.*)", + ( + "Powinniśmy rozmawiać o Tobie, nie o mnie.", + "Dlaczego tak o mnie mówisz?", + "Dlaczego obchodzi cię, czy ja %1?", + ), + ), + ( + r"Dlaczego (.*)", + ( + "Powiedz mi dlaczego %1?", + "Wydaje ci się że, %1?") + ), + ( + r"Ja chcę (.*)", + ( + "Co by dla ciebie znaczyło, gdybyś dostał %1?", + "Dlaczego chcesz %1?", + "Co byś zrobił, gdybyś dostał %1?", + "Jeśli masz %1, co byś zrobił?", + ), + ), + ( + r"(.*) mama(.*)", + ( + "Opowiedz mi więcej o twojej mamie.", + "Jaka była twoja relacja z mamą?", + "Co myślisz o swojej mamie?", + "Jak to się ma do twoich dzisiejszych uczuć?", + "Dobre relacje z rodziną są ważne.", + ), + ), + ( + r"(.*) tata(.*)", + ( + "Opowiedz mi więcej o twoim tacie.", + "Jakie uczucia wzbudzał w tobie twój tata?", + "Co myślisz o swoim tacie?", + "Czy twoja relacja z tatą ma wpływ na twoje dzisiejsze uczucia?", + "Czy masz problemy z okazywaniem uczuć swojej rodzinie?", + ), + ), + ( + r"(.*) dziecko(.*)", + ( + "Miałeś bliskich przyjaciół jako dziecko?", + "Jakie jest twoje ulubione wspomnienie z dzieciństwa?", + "Pamiętasz jakieś sny lub koszmary z dzieciństwa?", + "Czy inne dzieci czasem cię drażniły?", + "Jak myślisz, czy doświadczenia z dzieciństwa wpłynęły na twoje dzisiejsze uczucia?", + ), + ), + ( + r"(.*)\?", + ( + "Dlaczego o to pytasz?", + "Rozważ proszę, czy byłbyś w stanie odpowiedzieć na swoje pytanie.", + "Być może odpowiedź tkwi w tobie?", + "Dlaczego nie powiesz?", + ), + ), + ( + r"Do widzenia", + ( + "Dziękuję, że ze mną porozmawiałeś.", + "Do widzenia.", + "Dziękuję, miłego dnia!", + ), + ), + ( + r"(.*)", + ( + "Opowiedz mi więcej.", + "Zmieńmy trochę temat... Opowiedz mi o swojej rodzinie", + "Czy możesz to rozwinąć?", + "Dlaczego mówisz, że %1?", + "Rozumiem.", + "Bardzo interesujące.", + "%1.", + "Rozumiem, a co ci to mówi?", + "Jak się z tym czujesz?", + "Jak się czujesz, kiedy o tym mówisz?", + ), + ), +) + +eliza_chatbot = Chat(pairs, reflections) + + +def eliza_chat(): + print("Psycholog\n---------") + print("Porozmawiaj z programem, wpisując polskie słowa, używając") + print('dużych oraz małych liter i znaków interpunkcyjnych.') + print('Po zakończeniu wpisz „Do widzenia”') + print("=" * 75) + print("Dzień dobry. Nazywam się Eliza.\nJak się dzisiaj czujesz?") + + eliza_chatbot.converse() + + +def demo(): + eliza_chat() + + +if __name__ == "__main__": demo() \ No newline at end of file diff --git a/modules/AJN.py b/modules/AJN.py index 4ace0dd..202efe6 100644 --- a/modules/AJN.py +++ b/modules/AJN.py @@ -10,41 +10,53 @@ grammars = [] for grammarFile in onlyfiles: grammar = jsgf.parse_grammar_file(mypath + grammarFile) grammars.append(grammar) - -class Ajn: - - - def __init__(self, grammars = None): - self.grammars = grammars - def get_dialog_act(rule): - slots = [] - get_slots(rule.expansion, slots) - return {'act': rule.grammar.name, 'slots': slots} +def get_dialog_act(rule): + slots = [] + get_slots(rule.expansion, slots) + return {'act': rule.grammar.name, 'slots': slots} - def get_slots(expansion, slots): - if expansion.tag != '': - slots.append((expansion.tag, expansion.current_match)) - return +def get_slots(expansion, slots): + if expansion.tag != '': + slots.append((expansion.tag, expansion.current_match)) + return - for child in expansion.children: - get_slots(child, slots) + for child in expansion.children: + get_slots(child, slots) - if not expansion.children and isinstance(expansion, jsgf.NamedRuleRef): - get_slots(expansion.referenced_rule.expansion, slots) - - def nlu(utterance): - matched = None - for grammar in grammars: - matched = grammar.find_matching_rules(utterance) - if matched: - break + if not expansion.children and isinstance(expansion, jsgf.NamedRuleRef): + get_slots(expansion.referenced_rule.expansion, slots) +def nlu(utterance): + matched = None + for grammar in grammars: + matched = grammar.find_matching_rules(utterance) if matched: - return get_dialog_act(matched[0]) - else: - return {'act': 'null', 'slots': []} + break + if matched: + return get_dialog_act(matched[0]) + else: + return {'act': 'null', 'slots': []} + +def preprocess(text): + text = text.lower() + text = text.replace("ą","a") + text = text.replace("ę","e") + text = text.replace("ó","o") + text = text.replace("ł","l") + text = text.replace("ć","c") + text = text.replace("ń","n") + text = text.replace("ś","s") + text = text.replace("ą","a") + text = text.replace("ż","z") + text = text.replace("ź","z") + text = text.replace("ą","a") + + return text -ajn = Ajn() \ No newline at end of file + +def ajn(text): + frame = nlu(preprocess(text)) + return frame diff --git a/modules/DST.py b/modules/DST.py index 42550d5..f97d012 100644 --- a/modules/DST.py +++ b/modules/DST.py @@ -23,13 +23,19 @@ class Dst: if value == None: return key - def reset(self): - for key, value in self.checklist.items(): - value = None; + def reset_if_needed(self,text): + if text == "reset": + for key in self.checklist.keys(): + self.checklist[key] = None + + def save_answer(self, slots): for slot in slots: - #print(slot[0],slot[1]) - self.checklist[slot[0]] = slot[1] + if slot[0] == "numer": + if (len(slot[1].replace(" ",""))) == 9: + self.checklist[slot[0]] = slot[1].replace(" ","") + else: + self.checklist[slot[0]] = slot[1] self.messages.append(slots) \ No newline at end of file diff --git a/modules/NLG.py b/modules/NLG.py index 51b8d8e..b496cd9 100644 --- a/modules/NLG.py +++ b/modules/NLG.py @@ -1,13 +1,46 @@ -def nlg(query,frame): +import random + +unknown = ['Nie rozumiem. Proszę o powtórzenie.', + 'Czy możesz powiedzieć to innymi słowami?', + "Nie wiem co masz na myśli", + "Czy możesz powiedzieć to w inny sposób, proszę?"] + +bye = ["Trzymaj się!", + "Na razie!", + "Do zobaczenia później!", + "Do zobaczenia", + "Pogadamy później!" + ] + + + + +def nlg(query,frame,text): if frame['act'] == "hello": print("Witamy w systemie rezerwacji biletów kinowych. W czym mogę pomóc?") if frame['act'] == "repertuar": print("Aktualnie repertuar zawiera takie filmy jak: \"Batman\" \"Ambulans\" \"Bunkier strachu\" \"Córka\" \"Uncharted\" \"Inni ludzie\" \"Śmierć na Nilu\" \"Skarb Mikołajka\"") - if frame['act'] == 'null': - print('Nie rozumiem. Proszę o powtórzenie') + if frame['act'] == 'null': + if text == 'reset': + print("Resetowanie dialogu.") + if text == "exit": + print('Dziękujemy za skorzystanie z naszych usług!') + elif text != "reset": + print(random.choice(unknown)) + + if frame['act'] == "numer": + if len(text) != 9: + print("Proszę podać poprawny numer telefonu.") + elif query == None: + print("Rezerwacja została dokonana. Potwierdzenie rezerwacji zostanie niebawem przesłane wiadomością SMS. Proszę o przybycie 15 minut przed rozpoczęciem seansu w celu zakupu biletu, w innym przypadku rezerwacja przepada.") + + if frame['act'] == "bye" : + print(random.choice(bye)) + - else: +# if frame['act'] != "hello" and frame['act'] != "null" and : + if frame['act'] not in ['hello','bye','null']: if query == "miejsce": print("Czy miejsca mają być z przodu, z tyłu czy na środku?") if query == "numer": @@ -20,7 +53,7 @@ def nlg(query,frame): print("Ile biletów ma zostać zarezerwowanych?") if query == 'tytul': print("Na jaki film ma zostać dokonana rezerwacja?") - if query == None: - print("Rezerwacja została dokonana. Potwierdzenie rezerwacji zostanie niebawem przesłane wiadomością SMS. Proszę o przybycie 15 minut przed rozpoczęciem seansu w celu zakupu biletu, w innym przypadku rezerwacja przepada.") + +