Compare commits
No commits in common. "3651768e3eb21b217d6806248adf7b0fdea10d44" and "0c096589d7ea87bc08b46f179e97b85a2fc41c35" have entirely different histories.
3651768e3e
...
0c096589d7
8
.gitignore
vendored
8
.gitignore
vendored
@ -57,6 +57,8 @@ docs/_build/
|
||||
|
||||
Pipfile
|
||||
Pipfile.lock
|
||||
|
||||
# output
|
||||
/out
|
||||
decision_tree
|
||||
decision_tree.pdf
|
||||
Source.gv.pdf
|
||||
Source.gv
|
||||
decision_tree.txt
|
||||
|
16
README.MD
16
README.MD
@ -41,14 +41,8 @@
|
||||
|
||||
---
|
||||
|
||||
- [x] **Drzewa decyzyjne: wymagania dot. trzeciego przyrostu**
|
||||
- [x] Należy wykorzystać algorytm ID3 (tj. schemat indukcyjnego uczenia drzewa decyzyjnego oraz procedurę wyboru atrybutu o największym przyroście informacji) lub któreś z jego uogólnień.
|
||||
- [x] Należy przygotować zbiór uczący złożony z co najmniej 200 przykładów.
|
||||
- [x] Decyzja stanowiąca cel uczenia powinna zostać opisana przynajmniej ośmioma atrybutami.
|
||||
- [x] Powinna pojawić się opcja podglądu wyuczonego drzewa (np. w logach lub w pliku z graficzną reprezentacją drzewa).
|
||||
|
||||
---
|
||||
|
||||
- [ ] **Sieci neuronowe: wymagania dot. czwartego przyrostu**
|
||||
- [ ] Należy przygotować zbiór uczący zawierający co najmniej 1000 przykładów dla każdej klasy.
|
||||
- [ ] Agent powinien wykorzystywać wyuczoną sieć w procesie podejmowania decyzji.
|
||||
- [ ] **Drzewa decyzyjne: wymagania dot. trzeciego przyrostu**
|
||||
- [ ] Należy wykorzystać algorytm ID3 (tj. schemat indukcyjnego uczenia drzewa decyzyjnego oraz procedurę wyboru atrybutu o największym przyroście informacji) lub któreś z jego uogólnień.
|
||||
- [ ] Należy przygotować zbiór uczący złożony z co najmniej 200 przykładów.
|
||||
- [ ] Decyzja stanowiąca cel uczenia powinna zostać opisana przynajmniej ośmioma atrybutami.
|
||||
- [ ] Powinna pojawić się opcja podglądu wyuczonego drzewa (np. w logach lub w pliku z graficzną reprezentacją drzewa).
|
||||
|
38
TreeConcept.py
Normal file
38
TreeConcept.py
Normal file
@ -0,0 +1,38 @@
|
||||
from sklearn import tree
|
||||
import pandas as pd #for manipulating the csv data
|
||||
import numpy as np
|
||||
import graphviz
|
||||
import os
|
||||
os.environ["PATH"] += os.pathsep + 'C:/Program Files (x86)/Graphviz/bin/'
|
||||
|
||||
#importing the dataset from the disk
|
||||
train_data_m=np.genfromtxt("dataset/converted_dataset.csv", delimiter=",",skip_header=1);
|
||||
|
||||
# Separate the attributes and labels
|
||||
X_train = [data[:-1] for data in train_data_m]
|
||||
y_train = [data[-1] for data in train_data_m]
|
||||
|
||||
# Create the decision tree classifier using the ID3 algorithm
|
||||
clf = tree.DecisionTreeClassifier(criterion='entropy')
|
||||
#clf = tree.DecisionTreeClassifier(criterion='gini')
|
||||
|
||||
# Train the decision tree on the training data
|
||||
clf.fit(X_train, y_train)
|
||||
|
||||
# Visualize the trained decision tree
|
||||
tree_text = tree.export_text(clf,feature_names=['Battery Charge', 'Fullness', 'Ready orders', 'Waiting tables','Availability', 'Cleanliness', 'Error'])
|
||||
with open('decision_tree.txt', 'w') as f:
|
||||
f.write(tree_text) # Save the visualization as a text file
|
||||
dot_data = tree.export_graphviz(clf, out_file=None, feature_names=['Battery Charge', 'Fullness', 'Ready orders', 'Waiting tables','Availability', 'Cleanliness', 'Error'], class_names=['NO', 'YES'], filled=True,rounded=True)
|
||||
graph = graphviz.Source(dot_data)
|
||||
graph.render("decision_tree") # Save the visualization as a PDF file
|
||||
|
||||
# Test the decision tree with a new example
|
||||
#Battery Charge,Fullness,Ready orders,Waiting tables,Availability,Cleanliness,Error
|
||||
new_example = [2, 0, 1, 1, 1 ,2, 0]
|
||||
predicted_label = clf.predict([new_example])
|
||||
if predicted_label[0]>0:
|
||||
result="YES"
|
||||
else:
|
||||
result="NO"
|
||||
print("Predicted Label:", result)
|
18
agent.py
18
agent.py
@ -7,29 +7,31 @@ from src.obj.Table import Table
|
||||
from src.UserController import UserController
|
||||
from src.StateController import StateController
|
||||
|
||||
SCREEN_SIZE = [800, 800]
|
||||
SCREEN_SIZE = (800, 800)
|
||||
SQUARE_SIZE = 40
|
||||
|
||||
waiter = Waiter([0, 0], 0, SQUARE_SIZE, SCREEN_SIZE)
|
||||
kitchen = Kitchen([0, 0], 0, SQUARE_SIZE, SCREEN_SIZE)
|
||||
objects = []
|
||||
objects = [
|
||||
Kitchen([0, 0], 0, SQUARE_SIZE, SCREEN_SIZE)
|
||||
]
|
||||
|
||||
for i in range(150):
|
||||
|
||||
pos = [0, 0]
|
||||
|
||||
while any([o.compare_pos(pos) for o in objects]) or pos == [0, 0]:
|
||||
pos = [random.randint(1, SCREEN_SIZE[0]/SQUARE_SIZE - 1),
|
||||
random.randint(1, SCREEN_SIZE[0]/SQUARE_SIZE - 1)]
|
||||
while any([o.compare_pos(pos) for o in objects]):
|
||||
pos = [random.randint(1, SCREEN_SIZE[0]/SQUARE_SIZE),
|
||||
random.randint(1, SCREEN_SIZE[0]/SQUARE_SIZE)]
|
||||
|
||||
if (random.randint(0, 1)):
|
||||
objects.append(Block(pos, 0, SQUARE_SIZE, SCREEN_SIZE))
|
||||
else:
|
||||
objects.append(Table(pos, 0, SQUARE_SIZE, SCREEN_SIZE))
|
||||
objects.append(Table(pos, 0, SQUARE_SIZE,
|
||||
SCREEN_SIZE, random.randint(0, 3)))
|
||||
|
||||
user = UserController(waiter)
|
||||
state = StateController(waiter)
|
||||
engine = Engine(SCREEN_SIZE, SQUARE_SIZE, kitchen, user, state)
|
||||
engine = Engine(SCREEN_SIZE, SQUARE_SIZE, user, state)
|
||||
|
||||
for o in objects:
|
||||
engine.subscribe(o)
|
||||
|
201
dataset/Dataset.csv
Normal file
201
dataset/Dataset.csv
Normal file
@ -0,0 +1,201 @@
|
||||
Battery Charge,Fullness,Ready orders,Waiting tables,Availability,Cleanliness,Error,To go
|
||||
high,full,none,none,available,low,yes,no
|
||||
low,full,none,none,unavailable,medium,yes,no
|
||||
high,full,none,none,unavailable,medium,no,no
|
||||
medium,empty,none,none,unavailable,low,no,no
|
||||
high,full,none,none,available,medium,no,no
|
||||
low,full,none,available,unavailable,medium,yes,no
|
||||
medium,empty,none,available,unavailable,high,yes,no
|
||||
medium,full,none,available,available,low,yes,no
|
||||
medium,full,available,none,unavailable,low,yes,no
|
||||
high,empty,none,none,unavailable,medium,yes,no
|
||||
medium,empty,none,available,unavailable,medium,yes,no
|
||||
low,empty,available,none,available,high,no,no
|
||||
high,full,available,none,available,low,yes,no
|
||||
medium,full,none,available,available,low,no,no
|
||||
medium,full,none,available,available,medium,no,yes
|
||||
empty,full,none,none,unavailable,high,yes,no
|
||||
low,full,none,none,unavailable,medium,no,no
|
||||
low,full,available,none,unavailable,low,no,no
|
||||
medium,empty,none,available,unavailable,medium,no,no
|
||||
low,empty,available,available,unavailable,medium,no,no
|
||||
medium,empty,available,available,unavailable,medium,yes,no
|
||||
low,empty,none,none,unavailable,high,no,no
|
||||
medium,full,available,available,unavailable,medium,yes,no
|
||||
high,empty,available,none,available,medium,no,yes
|
||||
empty,empty,available,available,unavailable,low,yes,no
|
||||
high,empty,none,none,unavailable,high,yes,no
|
||||
medium,empty,available,available,available,medium,no,yes
|
||||
medium,full,available,available,available,low,no,no
|
||||
empty,full,none,available,available,high,no,no
|
||||
empty,empty,none,none,unavailable,low,no,no
|
||||
medium,full,none,none,unavailable,medium,no,no
|
||||
medium,empty,available,available,unavailable,high,yes,no
|
||||
high,full,available,none,available,medium,yes,no
|
||||
medium,empty,none,available,unavailable,low,yes,no
|
||||
low,empty,none,none,available,low,no,no
|
||||
high,full,available,available,available,low,yes,no
|
||||
high,full,available,available,unavailable,high,yes,no
|
||||
low,full,available,available,unavailable,high,yes,no
|
||||
low,full,none,none,unavailable,low,yes,no
|
||||
medium,full,none,none,unavailable,medium,yes,no
|
||||
high,full,none,available,available,medium,yes,no
|
||||
low,empty,none,none,unavailable,low,no,no
|
||||
high,empty,available,none,unavailable,low,yes,no
|
||||
medium,full,none,available,available,high,no,yes
|
||||
low,empty,available,available,available,high,yes,no
|
||||
low,full,available,none,unavailable,high,yes,no
|
||||
medium,full,available,none,unavailable,low,no,no
|
||||
medium,full,available,available,unavailable,high,no,no
|
||||
medium,full,none,available,unavailable,low,yes,no
|
||||
medium,empty,available,none,unavailable,low,yes,no
|
||||
medium,empty,none,none,available,high,no,no
|
||||
empty,full,none,none,available,low,no,no
|
||||
low,full,available,available,available,medium,yes,no
|
||||
low,full,available,none,unavailable,high,no,no
|
||||
high,full,available,none,available,medium,no,no
|
||||
low,full,none,available,available,medium,no,no
|
||||
empty,empty,none,available,available,high,no,no
|
||||
low,full,none,available,unavailable,low,no,no
|
||||
high,full,none,none,unavailable,high,no,no
|
||||
medium,full,none,none,available,high,yes,no
|
||||
low,empty,none,available,available,medium,no,no
|
||||
empty,empty,none,available,unavailable,low,no,no
|
||||
empty,full,available,none,available,low,yes,no
|
||||
empty,empty,available,available,available,medium,no,no
|
||||
empty,empty,available,none,unavailable,medium,no,no
|
||||
empty,empty,none,none,unavailable,high,no,no
|
||||
medium,empty,available,none,unavailable,high,no,no
|
||||
empty,empty,available,none,available,medium,yes,no
|
||||
empty,empty,none,none,unavailable,high,yes,no
|
||||
high,full,available,available,unavailable,low,no,no
|
||||
high,empty,available,available,available,high,yes,no
|
||||
high,empty,available,none,available,low,no,no
|
||||
low,empty,none,available,unavailable,medium,no,no
|
||||
medium,full,none,available,unavailable,low,no,no
|
||||
medium,empty,none,available,available,high,yes,no
|
||||
medium,empty,available,available,available,high,no,yes
|
||||
high,empty,none,available,unavailable,low,yes,no
|
||||
low,full,available,available,available,high,no,no
|
||||
medium,empty,none,available,available,high,no,no
|
||||
medium,empty,available,none,available,high,no,yes
|
||||
empty,full,available,available,unavailable,high,no,no
|
||||
low,empty,none,available,available,low,no,no
|
||||
high,full,none,available,available,low,yes,no
|
||||
high,empty,none,none,available,medium,yes,no
|
||||
empty,empty,available,none,unavailable,low,no,no
|
||||
high,full,none,available,unavailable,low,yes,no
|
||||
empty,full,none,available,unavailable,high,no,no
|
||||
empty,full,available,none,available,low,no,no
|
||||
medium,full,none,none,available,high,no,no
|
||||
medium,full,available,available,unavailable,low,yes,no
|
||||
empty,full,available,available,unavailable,low,yes,no
|
||||
low,empty,none,none,unavailable,medium,no,no
|
||||
low,full,none,none,unavailable,low,no,no
|
||||
low,full,available,available,unavailable,low,yes,no
|
||||
low,empty,none,available,available,low,yes,no
|
||||
empty,full,available,none,unavailable,high,no,no
|
||||
low,full,available,none,available,high,no,no
|
||||
high,full,available,available,available,medium,yes,no
|
||||
empty,full,none,available,available,medium,yes,no
|
||||
low,full,none,none,available,medium,no,no
|
||||
empty,full,available,available,available,low,no,no
|
||||
medium,full,available,none,unavailable,medium,yes,no
|
||||
empty,empty,none,none,available,medium,no,no
|
||||
high,full,none,available,unavailable,low,no,no
|
||||
low,empty,available,available,available,high,no,no
|
||||
low,empty,none,available,available,high,yes,no
|
||||
high,full,none,available,available,medium,no,yes
|
||||
empty,full,available,none,available,medium,yes,no
|
||||
high,full,none,none,available,low,no,no
|
||||
low,empty,available,available,unavailable,high,no,no
|
||||
low,full,available,none,available,medium,yes,no
|
||||
high,empty,none,none,unavailable,low,no,no
|
||||
low,full,none,none,unavailable,high,yes,no
|
||||
high,empty,none,available,available,low,yes,no
|
||||
empty,full,available,available,unavailable,low,no,no
|
||||
low,empty,available,available,unavailable,low,no,no
|
||||
low,full,available,none,unavailable,low,yes,no
|
||||
empty,empty,available,available,unavailable,high,no,no
|
||||
medium,full,available,none,available,medium,yes,no
|
||||
high,full,available,none,available,high,no,no
|
||||
low,full,none,available,available,medium,yes,no
|
||||
low,empty,none,available,unavailable,medium,yes,no
|
||||
high,full,available,available,unavailable,medium,yes,no
|
||||
high,full,none,none,unavailable,medium,yes,no
|
||||
low,full,available,available,available,low,yes,no
|
||||
low,full,available,available,unavailable,high,no,no
|
||||
empty,full,none,none,available,medium,no,no
|
||||
empty,empty,available,none,available,low,yes,no
|
||||
high,full,available,none,unavailable,high,no,no
|
||||
high,full,none,available,unavailable,high,no,no
|
||||
low,empty,available,available,unavailable,medium,yes,no
|
||||
high,empty,available,available,available,low,yes,no
|
||||
empty,full,none,none,unavailable,low,no,no
|
||||
high,full,none,available,unavailable,medium,yes,no
|
||||
high,empty,available,none,unavailable,medium,no,no
|
||||
empty,empty,available,none,available,high,yes,no
|
||||
high,empty,available,none,unavailable,medium,yes,no
|
||||
empty,empty,none,none,unavailable,medium,no,no
|
||||
high,empty,none,available,available,high,no,no
|
||||
medium,empty,none,none,unavailable,low,yes,no
|
||||
medium,full,available,none,unavailable,high,no,no
|
||||
high,full,none,none,unavailable,low,no,no
|
||||
high,empty,none,none,unavailable,medium,no,no
|
||||
medium,full,available,none,available,low,no,no
|
||||
high,empty,none,none,available,high,yes,no
|
||||
empty,full,available,available,available,high,no,no
|
||||
medium,full,available,available,unavailable,low,no,no
|
||||
empty,full,available,none,available,medium,no,no
|
||||
empty,full,available,available,unavailable,medium,yes,no
|
||||
empty,empty,available,none,available,high,no,no
|
||||
low,empty,none,none,available,high,yes,no
|
||||
empty,full,none,available,unavailable,medium,yes,no
|
||||
medium,full,none,available,unavailable,medium,yes,no
|
||||
medium,full,available,none,available,low,yes,no
|
||||
medium,full,available,none,unavailable,high,yes,no
|
||||
medium,full,available,available,available,high,no,yes
|
||||
medium,full,none,none,available,low,no,no
|
||||
high,full,none,available,available,high,no,yes
|
||||
low,empty,available,available,unavailable,low,yes,no
|
||||
low,full,none,available,unavailable,high,yes,no
|
||||
medium,full,available,available,available,high,yes,no
|
||||
high,full,available,available,available,low,no,no
|
||||
medium,full,none,none,unavailable,high,yes,no
|
||||
medium,full,none,available,unavailable,high,no,no
|
||||
high,empty,none,available,unavailable,high,yes,no
|
||||
empty,empty,none,available,available,medium,no,no
|
||||
empty,empty,available,none,unavailable,high,no,no
|
||||
high,empty,available,available,unavailable,high,yes,no
|
||||
medium,empty,available,available,unavailable,low,yes,no
|
||||
medium,full,none,none,unavailable,low,no,no
|
||||
high,empty,none,none,available,low,no,no
|
||||
high,full,available,none,unavailable,medium,no,no
|
||||
high,full,available,none,unavailable,low,yes,no
|
||||
empty,empty,available,available,available,low,yes,no
|
||||
high,empty,none,none,unavailable,low,yes,no
|
||||
medium,empty,none,none,available,low,no,no
|
||||
low,full,none,available,unavailable,medium,no,no
|
||||
low,full,none,available,available,high,yes,no
|
||||
high,full,none,available,unavailable,high,yes,no
|
||||
medium,full,none,available,available,medium,yes,no
|
||||
empty,empty,none,available,unavailable,high,yes,no
|
||||
medium,empty,available,none,unavailable,medium,yes,no
|
||||
empty,empty,none,available,unavailable,low,yes,no
|
||||
high,empty,none,available,unavailable,medium,no,no
|
||||
medium,empty,available,none,available,low,yes,no
|
||||
medium,full,available,available,available,medium,no,yes
|
||||
high,full,available,none,unavailable,medium,yes,no
|
||||
high,full,available,available,unavailable,medium,no,no
|
||||
low,full,available,none,available,medium,no,no
|
||||
medium,empty,available,none,unavailable,high,yes,no
|
||||
medium,empty,available,none,available,medium,yes,no
|
||||
high,empty,none,none,available,high,no,no
|
||||
empty,full,available,none,unavailable,high,yes,no
|
||||
low,empty,available,none,unavailable,low,yes,no
|
||||
empty,full,available,available,available,low,yes,no
|
||||
medium,empty,available,available,unavailable,medium,no,no
|
||||
medium,empty,none,none,unavailable,high,no,no
|
||||
medium,full,available,available,unavailable,medium,no,no
|
||||
empty,full,available,available,available,medium,no,no
|
||||
low,empty,available,none,available,low,no,no
|
|
200
dataset/converted_dataset.csv
Normal file
200
dataset/converted_dataset.csv
Normal file
@ -0,0 +1,200 @@
|
||||
3,1,0,0,1,0,1,0
|
||||
1,1,0,0,0,1,1,0
|
||||
3,1,0,0,0,1,0,0
|
||||
2,0,0,0,0,0,0,0
|
||||
3,1,0,0,1,1,0,0
|
||||
1,1,0,1,0,1,1,0
|
||||
2,0,0,1,0,2,1,0
|
||||
2,1,0,1,1,0,1,0
|
||||
2,1,1,0,0,0,1,0
|
||||
3,0,0,0,0,1,1,0
|
||||
2,0,0,1,0,1,1,0
|
||||
1,0,1,0,1,2,0,0
|
||||
3,1,1,0,1,0,1,0
|
||||
2,1,0,1,1,0,0,0
|
||||
2,1,0,1,1,1,0,1
|
||||
0,1,0,0,0,2,1,0
|
||||
1,1,0,0,0,1,0,0
|
||||
1,1,1,0,0,0,0,0
|
||||
2,0,0,1,0,1,0,0
|
||||
1,0,1,1,0,1,0,0
|
||||
2,0,1,1,0,1,1,0
|
||||
1,0,0,0,0,2,0,0
|
||||
2,1,1,1,0,1,1,0
|
||||
3,0,1,0,1,1,0,1
|
||||
0,0,1,1,0,0,1,0
|
||||
3,0,0,0,0,2,1,0
|
||||
2,0,1,1,1,1,0,1
|
||||
2,1,1,1,1,0,0,0
|
||||
0,1,0,1,1,2,0,0
|
||||
0,0,0,0,0,0,0,0
|
||||
2,1,0,0,0,1,0,0
|
||||
2,0,1,1,0,2,1,0
|
||||
3,1,1,0,1,1,1,0
|
||||
2,0,0,1,0,0,1,0
|
||||
1,0,0,0,1,0,0,0
|
||||
3,1,1,1,1,0,1,0
|
||||
3,1,1,1,0,2,1,0
|
||||
1,1,1,1,0,2,1,0
|
||||
1,1,0,0,0,0,1,0
|
||||
2,1,0,0,0,1,1,0
|
||||
3,1,0,1,1,1,1,0
|
||||
1,0,0,0,0,0,0,0
|
||||
3,0,1,0,0,0,1,0
|
||||
2,1,0,1,1,2,0,1
|
||||
1,0,1,1,1,2,1,0
|
||||
1,1,1,0,0,2,1,0
|
||||
2,1,1,0,0,0,0,0
|
||||
2,1,1,1,0,2,0,0
|
||||
2,1,0,1,0,0,1,0
|
||||
2,0,1,0,0,0,1,0
|
||||
2,0,0,0,1,2,0,0
|
||||
0,1,0,0,1,0,0,0
|
||||
1,1,1,1,1,1,1,0
|
||||
1,1,1,0,0,2,0,0
|
||||
3,1,1,0,1,1,0,0
|
||||
1,1,0,1,1,1,0,0
|
||||
0,0,0,1,1,2,0,0
|
||||
1,1,0,1,0,0,0,0
|
||||
3,1,0,0,0,2,0,0
|
||||
2,1,0,0,1,2,1,0
|
||||
1,0,0,1,1,1,0,0
|
||||
0,0,0,1,0,0,0,0
|
||||
0,1,1,0,1,0,1,0
|
||||
0,0,1,1,1,1,0,0
|
||||
0,0,1,0,0,1,0,0
|
||||
0,0,0,0,0,2,0,0
|
||||
2,0,1,0,0,2,0,0
|
||||
0,0,1,0,1,1,1,0
|
||||
0,0,0,0,0,2,1,0
|
||||
3,1,1,1,0,0,0,0
|
||||
3,0,1,1,1,2,1,0
|
||||
3,0,1,0,1,0,0,0
|
||||
1,0,0,1,0,1,0,0
|
||||
2,1,0,1,0,0,0,0
|
||||
2,0,0,1,1,2,1,0
|
||||
2,0,1,1,1,2,0,1
|
||||
3,0,0,1,0,0,1,0
|
||||
1,1,1,1,1,2,0,0
|
||||
2,0,0,1,1,2,0,0
|
||||
2,0,1,0,1,2,0,1
|
||||
0,1,1,1,0,2,0,0
|
||||
1,0,0,1,1,0,0,0
|
||||
3,1,0,1,1,0,1,0
|
||||
3,0,0,0,1,1,1,0
|
||||
0,0,1,0,0,0,0,0
|
||||
3,1,0,1,0,0,1,0
|
||||
0,1,0,1,0,2,0,0
|
||||
0,1,1,0,1,0,0,0
|
||||
2,1,0,0,1,2,0,0
|
||||
2,1,1,1,0,0,1,0
|
||||
0,1,1,1,0,0,1,0
|
||||
1,0,0,0,0,1,0,0
|
||||
1,1,0,0,0,0,0,0
|
||||
1,1,1,1,0,0,1,0
|
||||
1,0,0,1,1,0,1,0
|
||||
0,1,1,0,0,2,0,0
|
||||
1,1,1,0,1,2,0,0
|
||||
3,1,1,1,1,1,1,0
|
||||
0,1,0,1,1,1,1,0
|
||||
1,1,0,0,1,1,0,0
|
||||
0,1,1,1,1,0,0,0
|
||||
2,1,1,0,0,1,1,0
|
||||
0,0,0,0,1,1,0,0
|
||||
3,1,0,1,0,0,0,0
|
||||
1,0,1,1,1,2,0,0
|
||||
1,0,0,1,1,2,1,0
|
||||
3,1,0,1,1,1,0,1
|
||||
0,1,1,0,1,1,1,0
|
||||
3,1,0,0,1,0,0,0
|
||||
1,0,1,1,0,2,0,0
|
||||
1,1,1,0,1,1,1,0
|
||||
3,0,0,0,0,0,0,0
|
||||
1,1,0,0,0,2,1,0
|
||||
3,0,0,1,1,0,1,0
|
||||
0,1,1,1,0,0,0,0
|
||||
1,0,1,1,0,0,0,0
|
||||
1,1,1,0,0,0,1,0
|
||||
0,0,1,1,0,2,0,0
|
||||
2,1,1,0,1,1,1,0
|
||||
3,1,1,0,1,2,0,0
|
||||
1,1,0,1,1,1,1,0
|
||||
1,0,0,1,0,1,1,0
|
||||
3,1,1,1,0,1,1,0
|
||||
3,1,0,0,0,1,1,0
|
||||
1,1,1,1,1,0,1,0
|
||||
1,1,1,1,0,2,0,0
|
||||
0,1,0,0,1,1,0,0
|
||||
0,0,1,0,1,0,1,0
|
||||
3,1,1,0,0,2,0,0
|
||||
3,1,0,1,0,2,0,0
|
||||
1,0,1,1,0,1,1,0
|
||||
3,0,1,1,1,0,1,0
|
||||
0,1,0,0,0,0,0,0
|
||||
3,1,0,1,0,1,1,0
|
||||
3,0,1,0,0,1,0,0
|
||||
0,0,1,0,1,2,1,0
|
||||
3,0,1,0,0,1,1,0
|
||||
0,0,0,0,0,1,0,0
|
||||
3,0,0,1,1,2,0,0
|
||||
2,0,0,0,0,0,1,0
|
||||
2,1,1,0,0,2,0,0
|
||||
3,1,0,0,0,0,0,0
|
||||
3,0,0,0,0,1,0,0
|
||||
2,1,1,0,1,0,0,0
|
||||
3,0,0,0,1,2,1,0
|
||||
0,1,1,1,1,2,0,0
|
||||
2,1,1,1,0,0,0,0
|
||||
0,1,1,0,1,1,0,0
|
||||
0,1,1,1,0,1,1,0
|
||||
0,0,1,0,1,2,0,0
|
||||
1,0,0,0,1,2,1,0
|
||||
0,1,0,1,0,1,1,0
|
||||
2,1,0,1,0,1,1,0
|
||||
2,1,1,0,1,0,1,0
|
||||
2,1,1,0,0,2,1,0
|
||||
2,1,1,1,1,2,0,1
|
||||
2,1,0,0,1,0,0,0
|
||||
3,1,0,1,1,2,0,1
|
||||
1,0,1,1,0,0,1,0
|
||||
1,1,0,1,0,2,1,0
|
||||
2,1,1,1,1,2,1,0
|
||||
3,1,1,1,1,0,0,0
|
||||
2,1,0,0,0,2,1,0
|
||||
2,1,0,1,0,2,0,0
|
||||
3,0,0,1,0,2,1,0
|
||||
0,0,0,1,1,1,0,0
|
||||
0,0,1,0,0,2,0,0
|
||||
3,0,1,1,0,2,1,0
|
||||
2,0,1,1,0,0,1,0
|
||||
2,1,0,0,0,0,0,0
|
||||
3,0,0,0,1,0,0,0
|
||||
3,1,1,0,0,1,0,0
|
||||
3,1,1,0,0,0,1,0
|
||||
0,0,1,1,1,0,1,0
|
||||
3,0,0,0,0,0,1,0
|
||||
2,0,0,0,1,0,0,0
|
||||
1,1,0,1,0,1,0,0
|
||||
1,1,0,1,1,2,1,0
|
||||
3,1,0,1,0,2,1,0
|
||||
2,1,0,1,1,1,1,0
|
||||
0,0,0,1,0,2,1,0
|
||||
2,0,1,0,0,1,1,0
|
||||
0,0,0,1,0,0,1,0
|
||||
3,0,0,1,0,1,0,0
|
||||
2,0,1,0,1,0,1,0
|
||||
2,1,1,1,1,1,0,1
|
||||
3,1,1,0,0,1,1,0
|
||||
3,1,1,1,0,1,0,0
|
||||
1,1,1,0,1,1,0,0
|
||||
2,0,1,0,0,2,1,0
|
||||
2,0,1,0,1,1,1,0
|
||||
3,0,0,0,1,2,0,0
|
||||
0,1,1,0,0,2,1,0
|
||||
1,0,1,0,0,0,1,0
|
||||
0,1,1,1,1,0,1,0
|
||||
2,0,1,1,0,1,0,0
|
||||
2,0,0,0,0,2,0,0
|
||||
2,1,1,1,0,1,0,0
|
||||
0,1,1,1,1,1,0,0
|
||||
1,0,1,0,1,0,0,0
|
|
@ -1,17 +1,15 @@
|
||||
import csv
|
||||
|
||||
|
||||
def convertDataset():
|
||||
def convert_dataset(input_file, output_file):
|
||||
attributes = {
|
||||
1: ["low", "high"],
|
||||
2: ["far", "close"],
|
||||
3: ['bad', 'good', 'undefined'],
|
||||
4: ["no", "yes"],
|
||||
5: ["no", "yes"],
|
||||
6: ["no", "yes"],
|
||||
7: ["empty", "new order", "waiting for dish", "have a dish"],
|
||||
8: ["no", "yes"],
|
||||
9: ["high priority", "low priority", "return to kitchen"]
|
||||
1: ["empty", "low", "medium", "high"],
|
||||
2: ["empty", "full"],
|
||||
3: ["none", "available"],
|
||||
4: ["none", "available"],
|
||||
5: ["unavailable", "available"],
|
||||
6: ["low", "medium", "high"],
|
||||
7: ["no", "yes"],
|
||||
8: ["no", "yes"]
|
||||
}
|
||||
|
||||
# Create a mapping dictionary for attribute values
|
||||
@ -22,11 +20,10 @@ def convertDataset():
|
||||
converted_dataset = []
|
||||
|
||||
# Read the input CSV file
|
||||
with open("out/rawDataset.csv", "r") as csvfile:
|
||||
with open(input_file, "r") as csvfile:
|
||||
reader = csv.reader(csvfile)
|
||||
|
||||
header = next(reader) # Skip the header row
|
||||
converted_dataset.append(header)
|
||||
|
||||
# Convert the data rows
|
||||
for row in reader:
|
||||
@ -43,9 +40,15 @@ def convertDataset():
|
||||
converted_dataset.append(converted_row)
|
||||
|
||||
# Write the converted dataset to a new CSV file
|
||||
with open("out/dataset.csv", "w", newline="") as csvfile:
|
||||
with open(output_file, "w", newline="") as csvfile:
|
||||
writer = csv.writer(csvfile)
|
||||
|
||||
# Write the header row
|
||||
#writer.writerow(header)
|
||||
|
||||
# Write the converted data rows
|
||||
for row in converted_dataset:
|
||||
writer.writerow(row)
|
||||
|
||||
# Example usage:
|
||||
convert_dataset("dataset/Dataset.csv", "dataset/converted_dataset.csv")
|
57
dataset/datasetGenerator.py
Normal file
57
dataset/datasetGenerator.py
Normal file
@ -0,0 +1,57 @@
|
||||
import random
|
||||
import csv
|
||||
|
||||
attributes = {
|
||||
1: ["empty", "low", "medium", "high"],
|
||||
2: ["empty", "full"],
|
||||
3: ["none", "available"],
|
||||
4: ["none", "available"],
|
||||
5: ["unavailable", "available"],
|
||||
6: ["low", "medium", "high"],
|
||||
7: ["no", "yes"],
|
||||
8: ["no", "yes"]
|
||||
}
|
||||
|
||||
dataset = []
|
||||
while len(dataset) < 200:
|
||||
data = {}
|
||||
|
||||
# Generate random values for attributes 1-7
|
||||
for attr in range(1, 8):
|
||||
data[attr] = random.choice(attributes[attr])
|
||||
|
||||
# Apply the rules to determine the value of attribute 8
|
||||
if data[1] in ["empty", "low"]:
|
||||
data[8] = "no"
|
||||
elif data[2] == "full" and data[4] == "none":
|
||||
data[8] = "no"
|
||||
elif data[2] == "empty" and data[3] == "none":
|
||||
data[8] = "no"
|
||||
elif data[3] == "none" and data[4] == "none":
|
||||
data[8] = "no"
|
||||
elif data[5] == "unavailable":
|
||||
data[8] = "no"
|
||||
elif data[6] == "low":
|
||||
data[8] = "no"
|
||||
elif data[7] == "yes":
|
||||
data[8] = "no"
|
||||
else:
|
||||
data[8] = "yes"
|
||||
|
||||
# Check if the generated data already exists in the dataset
|
||||
if data not in dataset:
|
||||
dataset.append(data)
|
||||
|
||||
# Print the generated dataset
|
||||
for data in dataset:
|
||||
print(data)
|
||||
with open("dataset/Dataset.csv", "w", newline="") as csvfile:
|
||||
writer = csv.writer(csvfile)
|
||||
|
||||
# Write the header row
|
||||
writer.writerow(["Battery Charge", "Fullness", "Ready orders", "Waiting tables","Availability", "Cleanliness", "Error", "To go"])
|
||||
|
||||
# Write the data rows
|
||||
for data in dataset:
|
||||
row = [data[attr] for attr in range(1, 9)]
|
||||
writer.writerow(row)
|
@ -1,5 +1,2 @@
|
||||
-i https://pypi.org/simple
|
||||
pygame==2.3.0
|
||||
pandas
|
||||
scikit-learn
|
||||
graphviz
|
114
src/Engine.py
114
src/Engine.py
@ -1,30 +1,21 @@
|
||||
import time
|
||||
import pygame
|
||||
from .obj.Goal import Goal
|
||||
from .obj.Object import Object
|
||||
from .obj.Waiter import Waiter
|
||||
from .obj.Kitchen import Kitchen
|
||||
from .UserController import UserController
|
||||
from .StateController import StateController
|
||||
from .decisionTree.TreeConcept import TreeEngine
|
||||
from queue import PriorityQueue
|
||||
|
||||
|
||||
class Engine:
|
||||
|
||||
def __init__(self, screen_size, square_size, kitchen: Kitchen, user: UserController, state: StateController):
|
||||
def __init__(self, screen_size, square_size, user: UserController, state: StateController):
|
||||
pygame.display.set_caption('Waiter Agent')
|
||||
|
||||
self.action_clock = 0
|
||||
self.tree = TreeEngine()
|
||||
|
||||
self.kitchen: Kitchen = kitchen
|
||||
self.user: Waiter = user
|
||||
self.state: StateController = state
|
||||
self.screen_size: list[int] = screen_size
|
||||
self.user = user
|
||||
self.state = state
|
||||
self.screen_size = screen_size
|
||||
self.screen = pygame.display.set_mode(self.screen_size)
|
||||
|
||||
self.square_size: int = square_size
|
||||
self.square_size = square_size
|
||||
self.num_squares = self.screen_size[0] // self.square_size
|
||||
self.squares = self.__init_squares_field__(
|
||||
self.num_squares, self.square_size)
|
||||
@ -32,7 +23,7 @@ class Engine:
|
||||
self.objects: list[Object] = []
|
||||
self.goals: list = []
|
||||
|
||||
self.runnin: bool = False
|
||||
self.runnin = False
|
||||
|
||||
def __init_squares_field__(self, num_squares, square_size):
|
||||
squares = []
|
||||
@ -65,36 +56,15 @@ class Engine:
|
||||
if self.goals:
|
||||
self.state.graphsearch(self)
|
||||
self.user.handler(self)
|
||||
self.predict()
|
||||
else:
|
||||
# went path
|
||||
|
||||
state = self.user.obj.changeState(self.state.path.pop())
|
||||
self.clock_increment(state.cost)
|
||||
|
||||
print("Action:\t{0}\tCost:\t{1}\tCost so far: {2}\tBattery: {3}".format(
|
||||
print("Action:\t{0}\tCost:\t{1}\tCost so far: {2}".format(
|
||||
state.agent_role,
|
||||
state.cost,
|
||||
state.cost_so_far,
|
||||
self.user.obj.battery)
|
||||
state.cost_so_far)
|
||||
)
|
||||
|
||||
# waiter interaction
|
||||
|
||||
for o in self.objects:
|
||||
if self.user.obj.chechNeighbor(o):
|
||||
o.updateState(self.action_clock)
|
||||
if o.compare_pos(self.user.obj.position):
|
||||
o.action(self.user.obj, self.action_clock)
|
||||
|
||||
if self.kitchen.compare_pos(self.user.obj.position):
|
||||
self.kitchen.action(self.user.obj, self.action_clock)
|
||||
|
||||
time.sleep(0.5)
|
||||
|
||||
def clock_increment(self, action_time):
|
||||
self.action_clock += action_time
|
||||
|
||||
def redraw(self):
|
||||
self.screen.fill((255, 255, 255))
|
||||
|
||||
@ -105,7 +75,6 @@ class Engine:
|
||||
for o in self.objects:
|
||||
o.blit(self.screen)
|
||||
|
||||
self.kitchen.blit(self.screen)
|
||||
self.user.obj.blit(self.screen)
|
||||
|
||||
for f in self.state.fringe.queue:
|
||||
@ -114,72 +83,7 @@ class Engine:
|
||||
for s in self.state.path:
|
||||
s.blit(self.screen)
|
||||
|
||||
if self.goals:
|
||||
self.goals[-1].blit(self.screen)
|
||||
|
||||
pygame.display.flip()
|
||||
|
||||
def appendGoalPosition(self, position):
|
||||
self.goals.append(Goal(position, self.square_size, self.screen_size))
|
||||
|
||||
def predict(self):
|
||||
|
||||
goal_queue = PriorityQueue()
|
||||
|
||||
for o in self.objects:
|
||||
|
||||
condition = o.agent_role in [
|
||||
"table",
|
||||
"order",
|
||||
"wait",
|
||||
"done"
|
||||
]
|
||||
|
||||
if not condition or o.compare_pos(self.user.obj.position):
|
||||
continue
|
||||
|
||||
medium_dist = (self.screen_size[0] // self.square_size) // 2
|
||||
|
||||
dataset = [
|
||||
# battery
|
||||
self.user.obj.battery_status(),
|
||||
# high | low |
|
||||
|
||||
# distance between kitchen and object
|
||||
0 if o.distance_to(self.kitchen.position) > medium_dist else 1,
|
||||
# far | close |
|
||||
|
||||
# mood
|
||||
o.get_mood(self.action_clock),
|
||||
# undefined | good | bad |
|
||||
|
||||
# basket is empty
|
||||
1 if self.user.obj.basket_is_empty() else 0,
|
||||
# yes | no |
|
||||
|
||||
# dish is ready
|
||||
1 if o.dish_is_ready(self.action_clock) else 0,
|
||||
# yes | no |
|
||||
|
||||
# dish in basket
|
||||
1 if self.user.obj.dish_in_basket(o) else 0,
|
||||
# yes | no |
|
||||
|
||||
# status
|
||||
o.get_state_number(),
|
||||
# empty | new order | waiting for dish | have a dish |
|
||||
|
||||
# is actual
|
||||
1 if o.isActual() else 0,
|
||||
# yes | no |
|
||||
]
|
||||
|
||||
p = self.tree.make_predict(dataset)
|
||||
goal_queue.put((p, o.position))
|
||||
|
||||
if goal_queue.queue:
|
||||
priority, goal = goal_queue.queue[0]
|
||||
if priority == 2:
|
||||
self.appendGoalPosition(self.kitchen.position)
|
||||
else:
|
||||
self.appendGoalPosition(goal)
|
||||
self.goals.append(position)
|
||||
|
@ -15,11 +15,10 @@ class StateController:
|
||||
self.explored.clear()
|
||||
self.fringe = PriorityQueue()
|
||||
|
||||
def build_path(self, goal_state, engine):
|
||||
def build_path(self, goal_state):
|
||||
total_cost = goal_state.cost
|
||||
self.path.append(goal_state)
|
||||
engine.goals.pop()
|
||||
while self.path[-1].parent.agent_role not in ["blank", "waiter"]:
|
||||
while self.path[-1].parent.agent_role != "blank":
|
||||
self.path.append(self.path[-1].parent)
|
||||
total_cost += self.path[-1].cost
|
||||
|
||||
@ -29,7 +28,7 @@ class StateController:
|
||||
def graphsearch(self, engine): # A*
|
||||
print("Search path")
|
||||
|
||||
self.goal = list(engine.goals[-1].position)
|
||||
self.goal = list(engine.goals.pop())
|
||||
|
||||
self.reset()
|
||||
|
||||
@ -37,10 +36,13 @@ class StateController:
|
||||
|
||||
self.fringe.put(start)
|
||||
|
||||
while self.fringe.queue and not self.path:
|
||||
while self.fringe and not self.path:
|
||||
self.explored.append(self.fringe.get())
|
||||
if self.goal_test(engine):
|
||||
return
|
||||
|
||||
if self.explored[-1].position == self.goal:
|
||||
goal_state = self.explored[-1]
|
||||
self.reset()
|
||||
return self.build_path(goal_state)
|
||||
|
||||
self.succ(self.explored[-1].front(), engine)
|
||||
self.succ(self.explored[-1].left(), engine)
|
||||
@ -49,10 +51,6 @@ class StateController:
|
||||
engine.redraw()
|
||||
|
||||
self.reset()
|
||||
for o in engine.objects:
|
||||
o.compare_pos(engine.goals[-1].position)
|
||||
o.agent_role = "block"
|
||||
engine.goals.pop()
|
||||
|
||||
print("Not found")
|
||||
|
||||
@ -92,19 +90,3 @@ class StateController:
|
||||
|
||||
if state.cost_so_far < fringe.cost_so_far:
|
||||
fringe.replace(state)
|
||||
|
||||
def goal_test(self, engine) -> bool:
|
||||
if self.explored[-1].position == self.goal:
|
||||
self.__is_goal__(self.explored[-1], engine)
|
||||
return True
|
||||
|
||||
for fringe in self.fringe.queue:
|
||||
if fringe.position == self.goal:
|
||||
self.__is_goal__(fringe, engine)
|
||||
return True
|
||||
|
||||
return False
|
||||
|
||||
def __is_goal__(self, goal_state, engine):
|
||||
self.reset()
|
||||
self.build_path(goal_state, engine)
|
||||
|
@ -9,3 +9,8 @@ class UserController:
|
||||
for event in pygame.event.get():
|
||||
if event.type == pygame.QUIT:
|
||||
engine.quit()
|
||||
elif event.type == pygame.MOUSEBUTTONDOWN:
|
||||
pos = pygame.mouse.get_pos()
|
||||
pos = (pos[0] // engine.square_size,
|
||||
pos[1] // engine.square_size)
|
||||
engine.appendGoalPosition(pos)
|
||||
|
@ -1,70 +0,0 @@
|
||||
import time
|
||||
from sklearn import tree
|
||||
import numpy as np
|
||||
import graphviz
|
||||
from src.decisionTree.datasetGenerator import generateRawDataset
|
||||
from src.decisionTree.datasetConverter import convertDataset
|
||||
|
||||
|
||||
class TreeEngine():
|
||||
def __init__(self):
|
||||
generateRawDataset()
|
||||
convertDataset()
|
||||
|
||||
# importing the dataset from the disk
|
||||
train_data_m = np.genfromtxt(
|
||||
"out/dataset.csv", delimiter=",", skip_header=1)
|
||||
|
||||
# Separate the attributes and labels
|
||||
self.X_train = [data[:-1] for data in train_data_m]
|
||||
self.y_train = [data[-1] for data in train_data_m]
|
||||
|
||||
# Create the decision tree classifier using the ID3 algorithm
|
||||
self.clf = tree.DecisionTreeClassifier(
|
||||
criterion='entropy', splitter="best")
|
||||
# clf = tree.DecisionTreeClassifier(criterion='gini')
|
||||
|
||||
# Train the decision tree on the training data
|
||||
self.clf.fit(self.X_train, self.y_train)
|
||||
|
||||
self.exportText()
|
||||
self.exportPdf()
|
||||
|
||||
def exportText(self):
|
||||
# Visualize the trained decision tree
|
||||
tree_text = tree.export_text(self.clf, feature_names=[
|
||||
"Battery level",
|
||||
"Distance between kitchen and table",
|
||||
"Customers mood",
|
||||
"Basket is empty",
|
||||
"Dish is ready",
|
||||
"Dish in basket",
|
||||
"Table status",
|
||||
"Is actual",
|
||||
])
|
||||
|
||||
with open('out/decision_tree.txt', 'w') as f:
|
||||
f.write(tree_text) # Save the visualization as a text file
|
||||
|
||||
def exportPdf(self):
|
||||
dot_data = tree.export_graphviz(self.clf, out_file=None, feature_names=[
|
||||
"Battery level",
|
||||
"Distance between kitchen and table",
|
||||
"Customers mood",
|
||||
"Basket is empty",
|
||||
"Dish is ready",
|
||||
"Dish in basket",
|
||||
"Table status",
|
||||
"Is actual",
|
||||
], class_names=[
|
||||
'High priority',
|
||||
'Low priority',
|
||||
'Return to kitchen',
|
||||
], filled=True, rounded=True)
|
||||
|
||||
graph = graphviz.Source(dot_data)
|
||||
# Save the visualization as a PDF file
|
||||
graph.render("out/decision_tree")
|
||||
|
||||
def make_predict(self, dataset):
|
||||
return self.clf.predict([dataset])
|
@ -1,111 +0,0 @@
|
||||
import csv
|
||||
from pathlib import Path
|
||||
|
||||
|
||||
def generateRawDataset():
|
||||
battery_values = ['high', 'low']
|
||||
distance_values = ['far', 'close']
|
||||
mood_values = ['undefined', 'good', 'bad']
|
||||
status_values = ['empty', 'new order', 'waiting for dish', 'have a dish']
|
||||
other = ['no', 'yes']
|
||||
|
||||
training_data = []
|
||||
training_data.append([
|
||||
"Battery level",
|
||||
"Distance between kitchen and table",
|
||||
"Customers mood",
|
||||
"Basket is empty",
|
||||
"Dish is ready",
|
||||
"Dish in basket",
|
||||
"Table status",
|
||||
"Is actual",
|
||||
"Priority"
|
||||
])
|
||||
|
||||
for battery in battery_values:
|
||||
for distance in distance_values:
|
||||
for mood in mood_values:
|
||||
for basket in other:
|
||||
for ready in other:
|
||||
for dish in other:
|
||||
for status in status_values:
|
||||
for actual in other:
|
||||
|
||||
dataset = buildDataset(
|
||||
battery,
|
||||
distance,
|
||||
mood,
|
||||
basket,
|
||||
ready,
|
||||
dish,
|
||||
status,
|
||||
actual
|
||||
)
|
||||
|
||||
training_data.append(dataset)
|
||||
|
||||
Path("out/").mkdir(parents=True, exist_ok=True)
|
||||
with open('out/rawDataset.csv', 'w', newline='') as file:
|
||||
writer = csv.writer(file)
|
||||
writer.writerows(training_data)
|
||||
|
||||
|
||||
def buildDataset(b, d, m, e, r, i, s, a) -> list:
|
||||
dataset = [
|
||||
b, # battery
|
||||
d, # distance
|
||||
m, # mood
|
||||
e, # basket is empty
|
||||
r, # ready
|
||||
i, # dish in basket
|
||||
s, # status
|
||||
a, # actual
|
||||
]
|
||||
|
||||
dataset.append(getPriority(dataset))
|
||||
|
||||
return dataset
|
||||
|
||||
|
||||
def getPriority(dataset) -> str:
|
||||
PRIORITY = {
|
||||
'high': 'high priority',
|
||||
'low': 'low priority',
|
||||
'kitchen': 'return to kitchen'
|
||||
}
|
||||
|
||||
BATTERY_LEVEL = dataset[0]
|
||||
DISTANCE_TO_OBJECT = dataset[1]
|
||||
MOOD = dataset[2]
|
||||
BASKET_IS_EMPTY = dataset[3]
|
||||
DISH_IS_READY = dataset[4]
|
||||
DISH_IN_BASKET = dataset[5]
|
||||
STATUS_OF_TABLE = dataset[6]
|
||||
IS_ACTUAL = dataset[7]
|
||||
|
||||
def mood_and_distance() -> str:
|
||||
if MOOD == "undefined":
|
||||
return PRIORITY['kitchen']
|
||||
elif MOOD == "good":
|
||||
return PRIORITY['low']
|
||||
elif DISTANCE_TO_OBJECT == "far":
|
||||
return PRIORITY['high']
|
||||
else:
|
||||
return PRIORITY['low']
|
||||
|
||||
if BATTERY_LEVEL == "low":
|
||||
return PRIORITY['kitchen']
|
||||
elif IS_ACTUAL == "no":
|
||||
return PRIORITY['high']
|
||||
elif STATUS_OF_TABLE == "empty" or STATUS_OF_TABLE == "have a dish":
|
||||
return PRIORITY['kitchen']
|
||||
elif STATUS_OF_TABLE == "new order":
|
||||
return mood_and_distance()
|
||||
elif BASKET_IS_EMPTY == "yes":
|
||||
return PRIORITY['kitchen']
|
||||
elif DISH_IS_READY == "no":
|
||||
return PRIORITY['kitchen']
|
||||
elif DISH_IN_BASKET == "no":
|
||||
return PRIORITY['kitchen']
|
||||
else:
|
||||
return mood_and_distance()
|
BIN
src/img/goal.png
BIN
src/img/goal.png
Binary file not shown.
Before Width: | Height: | Size: 46 KiB |
@ -1,9 +0,0 @@
|
||||
from src.obj.Object import Object
|
||||
|
||||
|
||||
class Goal(Object):
|
||||
def __init__(self, position, square_size, screen_size):
|
||||
super().__init__("goal", position, 0, square_size, screen_size)
|
||||
|
||||
def collide_test(self, waiter: Object) -> bool:
|
||||
return waiter.position == self.position
|
@ -4,7 +4,3 @@ from src.obj.Object import Object
|
||||
class Kitchen(Object):
|
||||
def __init__(self, position, orientation, square_size, screen_size):
|
||||
super().__init__("kitchen", position, orientation, square_size, screen_size)
|
||||
|
||||
def action(self, waiter, current_time):
|
||||
waiter.combine_orders(current_time)
|
||||
waiter.recharge()
|
||||
|
@ -46,17 +46,3 @@ class Object:
|
||||
|
||||
def compare_pos(self, pos) -> bool:
|
||||
return self.position == pos
|
||||
|
||||
def distance_to(self, pos) -> int:
|
||||
x = abs(self.position[0] - pos[0])
|
||||
y = abs(self.position[1] - pos[1])
|
||||
|
||||
self.h = x + y
|
||||
|
||||
return self.h
|
||||
|
||||
def action(self, obj):
|
||||
pass
|
||||
|
||||
def updateState(self, current_time):
|
||||
pass
|
||||
|
@ -1,84 +1,14 @@
|
||||
import random
|
||||
from src.obj.Object import Object
|
||||
|
||||
|
||||
class Table(Object):
|
||||
def __init__(self, position, orientation, square_size, screen_size):
|
||||
def __init__(self, position, orientation, square_size, screen_size, current_role=0):
|
||||
super().__init__("table", position, orientation, square_size, screen_size)
|
||||
self.waiting_time = 0
|
||||
self.cooking_time = 0
|
||||
self.is_actual = False
|
||||
self.roles = ["table", "order", "wait", "done"]
|
||||
self.current_role = current_role
|
||||
self.change_role(self.roles[self.current_role])
|
||||
|
||||
def isActual(self):
|
||||
return self.is_actual
|
||||
|
||||
def updateState(self, current_time):
|
||||
if self.is_actual:
|
||||
return
|
||||
self.is_actual = True
|
||||
# here must be neural network choise
|
||||
new_role = random.choice(["table", "order", "wait", "done"])
|
||||
self.change_role(new_role, current_time)
|
||||
|
||||
if self.agent_role == "table":
|
||||
return
|
||||
elif self.agent_role == "wait":
|
||||
self.cooking_time = random.randint(0, 300)
|
||||
|
||||
def dish_is_ready(self, current_time):
|
||||
return current_time - self.waiting_time > self.cooking_time
|
||||
|
||||
def get_state_number(self) -> int:
|
||||
roles = {
|
||||
"table": 0,
|
||||
"order": 1,
|
||||
"wait": 2,
|
||||
"done": 3
|
||||
}
|
||||
|
||||
return roles[self.agent_role]
|
||||
|
||||
def change_role(self, new_role, current_time):
|
||||
self.waiting_time = current_time
|
||||
return super().change_role(new_role)
|
||||
|
||||
def reset(self, current_time):
|
||||
self.is_actual = False
|
||||
self.change_role("table", current_time)
|
||||
|
||||
def set_order(self, current_time):
|
||||
if self.agent_role == "table":
|
||||
self.change_role("order", current_time)
|
||||
|
||||
def set_wait(self, current_time):
|
||||
if self.agent_role == "order":
|
||||
self.change_role("wait", current_time)
|
||||
|
||||
def set_done(self, current_time):
|
||||
if self.agent_role == "wait":
|
||||
self.change_role("done", current_time)
|
||||
|
||||
def is_order(self):
|
||||
return self.agent_role == "order"
|
||||
|
||||
def is_wait(self):
|
||||
return self.agent_role == "wait"
|
||||
|
||||
def is_done(self):
|
||||
return self.agent_role == "done"
|
||||
|
||||
def get_customers_count(self) -> int:
|
||||
return self.customers
|
||||
|
||||
def get_mood(self, current_time) -> int: # перапісаць
|
||||
if self.agent_role == "table":
|
||||
return 2 # undefined
|
||||
|
||||
diff = current_time - self.waiting_time
|
||||
return 0 if diff >= 300 else 1 # 0 - bad; 1 - good
|
||||
|
||||
def action(self, waiter, current_time):
|
||||
if self.is_order():
|
||||
waiter.collect_order(self, current_time)
|
||||
elif self.is_done():
|
||||
waiter.deliver_dish(self, current_time)
|
||||
def next_role(self, waiter):
|
||||
if waiter.agent_role == "waiter":
|
||||
self.current_role = (self.current_role + 1) % 4
|
||||
self.change_role(self.roles[self.current_role])
|
||||
|
@ -11,11 +11,11 @@ class TemporaryState(Waiter):
|
||||
copy.copy(parent.basket))
|
||||
self.agent_role = action
|
||||
self.parent = parent
|
||||
self.change_role(action)
|
||||
self.apply_transformation()
|
||||
self.cost = cost
|
||||
self.cost_so_far = cost_so_far
|
||||
self.h = h
|
||||
self.change_role(action)
|
||||
self.apply_transformation()
|
||||
|
||||
def replace(self, repl):
|
||||
self.cost_so_far = copy.copy(repl.cost_so_far)
|
||||
@ -76,7 +76,11 @@ class TemporaryState(Waiter):
|
||||
self.cost = costs[obj.agent_role]
|
||||
|
||||
def heuristic(self, goal):
|
||||
self.h = self.distance_to(goal)
|
||||
x = abs(self.position[0] - goal[0])
|
||||
y = abs(self.position[1] - goal[1])
|
||||
|
||||
self.h = x + y
|
||||
|
||||
return self.h
|
||||
|
||||
def current_cost(self):
|
||||
|
@ -3,13 +3,16 @@ from src.obj.Object import Object
|
||||
|
||||
|
||||
class Waiter(Object):
|
||||
def __init__(self, position, orientation, square_size, screen_size, basket=[], memory=[], battery=300):
|
||||
def __init__(self, position, orientation, square_size, screen_size, basket=[]):
|
||||
super().__init__("waiter", position, orientation, square_size, screen_size)
|
||||
self.battery = battery
|
||||
self.basket_size = 4
|
||||
self.memory_size = 4
|
||||
self.basket_size = 2
|
||||
self.battery=2
|
||||
self.orderReadiness=1
|
||||
self.waitingTables=1
|
||||
self.availability=1
|
||||
self.cleanliness=2
|
||||
self.error=1
|
||||
self.basket = basket
|
||||
self.memory = memory
|
||||
self.prev_position = copy.deepcopy(self.position)
|
||||
self.prev_orientation = copy.copy(self.orientation)
|
||||
|
||||
@ -17,54 +20,88 @@ class Waiter(Object):
|
||||
self.position = copy.deepcopy(state.position)
|
||||
self.orientation = copy.copy(state.orientation)
|
||||
self.basket = copy.copy(state.basket)
|
||||
self.battery -= state.cost
|
||||
self.calcTree()
|
||||
return state
|
||||
|
||||
def dish_in_basket(self, table) -> bool:
|
||||
return table in self.basket
|
||||
def calcTree(self):
|
||||
from sklearn import tree
|
||||
import pandas as pd #for manipulating the csv data
|
||||
import numpy as np
|
||||
import os
|
||||
|
||||
def basket_is_full(self) -> bool:
|
||||
return self.basket_size == 0
|
||||
train_data_m=np.genfromtxt("dataset/converted_dataset.csv", delimiter=",",skip_header=1); #importing the dataset from the disk
|
||||
|
||||
def basket_is_empty(self) -> bool:
|
||||
return self.basket_size == 4
|
||||
|
||||
def combine_orders(self, current_time):
|
||||
while not self.basket_is_full() and not self.memory_is_empty():
|
||||
dish = self.memory.pop()
|
||||
dish.set_done(current_time)
|
||||
self.basket.append(dish)
|
||||
self.basket_size -= 1
|
||||
self.memory_size += 1
|
||||
X_train = [data[:-1] for data in train_data_m]
|
||||
y_train = [data[-1] for data in train_data_m]
|
||||
# Create the decision tree classifier using the ID3 algorithm
|
||||
clf = tree.DecisionTreeClassifier(criterion='entropy')
|
||||
|
||||
def deliver_dish(self, table, current_time):
|
||||
if table in self.basket:
|
||||
table.reset(current_time)
|
||||
self.basket.remove(table)
|
||||
self.basket_size += 1
|
||||
# Train the decision tree on the training data
|
||||
clf.fit(X_train, y_train)
|
||||
|
||||
def order_in_memory(self, table) -> bool:
|
||||
return table in self.memory
|
||||
# Visualize the trained decision tree
|
||||
tree_text = tree.export_text(clf,feature_names=['Battery Charge', 'Fullness', 'Ready orders', 'Waiting tables','Availability', 'Cleanliness', 'Error'])
|
||||
with open('decision_tree.txt', 'w') as f:
|
||||
f.write(tree_text) # Save the visualization as a text file
|
||||
|
||||
def memory_is_empty(self) -> bool:
|
||||
return not self.memory
|
||||
# Test the decision tree with a new example
|
||||
#Battery Charge,Fullness,Ready orders,Waiting tables,Availability,Cleanliness,Error
|
||||
new_example = [self.battery, 0,self.orderReadiness,self.waitingTables,self.availability, self.cleanliness, self.error]
|
||||
predicted_label = clf.predict([new_example])
|
||||
if predicted_label[0]>0:
|
||||
result="YES"
|
||||
else:
|
||||
result="NO"
|
||||
print("Predicted Label:", result)
|
||||
|
||||
def memory_is_full(self) -> bool:
|
||||
return self.memory_size == 0
|
||||
def calcTreePDF(self):
|
||||
from sklearn import tree
|
||||
import pandas as pd #for manipulating the csv data
|
||||
import numpy as np
|
||||
import graphviz
|
||||
import os
|
||||
os.environ["PATH"] += os.pathsep + 'C:/Program Files (x86)/Graphviz/bin/'
|
||||
|
||||
def collect_order(self, table, current_time):
|
||||
if self.memory_is_full():
|
||||
return
|
||||
if table.agent_role == "order":
|
||||
table.set_wait(current_time)
|
||||
self.memory.append(table)
|
||||
self.memory_size -= 1
|
||||
train_data_m=np.genfromtxt("dataset/converted_dataset.csv", delimiter=",",skip_header=1); #importing the dataset from the disk
|
||||
|
||||
def battery_status(self) -> int:
|
||||
return 1 if self.battery >= 100 else 0
|
||||
|
||||
def recharge(self):
|
||||
self.battery = 300
|
||||
X_train = [data[:-1] for data in train_data_m]
|
||||
y_train = [data[-1] for data in train_data_m]
|
||||
# Create the decision tree classifier using the ID3 algorithm
|
||||
clf = tree.DecisionTreeClassifier(criterion='entropy')
|
||||
|
||||
# Train the decision tree on the training data
|
||||
clf.fit(X_train, y_train)
|
||||
|
||||
# Visualize the trained decision tree
|
||||
tree_text = tree.export_text(clf,feature_names=['Battery Charge', 'Fullness', 'Ready orders', 'Waiting tables','Availability', 'Cleanliness', 'Error'])
|
||||
with open('decision_tree.txt', 'w') as f:
|
||||
f.write(tree_text) # Save the visualization as a text file
|
||||
dot_data = tree.export_graphviz(clf, out_file=None, feature_names=['Battery Charge', 'Fullness', 'Ready orders', 'Waiting tables','Availability', 'Cleanliness', 'Error'], class_names=['NO', 'YES'], filled=True,rounded=True)
|
||||
graph = graphviz.Source(dot_data)
|
||||
graph.render("decision_tree") # Save the visualization as a PDF file
|
||||
|
||||
# Test the decision tree with a new example
|
||||
#Battery Charge,Fullness,Ready orders,Waiting tables,Availability,Cleanliness,Error
|
||||
new_example = [self.battery, 0,self.orderReadiness,self.waitingTables,self.availability, self.cleanliness, self.error]
|
||||
predicted_label = clf.predict([new_example])
|
||||
if predicted_label[0]>0:
|
||||
result="YES"
|
||||
else:
|
||||
result="NO"
|
||||
print("Predicted Label:", result)
|
||||
|
||||
def dampState(self):
|
||||
self.prev_position = copy.deepcopy(self.position)
|
||||
self.prev_orientation = copy.copy(self.orientation)
|
||||
|
||||
def rollbackState(self):
|
||||
self.position = copy.deepcopy(self.prev_position)
|
||||
self.orientation = copy.copy(self.prev_orientation)
|
||||
|
||||
def orders_in_basket(self) -> bool:
|
||||
return self.basket
|
||||
|
||||
def left(self):
|
||||
self.orientation = (self.orientation + 1) % 4
|
||||
@ -78,9 +115,12 @@ class Waiter(Object):
|
||||
else: # y (0 or 2)
|
||||
self.position[1] += self.orientation - 1 # y (-1 or +1)
|
||||
|
||||
def chechNeighbor(self, n, r=1):
|
||||
def collide_test(self, obj) -> bool:
|
||||
out_of_range = [
|
||||
self.position[0] >= self.square_count,
|
||||
self.position[1] >= self.square_count,
|
||||
self.position[0] < 0,
|
||||
self.position[1] < 0
|
||||
]
|
||||
|
||||
cond_x = abs(self.position[0] - n.position[0]) <= r
|
||||
cond_y = abs(self.position[1] - n.position[1]) <= r
|
||||
|
||||
return cond_x and cond_y
|
||||
return any(out_of_range)
|
||||
|
Loading…
Reference in New Issue
Block a user