Beispiel #1
0
        public int heuristic_crni(int dubina)
        {
            Koordinate beliKralj = NadjiFiguru(Tip.BeliKralj, this);
            Koordinate beliTop = NadjiFiguru(Tip.BeliTop, this);
            Koordinate crniKralj = NadjiFiguru(Tip.CrniKralj, this);
            double     bonus = 0, penalty = 0;

            if (DaLiJeMat())
            {
                penalty += 1000 / Math.Abs(dubina) + 1;
            }
            else if (DaLiJePat())
            {
                bonus += 1000 / Math.Abs(dubina) + 1;
            }
            if (DalijeNapadnut(Tip.CrniKralj))
            {
                penalty += 500;
            }
            if (ChebyshevDistance(crniKralj.x, crniKralj.y, beliTop.x, beliTop.y) == 1)
            {
                bonus += 250;
            }
            if (ChebyshevDistance(crniKralj.x, crniKralj.y, beliKralj.x, beliKralj.y) == 1)
            {
                bonus += 10;
            }
            int    brojPoteza = FinalnaListaMogucihPoteza(this, new Potez(crniKralj.x, crniKralj.y)).Count;
            int    CK_CMD     = CMD[crniKralj.x, crniKralj.y];
            double BT_CK_diff = Math.Abs(Math.Abs(crniKralj.y - beliTop.y) - Math.Abs(crniKralj.x - beliTop.x));
            double vrati      = (-9.3 * BT_CK_diff - 5.7 * CK_CMD + (10 * brojPoteza / (CK_CMD + 1)) + penalty - bonus) * 200;

            return((int)vrati);
        }
Beispiel #2
0
        public bool DaLiJePat()
        {
            Koordinate crniKralj = NadjiFiguru(Tip.CrniKralj, this);

            if (FinalnaListaMogucihPoteza(this, new Potez(crniKralj.x, crniKralj.y)).Count == 0)
            {
                return(true);
            }
            return(false);
        }
Beispiel #3
0
        /// <summary>
        /// Da li je kraj igre
        /// </summary>
        /// <returns></returns>
        public bool DaLiJeKraj()
        {
            Koordinate crniKralj = NadjiFiguru(Tip.CrniKralj, this);

            if (FinalnaListaMogucihPoteza(this, new Potez(crniKralj.x, crniKralj.y)).Count == 0)
            {
                if (!DalijeNapadnut(Tip.BeliTop))
                {
                    return(true);
                }
            }
            return(false);
        }
Beispiel #4
0
        /// <summary>
        /// Vraca koordinate jedne trazene figure
        /// </summary>
        /// <param name="tip"></param>
        /// <param name="ctx"></param>
        /// <returns></returns>
        public Koordinate NadjiFiguru(Tip tip, Context ctx)
        {
            Koordinate retVal = new Koordinate(-10, -10);

            for (int i = 0; i < 8; i++)
            {
                for (int j = 0; j < 8; j++)
                {
                    if (ctx.Stanje.matrica[i, j] == (int)tip)
                    {
                        retVal = new Koordinate(i, j);
                    }
                }
            }

            return(retVal);
        }
Beispiel #5
0
        private void btnIgraj_Click(object sender, EventArgs e)
        {
            if (kontekst.naPotezu == (int)Igra.Beli)
            {
                Potez p = kontekst.AlphaBeta(kontekst, 4, int.MinValue, int.MaxValue);
                lblPotezi.Text = Context.i.ToString();
                Context.i      = 0;
                Koordinate mestoFigureKojaIgra = kontekst.NadjiFiguru(p.tipFigure, kontekst);
                Koordinate beliTop             = kontekst.NadjiFiguru(Tip.BeliTop, kontekst);
                Context    context             = new Context(kontekst);
                context.UradiPotez(new Potez(mestoFigureKojaIgra.x, mestoFigureKojaIgra.y), p);
                if (!context.DalijeNapadnut(Tip.BeliTop))
                {
                    kontekst.UradiPotez(new Potez(mestoFigureKojaIgra.x, mestoFigureKojaIgra.y), p);
                }
                else
                {
                    List <Potez> listaFigureKojaIgra = kontekst.FinalnaListaMogucihPoteza(kontekst, new Potez(beliTop.x, beliTop.y));
                    if (listaFigureKojaIgra.Contains(new Potez(beliTop.x, 0)))
                    {
                        kontekst.UradiPotez(new Potez(beliTop.x, beliTop.y), new Potez(beliTop.x, 0));
                    }
                    else
                    {
                        kontekst.UradiPotez(new Potez(beliTop.x, beliTop.y), new Potez(beliTop.x, 7));
                    }
                }
                Refresh();
                label1.Text = kontekst.DalijeNapadnut(Tip.CrniKralj).ToString();
                label3.Text = kontekst.DalijeNapadnut(Tip.BeliTop).ToString();

                if (kontekst.DaLiJeKraj())
                {
                    if (kontekst.DaLiJeMat())
                    {
                        MessageBox.Show("MAT!");
                    }
                    else if (kontekst.DaLiJePat())
                    {
                        MessageBox.Show("PAT!");
                    }
                    kontekst.Seralization(Context.transposTable);
                    MessageBox.Show("Serijalizacija transpozicione tabele uspesna!");
                }
            }
            else
            {
                Context.i = 0;
                Potez p = kontekst.AlphaBeta(kontekst, 4, int.MinValue, int.MaxValue);
                lblPotezi.Text = Context.i.ToString();
                Koordinate mestoFigureKojaIgra = kontekst.NadjiFiguru(p.tipFigure, kontekst);
                kontekst.UradiPotez(new Potez(mestoFigureKojaIgra.x, mestoFigureKojaIgra.y), p);
                Refresh();
                label1.Text = kontekst.DalijeNapadnut(Tip.CrniKralj).ToString();
                label3.Text = kontekst.DalijeNapadnut(Tip.BeliTop).ToString();
                if (kontekst.DaLiJeKraj())
                {
                    if (kontekst.DaLiJeMat())
                    {
                        MessageBox.Show("MAT!");
                    }
                    else if (kontekst.DaLiJePat())
                    {
                        MessageBox.Show("PAT!");
                    }
                    kontekst.Seralization(Context.transposTable);
                    MessageBox.Show("Serijalizacija transpozicione tabele uspesna!");
                }
            }
        }
