コード例 #1
0
    //lancia un torneo su population; alla fine di tutto, ordina i pesi in population in base al migliore risultato del torneo
    public SortedList <WeightScore, int> LaunchTournament(SortedList <WeightScore, int> population, List <WeightsForBoardEval> testPopulation)
    {
        SortedList <WeightScore, int> newPopulation = new SortedList <WeightScore, int>();
        Dictionary <WeightScore, int> scores        = new Dictionary <WeightScore, int>();

        for (int i = 0; i < population.Count; i++)
        {
            WeightScore ws1 = population.Keys[i];
            for (int j = 0; j < testPopulation.Count; j++)
            {
                WeightsForBoardEval testPlayer        = testPopulation[j];
                AlphaBeta           ws1AsGoose        = new AlphaBeta(PawnType.Goose, 3, ws1.weights, false);
                AlphaBeta           ws1AsFox          = new AlphaBeta(PawnType.Fox, 3, ws1.weights, false);
                AlphaBeta           ws2AsGoose        = new AlphaBeta(PawnType.Goose, 3, testPlayer, false);
                AlphaBeta           ws2AsFox          = new AlphaBeta(PawnType.Fox, 3, testPlayer, false);
                PairOfScores        pairOfScoresGoose = MatchTwoAi(ws1AsGoose, ws2AsFox, 1, i, j);
                PairOfScores        pairOfScoresFox   = MatchTwoAi(ws1AsFox, ws2AsGoose, 1, i, j);
                if (!scores.ContainsKey(ws1))
                {
                    scores[ws1] = 0;
                }
                scores[ws1] += pairOfScoresGoose.first;
                scores[ws1] += pairOfScoresFox.first;
            }
            WeightScore ws = new WeightScore(ws1.weights, scores[ws1]);
            newPopulation.Add(ws, scores[ws1]);
        }
        return(newPopulation);
    }
コード例 #2
0
 public AlphaBeta(PawnType aiPlayer, int maxPly, WeightsForBoardEval weights, bool random)
 {
     this.aiPlayer = aiPlayer;
     this.maxPly   = maxPly;
     this.weights  = weights;
     this.random   = random;
 }
コード例 #3
0
ファイル: Game.cs プロジェクト: giuliapetenazzi/FoxAndGeeseAI
        //valuta la qualità della board
        public int EvaluateBoard(PawnType aiPlayer, WeightsForBoardEval weights)
        {
            //TODO GIULIA
            //return winner == player ? 1 : -1;
            int score = 0;
            //winningState
            int signOfPlayer = aiPlayer == PawnType.Goose ? 1 : -1;

            if (IsGooseWinner())
            {
                return(weights.wWinningState * signOfPlayer);
            }
            if (IsFoxWinner())
            {
                return(weights.wWinningState * signOfPlayer * -1);
            }
            //AIplayer == oca e vince oca torna +200
            //AIplayer == oca e vince volpe torna -200
            //AIplayer == volpe e vince volpe torna +200
            //AIplayer == volpe e vince oca -200
            // else non ha vinto nessuno
            //Console.WriteLine("game weights = " + weights);
            //gooseNumber
            score += GetGooseNumber() * weights.weightDict["wGooseNumber"];
            //aheadGooseNumber
            score += GetAheadGooseNumber() * weights.weightDict["wAheadGooseNumber"];
            //foxEatingMoves
            Vector2 foxCoordinates = FindFoxCoordinates();
            int     rFox           = (int)foxCoordinates.x;
            int     cFox           = (int)foxCoordinates.y;

            //cambio
            score += IACalculateFoxValidEatingMoves(rFox, cFox).Count() * weights.weightDict["wFoxEatingMoves"];
            //foxMoves
            //cambio
            score += IACalculateFoxValidMoves(rFox, cFox).Count() * weights.weightDict["wFoxMoves"];
            //freedomness
            //cambio
            score += (int)Math.Round(GetGooseFreedomness() * weights.weightDict["wGooseFreedomness"], 0);
            //interness
            //cambio
            score += GetInterness(rFox, cFox) * weights.weightDict["wInterness"];
            //externess
            score += GetExterness(rFox, cFox) * weights.weightDict["wExterness"];
            //Console.WriteLine("score evaluated: " + score * signOfPlayer);
            return(score * signOfPlayer);
        }
コード例 #4
0
    public void StartTest()
    {
        MatchAlgo   matchAlgo   = new MatchAlgo();
        GeneticAlgo geneticAlgo = new GeneticAlgo();

        System.Random rand = new System.Random();
        List <WeightsForBoardEval> weights = new List <WeightsForBoardEval>();

        for (int i = 0; i < 50; i++)
        {
            WeightsForBoardEval w = new WeightsForBoardEval(rand);
            weights.Add(w);
            Console.WriteLine("pesInizRand = " + w);
        }

        SortedList <WeightScore, int> scoreMap = new SortedList <WeightScore, int>();

        //per ogni peso = giocatore, fa giocare 3 match come oca e 3 match come volpe al giocatore contro un giocatore casuale
        for (int i = 0; i < weights.Count; i++)
        {
            int score = 0;
            WeightsForBoardEval weight        = weights[i];
            AlphaBeta           playerAsFox   = new AlphaBeta(PawnType.Fox, 3, weight, false);
            AlphaBeta           playerAsGoose = new AlphaBeta(PawnType.Goose, 3, weight, false);
            score  = matchAlgo.MatchTwoAi(playerAsFox, null, 3, -1, -1).first;
            score += matchAlgo.MatchTwoAi(playerAsGoose, null, 3, -1, -1).first;
            WeightScore ws = new WeightScore(weight, score);
            scoreMap.Add(ws, score);
        }

        Console.WriteLine("aiTester prima di evoluzione");
        // evolve 50 volte la popolazione
        for (int i = 0; i < 50; i++)
        {
            Console.WriteLine("\n \n \n \n inizio evoluzione generazione " + i);
            scoreMap = geneticAlgo.Evolve(scoreMap, 0.3, 0.1, 0.01);
        }
        Console.WriteLine("best weights " + scoreMap.Keys[0]);
        Console.WriteLine("finito completamente aiTester ore: " + DateTime.Now.ToString("h:mm:ss tt"));
        Console.ReadKey();
    }
