From dd206307b912eb715ad7b08e432bfe399c451c05 Mon Sep 17 00:00:00 2001 From: Geoffrey Frogeye Date: Sat, 13 Feb 2016 16:43:54 +0100 Subject: [PATCH] Preparation for multiple stop trips Nothing should have changed in the results, yet it won three points. Oh well... --- reborn.py | 70 ++++++++++++++++++++++++++++++++++++++----------------- 1 file changed, 49 insertions(+), 21 deletions(-) diff --git a/reborn.py b/reborn.py index fb6936e..2b7f51d 100755 --- a/reborn.py +++ b/reborn.py @@ -30,6 +30,12 @@ class Product: self.weight = weight + def totalWeight(items): + s = 0 + for i in items: + s += Product.get(i).weight + return s + def get(pid): return __class__.ALL[pid] @@ -87,11 +93,15 @@ class Client: return len(self.needs) == 0 def pack(self, payload=-1): - # TODO Optimise for same product wanted more than once if payload == -1: payload = Drone.PAYLOAD p = [] load = 0 + # # Sort occurences + # occ = [(i, self.plannedNeeds.count(i)) for i in self.plannedNeeds] + # occ.sort(key=lambda c: c[1]) + # # TODO Optimise for same product wanted more than once + # Looks like it's not necessary for set 2, we'll see that later # Sort needs by weight couples = [(i, Product.get(i).weight) for i in self.plannedNeeds] couples.sort(key=lambda c: c[1]) @@ -143,10 +153,7 @@ class Drone: self.wait() def weight(self): - s = 0 - for i in self.items: - s += Product.get(i).weight - return s + return Product.totalWeight(self.items) def busyFor(self, time): self.avail += time @@ -280,31 +287,52 @@ def newTurn(): #log("Drones", ", ".join(availableDrones), "("+str(len(availableDrones))+")", "are available") # Algorithm that only works for 1 warehouse +def route(roadmap): + # Find the nearest client that still has things to be delivered + remainingClients = [c for c in Client.near(roadmap['pos']) if c.plannedNeeds] + if remainingClients: + client = remainingClients[0] + # Create a pack to deliver + pack = client.pack() + # TODO if pack ... else ... + # Plan the delivery + roadmap['warehouse'].plan(pack) + client.plan(pack) + roadmap['deliverTime'] += distance(roadmap['pos'], client.pos) + len(list(set(pack))) + roadmap['pos'] = client.pos + roadmap['loads'] += pack + roadmap['stops'].append((client, pack)) + return roadmap + + def think(): # For each drone that has nothing to do for drone in [d for d in Drone.ALL if d.available() and not d.tasks]: # Find the nearest warehouse warehouse = Warehouse.near(drone.pos)[0] - # Find the nearest client that still has things to be delivered - remainingClients = [c for c in Client.near(warehouse.pos) if c.plannedNeeds] - if remainingClients: - client = remainingClients[0] - # Create a pack to deliver - pack = client.pack() - # Plan the delivery - packOccurences = dict((i, pack.count(i)) for i in pack) - # From http://stackoverflow.com/a/7843090/2766106 - for i in packOccurences: - drone.addTask('load', warehouse, Product.get(i), packOccurences[i]) - warehouse.plan(pack) - for i in packOccurences: - drone.addTask('deliver', client, Product.get(i), packOccurences[i]) - client.plan(pack) - else: + roadmap = route({ + 'pos': warehouse.pos, + 'warehouse': warehouse, + 'deliverTime': 0, + 'loads': [], + 'stops': [] + }) + + if not roadmap['stops']: global done done = True break + loadOcc = dict((i, roadmap['loads'].count(i)) for i in roadmap['loads']) + for i in loadOcc: + drone.addTask('load', warehouse, Product.get(i), loadOcc[i]) + + for client, items in roadmap['stops']: + itemsOcc = dict((j, items.count(j)) for j in items) + for i in itemsOcc: + drone.addTask('deliver', client, Product.get(i), itemsOcc[i]) + + if DEBUG: SIMULATION = 1000