Genetic Alghoritm implemented, Tree moved

This commit is contained in:
Kamszooo 2023-06-16 12:20:46 +02:00
parent 3b2342a6b4
commit 1c26edad6c
6 changed files with 216 additions and 25 deletions

10
collect
View File

@ -24,11 +24,11 @@ edge [fontname="helvetica"] ;
6 -> 10 ; 6 -> 10 ;
11 [label="garbage_weight <= 0.612\ngini = 0.094\nsamples = 61\nvalue = [3, 58]\nclass = no-collect"] ; 11 [label="garbage_weight <= 0.612\ngini = 0.094\nsamples = 61\nvalue = [3, 58]\nclass = no-collect"] ;
10 -> 11 ; 10 -> 11 ;
12 [label="garbage_type <= 2.0\ngini = 0.5\nsamples = 2\nvalue = [1, 1]\nclass = collect"] ; 12 [label="space_occupied <= 0.382\ngini = 0.5\nsamples = 2\nvalue = [1, 1]\nclass = collect"] ;
11 -> 12 ; 11 -> 12 ;
13 [label="gini = 0.0\nsamples = 1\nvalue = [1, 0]\nclass = collect"] ; 13 [label="gini = 0.0\nsamples = 1\nvalue = [0, 1]\nclass = no-collect"] ;
12 -> 13 ; 12 -> 13 ;
14 [label="gini = 0.0\nsamples = 1\nvalue = [0, 1]\nclass = no-collect"] ; 14 [label="gini = 0.0\nsamples = 1\nvalue = [1, 0]\nclass = collect"] ;
12 -> 14 ; 12 -> 14 ;
15 [label="garbage_type <= 2.5\ngini = 0.065\nsamples = 59\nvalue = [2, 57]\nclass = no-collect"] ; 15 [label="garbage_type <= 2.5\ngini = 0.065\nsamples = 59\nvalue = [2, 57]\nclass = no-collect"] ;
11 -> 15 ; 11 -> 15 ;
@ -50,11 +50,11 @@ edge [fontname="helvetica"] ;
5 -> 23 ; 5 -> 23 ;
24 [label="gini = 0.0\nsamples = 2\nvalue = [0, 2]\nclass = no-collect"] ; 24 [label="gini = 0.0\nsamples = 2\nvalue = [0, 2]\nclass = no-collect"] ;
23 -> 24 ; 23 -> 24 ;
25 [label="odour_intensity <= 8.841\ngini = 0.219\nsamples = 8\nvalue = [7, 1]\nclass = collect"] ; 25 [label="days_since_last_collection <= 22.0\ngini = 0.219\nsamples = 8\nvalue = [7, 1]\nclass = collect"] ;
23 -> 25 ; 23 -> 25 ;
26 [label="gini = 0.0\nsamples = 6\nvalue = [6, 0]\nclass = collect"] ; 26 [label="gini = 0.0\nsamples = 6\nvalue = [6, 0]\nclass = collect"] ;
25 -> 26 ; 25 -> 26 ;
27 [label="days_since_last_collection <= 22.0\ngini = 0.5\nsamples = 2\nvalue = [1, 1]\nclass = collect"] ; 27 [label="odour_intensity <= 8.841\ngini = 0.5\nsamples = 2\nvalue = [1, 1]\nclass = collect"] ;
25 -> 27 ; 25 -> 27 ;
28 [label="gini = 0.0\nsamples = 1\nvalue = [1, 0]\nclass = collect"] ; 28 [label="gini = 0.0\nsamples = 1\nvalue = [1, 0]\nclass = collect"] ;
27 -> 28 ; 27 -> 28 ;

Binary file not shown.

View File