コード例 #5
0
    // ritorna un WeightsForBoardEval nato da male e female con operazioni bitwise
    private WeightsForBoardEval CrossoverAndMutate(WeightsForBoardEval male, WeightsForBoardEval female, double mutationProbability)
    {
        Console.WriteLine("genetic algo crossover");
        Dictionary <String, BitArray> bitFather = new Dictionary <String, BitArray>();
        Dictionary <String, BitArray> bitMother = new Dictionary <String, BitArray>();
        Dictionary <String, BitArray> bitChild  = new Dictionary <String, BitArray>();

        foreach (String key in male.weightDict.Keys)
        {
            byte[] byteFather = BitConverter.GetBytes(male.weightDict[key]);
            byte[] byteMother = BitConverter.GetBytes(female.weightDict[key]);
            bitFather[key] = new BitArray(byteFather);
            bitMother[key] = new BitArray(byteMother);
            //crossover
            bitChild[key] = Mix(bitFather[key], bitMother[key]);
            //mutazione
            System.Random random = new System.Random();
            double        prob   = random.NextDouble();
            if (prob < mutationProbability)
            {
                bitChild[key] = Mutate(bitChild[key]);
            }
        }

        WeightsForBoardEval child = new WeightsForBoardEval(
            GetIntFromBitArray(bitChild["wGooseNumber"]),
            GetIntFromBitArray(bitChild["wAheadGooseNumber"]),
            GetIntFromBitArray(bitChild["wFoxEatingMoves"]),
            GetIntFromBitArray(bitChild["wFoxMoves"]),
            GetIntFromBitArray(bitChild["wGooseFreedomness"]),
            GetIntFromBitArray(bitChild["wInterness"]),
            GetIntFromBitArray(bitChild["wExterness"])
            );

        return(child);
    }
コード例 #6
0
    }                                  //punteggio di vittorie

    public WeightScore(WeightsForBoardEval weights, int score)
    {
        this.weights = weights;
        this.score   = score;
    }
コード例 #7
0
    public SortedList <WeightScore, int> Evolve(SortedList <WeightScore, int> population, double retain, double randomSelect, double mutate)
    {
        Console.WriteLine("start genetic algo evolve");

        foreach (var key in population.Keys)
        {
            Console.WriteLine(key);
        }
        System.Random rand        = new System.Random();
        int           retainIndex = (int)(population.Count * retain);

        Console.WriteLine("population size = " + population.Count + " " + retain + " " + randomSelect + " " + mutate);
        Console.WriteLine("retain tengo " + retainIndex + " soggetti");
        SortedList <WeightScore, int> parents = new SortedList <WeightScore, int>();

        var iter = population.GetEnumerator();

        iter.MoveNext();
        for (int i = 0; i < retainIndex; i++)
        {
            parents[iter.Current.Key] = iter.Current.Value;
            iter.MoveNext();
        }

        //aggiunge altri soggetti con una percentuale di aggiunta pari a randomSelect
        while (iter.MoveNext())
        {
            if (randomSelect > rand.NextDouble())
            {
                var ws = iter.Current;
                parents[ws.Key] = ws.Value;
            }
        }

        foreach (var key in parents.Keys)
        {
            Console.WriteLine(key);
        }
        int parentsCount       = parents.Count;
        int childrenToGenerate = population.Count - parentsCount;         //quanti figli devo generare per ritornare ad avere una popolazione completa
        int generatedChildren  = 0;

        Console.WriteLine("fine evolve" + population.Count + " " + parents.Count + " " + childrenToGenerate);

        //crossover
        while (parents.Count < population.Count - 2)
        {
            //Console.WriteLine("parent count= " + parents.Count + " pop count = " + population.Count);
            //Console.WriteLine("GeneticAlgo genero figli");

            int firstN  = rand.Next(parentsCount);
            int secondN = rand.Next(parentsCount);
            WeightsForBoardEval male   = parents.Keys[firstN].weights;
            WeightsForBoardEval female = parents.Keys[secondN].weights;
            if (!male.Equals(female))
            {
                WeightsForBoardEval child = CrossoverAndMutate(male, female, mutate);
                WeightScore         ws    = new WeightScore(child, 0);
                parents[ws] = 0;
                generatedChildren++;
            }
        }
        WeightScore ws1 = new WeightScore(new WeightsForBoardEval(rand), 0);
        WeightScore ws2 = new WeightScore(new WeightsForBoardEval(rand), 0);

        parents[ws1] = 0;
        parents[ws2] = 0;
        List <WeightsForBoardEval> testPopulation = new List <WeightsForBoardEval>();

        testPopulation.Add(new WeightsForBoardEval(1, 0, 0, 0, 0, 0, 0));
        testPopulation.Add(new WeightsForBoardEval(2, 2, -2, -2, -1, -1, 0));
        return(new MatchAlgo().LaunchTournament(parents, testPopulation));        //lancia un torneo sulla popolazione e ritorna la popolazione con gli score aggiornati
    }