Beispiel #6
0
        /// <summary>
        /// Proverava da li je unesen Tip figure napadnut
        /// </summary>
        /// <returns></returns>
        public bool DalijeNapadnut(Tip tip)
        {
            Koordinate koordinate = NadjiFiguru(tip, this);
            int        x          = koordinate.x;
            int        y          = koordinate.y;

            if (Stanje.matrica[x, y] == 1)//provera za crnog kralja
            {
                Koordinate   beliKralj      = NadjiFiguru(Tip.BeliKralj, this);
                Koordinate   beliTop        = NadjiFiguru(Tip.BeliTop, this);
                List <Potez> listaBelogTopa = FinalnaListaMogucihPoteza(this, new Potez(beliTop.x, beliTop.y));
                int          dwkbk          = ChebyshevDistance(beliKralj.x, beliKralj.y, koordinate.x, koordinate.y);
                int          dwrbk          = ChebyshevDistance(beliTop.x, beliTop.y, koordinate.x, koordinate.y);
                if (koordinate.x == beliTop.x)
                {
                    if (koordinate.x != beliKralj.x)
                    {
                        return(true);
                    }
                    else
                    {
                        if ((beliKralj.y < koordinate.y && koordinate.y < beliTop.y) || (beliTop.y < koordinate.y && koordinate.y < beliKralj.y))
                        {
                            return(true);
                        }
                        else
                        {
                            if (dwrbk < dwkbk)
                            {
                                return(true);
                            }
                        }
                        return(false);
                    }
                }
                if (koordinate.y == beliTop.y)
                {
                    if (koordinate.y != beliKralj.y)
                    {
                        return(true);
                    }
                    else
                    {
                        if ((beliKralj.x < koordinate.x && koordinate.x < beliTop.x) || (beliTop.x < koordinate.x && koordinate.x < beliKralj.x))
                        {
                            return(true);
                        }
                        else
                        {
                            if (dwrbk < dwkbk)
                            {
                                return(true);
                            }
                        }
                        return(false);
                    }
                }
                if (ChebyshevDistance(beliKralj.x, beliKralj.y, koordinate.x, koordinate.y) == 1) //ovo nikad nece da se bude true
                {
                    return(true);
                }
            }
            else //provera  belog topa
            {
                Koordinate crniKralj = NadjiFiguru(Tip.CrniKralj, this);
                Koordinate beliKralj = NadjiFiguru(Tip.BeliKralj, this);
                if (ChebyshevDistance(crniKralj.x, crniKralj.y, koordinate.x, koordinate.y) == 1)
                {
                    if (ChebyshevDistance(beliKralj.x, beliKralj.y, koordinate.x, koordinate.y) != 1)
                    {
                        return(true);
                    }
                }
            }
            return(false);
        }
