Skip to content

DimaOanaTeodora/Fox-and-Geese-AI-Game

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

33 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Vulpi si Gaste ( 🦊 vs 🦆 )

Link cerinta joc

Link joc online

Meniu cu mai multe butoane

💹 Posibilitate de selectare a celor 3 optiuni: Jucator vs Jucator, Jucator vs Calculator, Calculator(estimare gaste) vs Calculator(estimare vulpe)

💹 Selectare default Jucator vs Calculator : Gaste vs Calculator Min-Max

💹 Utilizatorul poate alege ce algoritm doreste sa foloseasca (Min-Max sau Alpha-Beta)

💹 Utilizatorul poate sa aleaga daca joaca de partea vulpii sau a gastelor

💹 Prin utilizarea meniului utilizatorul nu poate raspunde gresit

💹 Utilizatorul poate alege din 3 nivele de dificultate

💹 Fiecare nivel corespunde unei adancimi a arborelui calculata prin formula 1 + 2 * dificultate ( pt niv Usor => adancime = 1, pt niv Mediu => adancime=3, pt niv Greu => adancime =5 )

Tabla de joc

💹 Interfata grafica PyGame

    def desenare_tabla_joc(self, ecran):
        for i in range(len(self.noduri)):
            for muchie in self.muchii[i]:
                pozitia1 = self.noduri[i].punct_desenat
                pozitia2 = self.noduri[muchie].punct_desenat

                # desenare linie dintre doua puncte
                pygame.draw.line(ecran, (0, 0, 0), pozitia1, pozitia2, 2)

💹 Afisarea a cui este rândul să mute.

💹 Indicarea, la finalul jocului, a câstigatorului

💹 Generarea si afisarea starii initiale de joc: 13 gaste si o vulpe

💹 Generarea si afisarea starilor intermediare de joc

💹 Mutare utilizator prin eveniment in interfata grafica (click mouse)

💹 clasa utilitara pentru controlul inputului de mouse: MouseInput ( constructor + metoda update(self))

💹 Verificata si corectitudinea mutarilor utilizatorului prin apelul functiei:

returneaza_nod_apasat(tabla_de_joc, pygame.mouse.get_pos())
# daca nodul nu exista returneaza -1

Afisare + debugging in consola

💹 Afisare in consola tabela de joc

    def afisare_consola(self, tabla_de_joc):
        for x in range(8):
            for y in range(8):
                if tabla_de_joc.numar_nod_in_grafic.get((x, y)) != None:

                    # accesez valoarea din dictionarul numar_nod_in_grafic
                    numar_nod = tabla_de_joc.numar_nod_in_grafic[(x, y)]

                    if numar_nod in self.gaste:
                        print("G ", end="")
                    elif numar_nod == self.vulpe:
                        print("V ", end="")
                    else:
                        print("# ", end="")
                else:
                    print("  ", end="")

            print("\n", end="")

💹 Afisarea timpului de gandire, dupa fiecare mutare

💹 Pentru timpul de găndire al calculatorului: afișarea la final a timpului minim, maxim, mediu și a medianei.

 def update(self): # din clas Joc

💹 Afișarea estimărilor date si numărului de noduri generate de minimax și alpha-beta ( functiile muta din clase)

💹 La final se va afișa numărul minim, maxim, mediu și mediana pentru numarul de noduri generat pentru fiecare mutare

💹 Afisarea timpului final de joc (cat a rulat programul) si a numarului total de mutari

💹 Utilizatorul poate sa opreasca jocul cand vrea si sa afiseze analiza timpilor si a mutarilor in consola folosind tasta ESCAPE care il va intoarce in meniul principal

Cerinte suplimentare

💹 Titlul ferestrei de joc

pygame.display.set_caption('Dima Oana-Teodora Vulpi si Gaste')

💹 Functia de generare succesorilor

    def genereaza_posibile_capturi(solutii, tabla_de_joc, configuratie_curenta, solutie_actuala):
        """
        Recrusivitate
        """
        if solutie_actuala != []: # adauga la lista noile noduri
            solutii.append(solutie_actuala)

        for alt_nod in range(len(tabla_de_joc.noduri)):
            if verificare_adaugare(solutie_actuala, tabla_de_joc, configuratie_curenta, alt_nod):
                solutie_noua = solutie_actuala.copy()
                solutie_noua.append(alt_nod)

                # apel recrusiv
                Vulpe.genereaza_posibile_capturi(solutii, tabla_de_joc, configuratie_curenta, solutie_noua)

💹 Functie de testare a validitatii unei mutari (folosita si pentru a verifica mutarea utilizatorului)

def mutare_valida(tabla_de_joc, configuratie_curenta, nr_nod_curent, nr_alt_nod):
    lista_muchii = tabla_de_joc.muchii[nr_nod_curent]

    if nr_alt_nod in lista_muchii:
        if (nr_alt_nod not in configuratie_curenta.gaste) and (nr_alt_nod != configuratie_curenta.vulpe):
            return True

    return False

💹 Functia de stabilire a castigatorului

 def gaseste_castigator(self, tabla_de_joc):
        # calculez miscarile posibile ale vulpii
        configurari_vulpe = Vulpe.configurari_posibile(tabla_de_joc, self)

        if len(configurari_vulpe) == 0:  # daca vulpea nu mai are miscari, gastele castiga
            return "castiga gastele"

        if len(self.gaste) <= 4:  # daca gastele raman mai putine de 4 atunci vulpea castiga
            return "castiga vulpea"

        return "configuratie nefinala"  # nu am configuratie finala

💹 Doua moduri diferite de estimare a scorului (pentru stari care nu sunt inca finale)

def estimare_gaste(tabla_de_joc, configuratie_curenta, dummy): # in favoarea gastelor
def estimare_vulpe(tabla_de_joc, configuratie_anterioara, configuratie_curenta): # in favoarea vulpii

💹 Comentarii

💹 Explicarea pe scurt a fiecarei functii si a parametrilor: Python DocStrings

💹 Ordonarea succesorilor înainte de expandare (bazat pe estimare) astfel încât alpha-beta să taie cât mai mult din arbore.

configuratii_posibile = sorted(configuratii_posibile, key=lambda t: functie_estimare(tabla_de_joc, t, t))

💹 Algoritmului de generare a mutarilor

Fiecare din cele 4 clase care apeleaza algoritmii de Min-Max sau Alpha-Beta, au o metoda prin care returneaza configuratiile urmatoare posibile generate in urma aplicarii unuia din cei 2 algoritmi.

 def muta(self, tabla_de_joc, configuratie_curenta)

💹 Estimarea scorului

Se face prin 2 metode.

🦊 Clasa Vulpe

    def estimare_vulpe(tabla_de_joc, configuratie_anterioara, configuratie_curenta):
        return len(configuratie_anterioara.gaste) - len(configuratie_curenta.gaste)

Returneaza diferenta care reprezinta cate gaste a mancat vulpea de la ultima mutare in joc.

🦆 Clasa Gaste

    def estimare_gaste(tabla_de_joc, configuratie_curenta, dummy):
        nr_gaste = 0

        for nr_alt_nod in tabla_de_joc.muchii[configuratie_curenta.vulpe]:
            if nr_alt_nod in configuratie_curenta.gaste:
                nr_gaste += 1

        return nr_gaste

Returneaza nr de gaste care inconjoara vulpea in configuratia curenta.