@ -54,6 +54,8 @@ class GarbageTruck:
def next_destination(self): def next_destination(self):
for i in range(len(self.request_list)): for i in range(len(self.request_list)):
if(self.request_list==[]):
break
request = self.request_list[i] request = self.request_list[i]
#nie ma miejsca w zbiorniku lub za ciężkie śmieci #nie ma miejsca w zbiorniku lub za ciężkie śmieci
@ -64,25 +66,10 @@ class GarbageTruck:
if heuristicfn(request.x_pos, request.y_pos, self.dump_x, self.dump_y) // 50 * 200 > self.fuel: if heuristicfn(request.x_pos, request.y_pos, self.dump_x, self.dump_y) // 50 * 200 > self.fuel:
continue continue
self.request_list.pop(i)
self.free_space -= request.volume
distance = heuristicfn(self.rect.x, self.rect.y, request.x_pos, request.y_pos) // 50 self.weight_capacity -= request.weight
return request.x_pos, request.y_pos
r = [
self.fuel,
distance,
request.volume,
request.last_collection,
request.is_paid,
request.odour_intensity,
request.weight,
request.type
]
if self.clf.predict([r]) == True:
self.request_list.pop(i)
self.free_space -= request.volume
self.weight_capacity -= request.weight
return request.x_pos, request.y_pos
return self.dump_x, self.dump_y return self.dump_x, self.dump_y
@ -96,7 +83,10 @@ class GarbageTruck:
self.weight_capacity_mixed = MAX_WEIGHT_MIXED self.weight_capacity_mixed = MAX_WEIGHT_MIXED
self.weight_capacity_glass = MAX_WEIGHT_GLASS self.weight_capacity_glass = MAX_WEIGHT_GLASS
self.weight_capacity_paper = MAX_WEIGHT_PAPER self.weight_capacity_paper = MAX_WEIGHT_PAPER
request = self.request_list[0] if self.request_list==[]:
return 1
else:
request = self.request_list[0]
if garbage_type == "glass": if garbage_type == "glass":
if request.weight > self.weight_capacity_glass: if request.weight > self.weight_capacity_glass:
return 1 return 1

162
genetic.py Normal file
View File