Beispiel #7
0
        public Potez AlphaBeta(Context ctx, int depth, int alpha, int beta)
        {
            Potez najbolji = new Potez(); //ovaj potez vraca funkcija
            Potez pom      = new Potez();

            Context.i++;
            if (depth == 0 || ctx.DaLiJeKraj())
            {
                najbolji.Value = ctx.Evaluate(depth - 4);
                return(najbolji);
            }
            Potez        trenutnoMesto;
            Koordinate   trenutneKoordinate;
            List <Potez> listaPoteza = new List <Potez>();
            List <Potez> listaKralja = new List <Potez>();
            List <Potez> listaTopa   = new List <Potez>();
            Koordinate   beliKralj   = NadjiFiguru(Tip.BeliKralj, ctx);
            Koordinate   beliTop     = NadjiFiguru(Tip.BeliTop, ctx);
            Koordinate   crniKralj   = NadjiFiguru(Tip.CrniKralj, ctx);

            if (ctx.naPotezu == (int)Igra.Beli)
            {
                listaKralja = FinalnaListaMogucihPoteza(ctx, new Potez(beliKralj.x, beliKralj.y));

                listaTopa = FinalnaListaMogucihPoteza(ctx, new Potez(beliTop.x, beliTop.y));
                listaPoteza.AddRange(listaTopa);
                listaPoteza.AddRange(listaKralja);
            }
            else
            {
                listaPoteza = FinalnaListaMogucihPoteza(ctx, new Potez(crniKralj.x, crniKralj.y));
            }
            int v;

            if (ctx.naPotezu == (int)Igra.Beli)
            {
                v = int.MinValue;
                foreach (Potez pot in listaPoteza)
                {
                    trenutneKoordinate = NadjiFiguru(pot.tipFigure, ctx);
                    trenutnoMesto      = new Potez(trenutneKoordinate.x, trenutneKoordinate.y);
                    Context zaProsledjivanje = new Context(ctx);
                    zaProsledjivanje.UradiPotez(trenutnoMesto, pot);
                    if (transposTable.Contains(zaProsledjivanje.hashFunction() + zaProsledjivanje.hash2() + zaProsledjivanje.GetHashCode()))
                    {
                        int hash = (int)transposTable[zaProsledjivanje.hashFunction() + zaProsledjivanje.hash2() + zaProsledjivanje.GetHashCode()];
                        najbolji.Value = hash;
                        return(najbolji);
                    }
                    pom = AlphaBeta(zaProsledjivanje, depth - 1, alpha, beta);
                    if (v < pom.Value)
                    {
                        v              = pom.Value;
                        najbolji       = pot;
                        najbolji.Value = v;
                        alpha          = Math.Max(alpha, v);
                    }
                    if (beta <= alpha)
                    {
                        break;
                    }
                }
                if (!transposTable.Contains(ctx.hashFunction() + ctx.hash2() + ctx.GetHashCode()))
                {
                    transposTable.Add(ctx.hashFunction() + ctx.hash2() + ctx.GetHashCode(), najbolji.Value);
                }
                return(najbolji);
            }
            else
            {
                v = int.MaxValue;
                foreach (Potez pot in listaPoteza)
                {
                    trenutneKoordinate = NadjiFiguru(Tip.CrniKralj, ctx);
                    trenutnoMesto      = new Potez(trenutneKoordinate.x, trenutneKoordinate.y);
                    Context zaProsledjivanje = new Context(ctx);
                    zaProsledjivanje.UradiPotez(trenutnoMesto, pot);
                    if (transposTable.Contains(zaProsledjivanje.hashFunction() + zaProsledjivanje.hash2() + zaProsledjivanje.GetHashCode()))
                    {
                        int hash = (int)transposTable[zaProsledjivanje.hashFunction() + zaProsledjivanje.hash2() + zaProsledjivanje.GetHashCode()];
                        najbolji.Value = hash;
                        return(najbolji);
                    }
                    pom = AlphaBeta(zaProsledjivanje, depth - 1, alpha, beta);
                    if (v > pom.Value)
                    {
                        v              = pom.Value;
                        najbolji       = pot;
                        najbolji.Value = v;
                        beta           = Math.Min(beta, v);
                    }
                    if (beta <= alpha)
                    {
                        break;
                    }
                }
                if (!transposTable.Contains(ctx.hashFunction() + ctx.hash2() + ctx.GetHashCode()))
                {
                    transposTable.Add(ctx.hashFunction() + ctx.hash2() + ctx.GetHashCode(), najbolji.Value);
                }
                return(najbolji);
            }
        }
