diff --git a/.gitignore b/.gitignore index 3c3629e6..274d0491 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,2 @@ node_modules +.venv \ No newline at end of file diff --git a/sprint-5/laptop-allocation.py b/sprint-5/laptop-allocation.py new file mode 100644 index 00000000..a4139862 --- /dev/null +++ b/sprint-5/laptop-allocation.py @@ -0,0 +1,88 @@ +from dataclasses import dataclass +from enum import Enum +from typing import List, Dict +from itertools import permutations + +unpreferred_OS_penalty = 100 + +class OperatingSystem(Enum): + MACOS = "macOS" + ARCH = "Arch Linux" + UBUNTU = "Ubuntu" + +@dataclass(frozen=True) +class Person: + name: str + age: int + preferred_operating_system: tuple + +@dataclass(frozen=True) +class Laptop: + id: int + manufacturer: str + model: str + screen_size_in_inches: float + operating_system: OperatingSystem + +def allocate_laptops(people: List[Person], laptops: List[Laptop]) -> Dict[Person, Laptop]: + if len(people) != len(laptops): + raise ValueError("Number of people must match number of laptops") + + best_assignment = None + lowest_sadness = float("inf") + + for perm in permutations(laptops): + total_sadness = 0 + for person, laptop in zip(people, perm): + if laptop.operating_system in person.preferred_operating_system: + sadness = person.preferred_operating_system.index(laptop.operating_system) + else: + sadness = unpreferred_OS_penalty + total_sadness += sadness + + if total_sadness < lowest_sadness: + lowest_sadness = total_sadness + best_assignment = perm + + return {person: laptop for person, laptop in zip(people, best_assignment)} + +laptops = [ + Laptop(1, "Dell", "XPS 13", 13, OperatingSystem.ARCH), + Laptop(2, "HP", "Spectre 15", 15, OperatingSystem.UBUNTU), + Laptop(3, "Lenovo", "ThinkPad 14", 14, OperatingSystem.UBUNTU), + Laptop(4, "Apple", "MacBook Air", 13, OperatingSystem.MACOS), + Laptop(5, "Apple", "MacBook Pro", 16, OperatingSystem.MACOS), + Laptop(6, "Dell", "Latitude", 15, OperatingSystem.ARCH), + Laptop(7, "HP", "EliteBook", 13, OperatingSystem.MACOS), + Laptop(8, "Lenovo", "Yoga", 14, OperatingSystem.UBUNTU) +] + +people = [ + Person("Alice", 29, (OperatingSystem.UBUNTU, OperatingSystem.MACOS)), + Person("Bob", 34, (OperatingSystem.ARCH, OperatingSystem.UBUNTU)), + Person("Charlie", 40, (OperatingSystem.MACOS, OperatingSystem.ARCH)), + Person("Diana", 25, (OperatingSystem.MACOS,)), + Person("Ethan", 31, (OperatingSystem.UBUNTU, OperatingSystem.ARCH)), + Person("Fiona", 27, (OperatingSystem.MACOS, OperatingSystem.UBUNTU)), + Person("George", 22, (OperatingSystem.ARCH, OperatingSystem.MACOS)), + Person("Zara", 33, (OperatingSystem.ARCH, OperatingSystem.MACOS)) +] + +assignment = allocate_laptops(people, laptops) + + +for person, laptop in assignment.items(): + person_sadness_score = ( + person.preferred_operating_system.index(laptop.operating_system) + if laptop.operating_system in person.preferred_operating_system + else unpreferred_OS_penalty + ) + print(f"{person.name} was allocated {laptop.manufacturer} {laptop.model} " + f"with {laptop.operating_system.value} (Score: {person_sadness_score})") + +total_sadness = sum( + person.preferred_operating_system.index(laptop.operating_system) + if laptop.operating_system in person.preferred_operating_system else unpreferred_OS_penalty + for person, laptop in assignment.items() +) +print("\nTotal sadness:", total_sadness)