@ -0,0 +1,162 @@
import pygame
from treelearn import treelearn
import loadmodel
from astar import astar
from state import State
import time
from garbage_truck import GarbageTruck
from heuristicfn import heuristicfn
from map import randomize_map
from heuristicfn import heuristicfn
import pygame as pg
import random
from request import Request
def determine_fitness(requests_list):
distances = []
for i in range(len(requests_list)+1): #from: request_list[i].x_pos and .y_pos
temp = []
for j in range(len(requests_list)+1):
if j<i:
temp.append('-')
elif j==i:
temp.append(0)
elif j>i:
if i==0:
dist = heuristicfn(0, 0, requests_list[j-1].x_pos, requests_list[j-1].y_pos)
temp.append(dist)
else:
dist = heuristicfn(requests_list[i-1].x_pos, requests_list[i-1].y_pos, requests_list[j-1].x_pos, requests_list[j-1].y_pos)
temp.append(dist)
distances.append(temp)
return(distances)
def perform_permutation(obj_list, perm_list):
result = [None] * len(obj_list)
for i, index in enumerate(perm_list):
result[int(index)-1] = obj_list[i-1]
return result
def apply_genetic(request_list):
print("Genetic algorithm started")
distances = determine_fitness(request_list)
population_size = 12
num_generations = 8
mutation_rate = 0.3
NUM = len(distances)
def initialize_population():
population = []
for _ in range(population_size):
chromosome = ['0']
while True:
if len(chromosome) == NUM:
chromosome.append('0')
break
temp = random.randint(1, NUM-1)
temp_str = str(temp)
if temp_str not in chromosome:
chromosome.append(temp_str)
population.append(chromosome)
return population
def calculate_route_length(route):
length = 0
for i in range(len(route)-1):
p = int(route[i])
q = int(route[i + 1])
length += distances[int(min(p,q))][int(max(p,q))]
return length
def calculate_fitness(population):
fitness_scores = []
for chromosome in population:
fitness_scores.append(1 / calculate_route_length(chromosome))
return fitness_scores
def parents_selection(population, fitness_scores):
selected_parents = []
for _ in range(len(population)):
candidates = random.sample(range(len(population)), 2)
fitness1 = fitness_scores[candidates[0]]
fitness2 = fitness_scores[candidates[1]]
selected_parent = population[candidates[0]] if fitness1 > fitness2 else population[candidates[1]]
selected_parents.append(selected_parent)
return selected_parents
def david_crossover(parent1, parent2):
start_index = random.randint(1, len(parent1)-3)
end_index = random.randint(start_index+1, len(parent1)-2)
parent1_chain = parent1[start_index:end_index+1]
parent2_letters = []
for trash in parent2[1:-1]:
if trash not in parent1_chain:
parent2_letters.append(trash)
child = [parent2[0]]+parent2_letters[0:start_index] + parent1_chain + parent2_letters[start_index:]+[parent2[-1]]
""" print('PARENTS: ')
print(parent1)
print(parent2)
print('CHILDS:')
print(child) """
return child
def mutation(chromosome):
index1 = random.randint(1, len(chromosome)-2)
index2 = random.randint(1, len(chromosome)-2)
chromosome[index1], chromosome[index2] = chromosome[index2], chromosome[index1]
return chromosome
def genetic_algorithm():
population = initialize_population()
for _ in range(num_generations):
fitness_scores = calculate_fitness(population)
parents = parents_selection(population, fitness_scores)
offspring = []
for i in range(0, len(parents), 2):
parent1 = parents[i]
parent2 = parents[i+1]
child1 = david_crossover(parent1, parent2)
child2 = david_crossover(parent2, parent1)
offspring.extend([child1, child2])
population = offspring
for i in range(len(population)):
if random.random() < mutation_rate:
population[i] = mutation(population[i])
return population
best_route = None
best_length = float('inf')
population = genetic_algorithm()
for chromosome in population:
length = calculate_route_length(chromosome)
if length < best_length:
best_length = length
best_route = chromosome
print("Permutation chosen: ", best_route)
print("Its length:", best_length)
permuted_list = perform_permutation(request_list, best_route[1:-1])

View File

@ -7,6 +7,8 @@ import time
from garbage_truck import GarbageTruck from garbage_truck import GarbageTruck
from heuristicfn import heuristicfn from heuristicfn import heuristicfn
from map import randomize_map from map import randomize_map
from tree import apply_tree
from genetic import apply_genetic
pygame.init() pygame.init()
@ -38,6 +40,8 @@ def main():
clock = pygame.time.Clock() clock = pygame.time.Clock()
run = True run = True
fields, priority_array, request_list, imgpath_array = randomize_map() fields, priority_array, request_list, imgpath_array = randomize_map()
apply_tree(request_list)
apply_genetic(request_list)
agent = GarbageTruck(0, 0, pygame.Rect(0, 0, 50, 50), 0, request_list, clf) # tworzenie pola dla agenta agent = GarbageTruck(0, 0, pygame.Rect(0, 0, 50, 50), 0, request_list, clf) # tworzenie pola dla agenta
low_space = 0 low_space = 0
while run: while run:

35
tree.py Normal file
View File

@ -0,0 +1,35 @@
import pygame
from treelearn import treelearn
import loadmodel
from astar import astar
from state import State
import time
from garbage_truck import GarbageTruck
from heuristicfn import heuristicfn
from map import randomize_map
from heuristicfn import heuristicfn
import pygame as pg
import random
from request import Request
def apply_tree(request_list):
print("Przed zastosowaniem drzewa na liście jest śmieci: ", len(request_list))
for address in request_list:
r = [
0,
0,
address.volume,
address.last_collection,
address.is_paid,
address.odour_intensity,
address.weight,
address.type
]
clf = treelearn()
if clf.predict([r]) == False:
request_list.pop(request_list.index(address))
print("Po zastosowaniu drzewa na liście jest śmieci: ", len(request_list))
return request_list