Beispiel #8
0
        /// <summary>
        ///  Kreira konacnu listu mogucih poteza koje figura moze odigradi
        /// </summary>
        /// <param name="ctx"></param>
        /// <param name="trenutneKoordinate"></param>
        /// <returns></returns>
        public List <Potez> FinalnaListaMogucihPoteza(Context ctx, Potez trenutneKoordinate)
        {
            List <Potez> listaZaVracanje          = new List <Potez>();
            List <Potez> listaNedozvoljenihPoteza = new List <Potez>();
            Tip          figura    = (Tip)ctx.Stanje.matrica[trenutneKoordinate.x, trenutneKoordinate.y];
            Koordinate   beliKralj = NadjiFiguru(Tip.BeliKralj, ctx);
            Koordinate   beliTop   = NadjiFiguru(Tip.BeliTop, ctx);
            Koordinate   crniKralj = NadjiFiguru(Tip.CrniKralj, ctx);

            //kreira listu svih poteza za figuru
            listaZaVracanje = ctx.listaMogucihPoteza(figura, trenutneKoordinate);
            switch (figura)
            {
            case Tip.CrniKralj:         //treba da nadje polja koja napadaju beli kralj i top

                List <Potez> listaNedozvoljenihPotezaKralj = new List <Potez>();
                List <Potez> listaNedozvoljenihPotezaTop   = new List <Potez>();

                listaNedozvoljenihPotezaKralj = listaMogucihPoteza(Tip.BeliKralj, new Potez(beliKralj.x, beliKralj.y));
                listaNedozvoljenihPotezaTop   = listaMogucihPoteza(Tip.BeliTop, new Potez(beliTop.x, beliTop.y));

                if (beliKralj.x == beliTop.x || beliKralj.y == beliTop.y)
                {
                    List <Potez> blokiraniPotezi = new List <Potez>();

                    if (beliKralj.x == beliTop.x)
                    {
                        if (beliKralj.y < beliTop.y)
                        {
                            for (int i = 0; i <= beliKralj.y; blokiraniPotezi.Add(new Potez(beliKralj.x, i++)))
                            {
                                ;
                            }
                        }
                        else
                        {
                            for (int i = 7; i >= beliKralj.y; blokiraniPotezi.Add(new Potez(beliKralj.x, i--)))
                            {
                                ;
                            }
                        }
                    }
                    else if (beliKralj.y == beliTop.y)
                    {
                        if (beliKralj.x < beliTop.x)
                        {
                            for (int i = 0; i <= beliKralj.x; blokiraniPotezi.Add(new Potez(i++, beliKralj.y)))
                            {
                                ;
                            }
                        }
                        else
                        {
                            for (int i = 7; i >= beliKralj.x; blokiraniPotezi.Add(new Potez(i--, beliKralj.y)))
                            {
                                ;
                            }
                        }
                    }

                    listaNedozvoljenihPotezaTop = listaNedozvoljenihPotezaTop.Except(blokiraniPotezi).ToList();
                }

                listaNedozvoljenihPoteza.AddRange(listaNedozvoljenihPotezaKralj);
                listaNedozvoljenihPoteza.AddRange(listaNedozvoljenihPotezaTop);

                break;

            case Tip.BeliKralj:         //treba da nadje polja koja napada crni kralj

                listaNedozvoljenihPoteza = listaMogucihPoteza(Tip.CrniKralj, new Potez(crniKralj.x, crniKralj.y));

                break;

            case Tip.BeliTop:           //treba da nadje polja koja napada crni kralj, a ne stiti beli kralj
                                        //i da mu onemoguci da preskace belog kralja

                listaNedozvoljenihPoteza = listaMogucihPoteza(Tip.CrniKralj, new Potez(crniKralj.x, crniKralj.y));
                List <Potez> kretanjeBelogKralja = listaMogucihPoteza(Tip.BeliKralj, new Potez(beliKralj.x, beliKralj.y));

                listaNedozvoljenihPoteza = listaNedozvoljenihPoteza.Except(kretanjeBelogKralja).ToList();

                //proverava da li beli kralj blokira kretanje topa
                if (beliKralj.x == beliTop.x)
                {
                    if (beliKralj.y < beliTop.y)
                    {
                        for (int i = 0; i <= beliKralj.y; listaNedozvoljenihPoteza.Add(new Potez(beliKralj.x, i++)))
                        {
                            ;
                        }
                    }
                    else
                    {
                        for (int i = 7; i >= beliKralj.y; listaNedozvoljenihPoteza.Add(new Potez(beliKralj.x, i--)))
                        {
                            ;
                        }
                    }
                }
                else if (beliKralj.y == beliTop.y)
                {
                    if (beliKralj.x < beliTop.x)
                    {
                        for (int i = 0; i <= beliKralj.x; listaNedozvoljenihPoteza.Add(new Potez(i++, beliKralj.y)))
                        {
                            ;
                        }
                    }
                    else
                    {
                        for (int i = 7; i >= beliKralj.x; listaNedozvoljenihPoteza.Add(new Potez(i--, beliKralj.y)))
                        {
                            ;
                        }
                    }
                }

                break;
            }

            //iz liste mogucih poteza brise sve nedozvoljene poteze
            //u klasi potez funkcije Equals i GetHashCode su override-ovane da bi Except mogao da poredi poteze
            listaZaVracanje = listaZaVracanje.Except(listaNedozvoljenihPoteza).ToList();

            return(listaZaVracanje);
        }