• Здраво и добредојдовте на форумот на IT.mk.

    Доколку сеуште не сте дел од најголемата заедница на ИТ професионалци и ентузијасти во Македонија, можете бесплатно да се - процесот нема да ви одземе повеќе од 2-3 минути, а за полесна регистрација овозможивме и регистрирање со Facebook и Steam.

Шах во С++

  • Ја почнал/а темата
  • #1

maximilian

Gaining Experience
26 март 2008
1,064
74
Значи, на средината на семестаров започнав едно проектче, но заради обврските на факултетот го баталив и го немам чепнато од тогаш, па сакав да чујам идеи околу ова. Значи, почнав да пишувам програма за игра шах, но само со 2 играчи, не компјутерот да развива стратегии. Е сеа, заради тоа шо имав малце познавања од можностите на С++ почнав да го правам само со функции и матрици. Прво да ви објаснам како ми е замислата:

Знали, шах таблата е една матрица од тип 8 х 8, и секое поле си е означено како шо треба (А,В,...,Н ; 1,2,...8). Секое празно поле на шахот има вредност 0 (т.е. тоа е поле на матрицата). Фигурите ги имаат следните вредности на матрицата: белите/црните пиони-1/11, белите/црните топови-2/12, белите/црните коњи-3/13, белите/црните ловци-4/14, белата/црната кралица-5/15, белиот/црниот крал-6/16. Се воведува поле, (А,В,...,Н ; 1,2,...8), т.е. се маркира фигурата со која сакате да играте. Доколку тоа поле на матрицата има вредност различна од 0, продолжувате. Значи, селектирате каде сака да оди. И се мести. Сега за сега, направив да бидат подвижни само пионите, и пак не ми се целосно доработени. Секоја фигура си има дефиниција каде може да се движи. Ова ми е всушност продолжение од едно домашно, каде за воведено поле, и воведена фигура програмата кажува каде е можно да се движи фигурата. Значи, замислата за можните комбинации ми е, на секое поле a[j]каде што може да се движи фигурата, се додава вредност a[j]+20. Се даваат условите каде да се додаде вредност a[j]+20. Од кога ќе се избери каде да се движи, програмата проверува дали полето има вредност >20. Ако има, на првичното поле се става вредност 0,а за сите останати има проверка ако се >20, се пражи a[j]-20, а на второто избрано поле се додава вредноста на првото избрано поле. Е сеа, има функции player1 и player2, но за да се менуваат наизменично, цело време се повикуваат рекурсивно, што не е добро решение,т.е. колку повеќе играш, толку повеќе меморија се трупа. Имав и на друго место истиот услов со +20, само наместо тоа, додадов вредност 41, и си одат истите проверки. Кодов не ми е ни 20% готов, ама чисто ако сакате видете го и кажете ми мислење околу ова, мислам дека би можело да се најде пооптимално решение, зашто стварно сакам да го направам кога ќе имам време (нека поминат испитиве :lut2:).
Заради тоа шо ова за мене е малце и комплицирано и најтешко нешто на кое сум се нафатил до сега да го правам, извинете ако сум направил некаков пропуст, не сум дообјаснил нешто, и сл работи, битно ми е, дали мислете дека има друго решение за проблемов, т.е. да се реши на друг начин. За вака знам да го доправам, но ќе ми одземе многу време, а мислам дека решениево не е најоптималното.
 
  • Ја почнал/а темата
  • #2

maximilian

Gaining Experience
26 март 2008
1,064
74
Кодот е во наредните два поста зашто е голем за еден :)

Код:
#include<iostream>
#include<stdlib.h>
#include<cmath>
#include<iomanip>

using namespace std;

const int n=8;

void player1(int a[][n]);

void player2(int a[][n]);

void pion (int k, int l, int a[][n]);

void top (int k, int l, int a[][n]);

void konj (int k, int l, int a[][n]);

void lanfer (int k, int l, int a[][n]);

void kralica (int k, int l, int a[][n]);

void kral (int k, int l, int a[][n]);

void pion1 (int k, int l, int a[][n]);

int main()
{
    int a[n][n];
    for (int i=0; i<n; i++)
        for (int j=0; j<n; j++)
            {
                 a[i][j]=0;
                 if (i==6)
                    for (int i1=0; i1<n; i1++)
                        a[i][j]=1;
                 if (i==7)
                    {
                          if ((j==0) || (j==7))
                             a[i][j]=2;
                          if ((j==1) || (j==6))
                             a[i][j]=3;
                          if ((j==2) || (j==5))
                             a[i][j]=4;
                          if (j==3)
                             a[i][j]=5;
                          if (j==4)
                             a[i][j]=6;
                    }
                 if (i==1)
                    for (int i1=0; i1<n; i1++)
                        a[i][j]=11;
                 if (i==0)
                    {
                          if ((j==0) || (j==7))
                             a[i][j]=12;
                          if ((j==1) || (j==6))
                             a[i][j]=13;
                          if ((j==2) || (j==5))
                             a[i][j]=14;
                          if (j==3)
                             a[i][j]=15;
                          if (j==4)
                             a[i][j]=16;
                    }
            }
     for (int i=0; i<n; i++)
         {
              for (int j=0; j<n; j++)
                  {
                       if (j==0)
                          cout << n-i << "|";
                       cout << "  " << setw(2) << a[i][j];
                  }
              
              cout << endl << endl;
         }
    player1(a);
    player2(a);
    system ("pause");
    return 0;
}
void player1(int a[][n])
{    
    cout <<"Player 1" << endl;
    cout << "Vnesi pole so i[A...H], j= [1..8]" << endl;
    cout << "i=";
    int k,l;
    char z;
    cin >> z;
    int inte=int(z);
    if (!cin || (inte<65) || (inte>72))
    {
             cout <<"ERROR. Bad input" << endl;
             system ("pause");
             player1(a);
    }
    l=inte-65;
    cout << "j=";
    int l1;
    cin >> l1;
    if (!cin || l1<1 || l1>8)
    {
             cout <<"ERROR. Bad input" << endl;
             system ("pause");
             player1(a);
    }
    k=fabs(l1-8);
    int pole;
    for (int i=0; i<n; i++)
        for (int j=0; j<n; j++)
            if ((i==k) && (j==l))
               pole=a[i][j];
    cout << "Figurata e " << pole << endl;
    switch (pole)
    {
           case 1: pion(k,l,a); break;
           case 2: top(k,l,a); break;
           case 3: konj(k,l,a); break;
           case 4: lanfer (k,l,a); break;
           case 5: kralica (k,l,a); break;
           case 6: kral (k,l,a); break;
    }
    cout << endl;
    player2(a);
}

void player2(int a[][n])
{
    cout << "Player 2" << endl;
    cout << "Vnesi pole so i[A...H], j= [1..8]" << endl;
    cout << "i=";
    int k,l,inte;
    char z;
    cin >> z;
    inte=int(z);
    if (!cin || (inte<65) || (inte>72))
    {
             cout <<"ERROR. Bad input" << endl;
             system ("pause");
             player2(a);
    }
    l=inte-65;
    cout << "j=";
    int l1;
    cin >> l1;
    if (!cin || l1<1 || l1>8)
    {
             cout <<"ERROR. Bad input" << endl;
             system ("pause");
             player2(a);
    }
    k=fabs(l1-8);
    int pole;
    for (int i=0; i<n; i++)
        for (int j=0; j<n; j++)
            if ((i==k) && (j==l))
               pole=a[i][j];
    cout << "Figurata e " << pole << endl;
    switch (pole)
    {
           case 11: pion1(k,l,a); break;
           case 12: top(k,l,a); break;
           case 13: konj(k,l,a); break;
           case 14: lanfer (k,l,a); break;
           case 15: kralica (k,l,a); break;
           case 16: kral (k,l,a); break;
    }
    cout << endl;
    player1(a);
}
   

void pion (int k, int l, int a[][n])
{ 
     for (int i=0; i<n; i++)
         for (int j=0; j<n; j++)
             {
                  if (k==6)
                     a[k-2][l]=a[k-2][l]+20;
                  a[k-1][l]=a[k-1][l]+20;
                  if ((l-1)>=0)
                     if ((a[k-1][l-1]>10) && (a[k-1][l-1]<17))
                        a[k-1][l-1]=a[k-1][l-1]+20;
                  if ((l+1)<=7) 
                     if ((a[k-1][l+1]>10) && (a[k-1][l+1]<17))
                        a[k-1][l+1]=a[k-1][l+1]+20;
                  
             }
    cout <<"Kade sakate da ja mrdnete figurata? " << endl;
    cout << "Vnesi pole so i[A...H], j= [1..8]" << endl;
    cout << "i=";
    int k2,l2;
    char z;
    cin >> z;
    int inte=int(z);
    if (!cin || (inte<65) || (inte>72))
    {
             cout <<"ERROR. Bad input. Try again" << endl;
             system ("pause");
             pion (k,l,a);
    }
    l2=inte-65;
    cout << "j=";
    int l1;
    cin >> l1;
    if (!cin || l1<1 || l1>8)
    {
             cout <<"ERROR. Bad input. Try again" << endl;
             system ("pause");
             pion (k,l,a);
    }
    k2=fabs(l1-8);
    bool b;
    int pole;
    for (int i=0; i<n; i++)
        for (int j=0; j<n; j++)  
            {
                 a[k][l]=0;
                 if (a[k2][l2]>=20)
                 {
                    a[k2][l2]=1;
                 }
            }
    for (int i=0; i<n; i++)
        for (int j=0; j<n; j++)   
            {
                 if (a[i][j]>=20)
                    a[i][j]=a[i][j]-20;
                 if (a[i][j]>1000)
                    a[i][j]=0;
            }
    
    for (int i=0; i<n; i++)
         {
              for (int j=0; j<n; j++)
                 cout << "  " << setw(2) << a[i][j];
              cout << endl << endl;
         }
   
}

void top (int k, int l, int a[][n])
{
     for (int i=0; i<n; i++)
         for (int j=0; j<n; j++)
             {
                  if (k==i)
                     a[i][j]=1;
                  if (j==l)
                     a[i][j]=1;
                  if ((k==i) && (j==l))
                     a[i][j]=2;
             }
    for (int i=0; i<n; i++)
         {
              for (int j=0; j<n; j++)
                  cout << " " << a[i][j];
              cout << endl;
         }
     cout << "Ili so zborovi kazano, topot moze da odi na:";
     for (int j=0; j<8; j++)
         for (int i=0; i<8; i++)
             {
                  if (a[i][j]==1)
                     cout << " " << char(j+65) << fabs(i-8);
             }
}

void konj (int k, int l, int a[][n])
{
     for (int i=0; i<8; i++)
         for (int j=0; j<8; j++)
             {
                  if ((i==k) && (j==l))
                  {
                     if (((i-2)>=0) && ((i-2)<8) && ((j-1)>=0) && ((j-1)<8))
                        a[i-2][j-1]=1;
                     if (((i-2)>=0) && ((i-2)<8) && ((j+1)>=0) && ((j+1)<8))
                        a[i-2][j+1]=1;
                     if (((i-1)>=0) && ((i-1)<8) && ((j-2)>=0) && ((j-2)<8))
                        a[i-1][j-2]=1;
                     if (((i-1)>=0) && ((i-1)<8) && ((j+2)>=0) && ((j+2)<8))
                        a[i-1][j+2]=1;
                     a[i][j]=2;
                     if (((i+1)>=0) && ((i+1)<8) && ((j-2)>=0) && ((j-2)<8))
                        a[i+1][j-2]=1;
                     if (((i+1)>=0) && ((i+1)<8) && ((j+2)>=0) && ((j+2)<8))
                        a[i+1][j+2]=1;
                     if (((i+2)>=0) && ((i+2)<8) && ((j-1)>=0) && ((j-1)<8))
                        a[i+2][j-1]=1;
                     if (((i+2)>=0) && ((i+2)<8) && ((j+1)>=0) && ((j+1)<8))
                        a[i+2][j+1]=1;
                  }
             }
     for (int i=0; i<n; i++)
         {
              for (int j=0; j<n; j++)
                  cout << " " << a[i][j];
              cout << endl;
         }
     cout << "Ili so zborovi kazano, konjot moze da odi na:";
     for (int j=0; j<8; j++)
         for (int i=0; i<8; i++)
             {
                  if (a[i][j]==1)
                     cout << " " << char(j+65) << fabs(i-8);
             }
}
 
  • Ја почнал/а темата
  • #3

maximilian

Gaining Experience
26 март 2008
1,064
74
Код:
void lanfer (int k, int l, int a[][n])
{
     int s=k+l;
     int r=l-k;
     for (int i=0; i<n; i++)
         for (int j=0; j<n; j++)
             {
                  if ((i+j)==s)
                     a[i][j]=1;
                  if ((j-i)==r)
                     a[i][j]=1;
                  if ((i==k) && (j==l))
                     a[i][j]=2;
             }
     for (int i=0; i<n; i++)
         {
              for (int j=0; j<n; j++)
                  cout << " " << a[i][j];
              cout << endl;
         }
     cout << endl;
     cout << "Ili so zborovi kazano, lanferot moze da odi na:";
      for (int j=0; j<8; j++)
         for (int i=0; i<8; i++)
             {
                  if (a[i][j]==1)
                     cout << " " << char(j+65) << fabs(i-8);
             }
}

void kralica (int k, int l, int a[][n])
{
     int s=k+l;
     int r=l-k;
     for (int i=0; i<n; i++)
         for (int j=0; j<n; j++)
             {
                  if ((i+j)==s)
                     a[i][j]=1;
                  if ((j-i)==r)
                     a[i][j]=1;
                  if (k==i)
                     a[i][j]=1;
                  if (j==l)
                     a[i][j]=1;
                  if ((i==k) && (j==l))
                     a[i][j]=2;
             }
     for (int i=0; i<n; i++)
         {
              for (int j=0; j<n; j++)
                  cout << " " << a[i][j];
              cout << endl;
         }
     cout << "Ili so zborovi kazano, kralicata moze da odi na:";
      for (int j=0; j<8; j++)
         for (int i=0; i<8; i++)
             {
                  if (a[i][j]==1)
                     cout << " " << char(j+65) << fabs(i-8);
             }
}

void kral (int k, int l, int a[][n])
{
     for (int i=0; i<n; i++)
         for (int j=0; j<n; j++)
             {
                  if ((i==k) && (j==l))
                     {
                             for (int k1=-1; k1<2; k1++)
                                 for (int l1=-1; l1<2; l1++)
                                      if ((i+k1>=0) && (j+l1>=0) && (i+k1<n) && (j+l1<n))
                                         a[k+k1][l+l1]=1;
                             a[k][l]=2;
                     } 
             }
     for (int i=0; i<n; i++)
         {
              for (int j=0; j<n; j++)
                  cout << " " << a[i][j];
              cout << endl;
         }
     cout << "Ili so zborovi kazano, kralot moze da odi na:";
     for (int j=0; j<8; j++)
         for (int i=0; i<8; i++)
             {
                  if (a[i][j]==1)
                     cout << " " << char(j+65) << fabs(i-8);
             }
}   

void pion1 (int k, int l, int a[][n])
{ 
     for (int i=0; i<n; i++)
         for (int j=0; j<n; j++)
             {
                  if (k==1)
                     a[k+2][l]=41;
                  a[k][l]=42;
                  a[k+1][l]=41;
                  if ((l-1)>=0) 
                     a[k+1][l-1]=41;
                  if ((l+1)<=7)
                     a[k-1][l+1]=41;
                  
             }
    cout <<"Kade sakate da ja mrdnete figurata? " << endl;
    cout << "Vnesi pole so i[A...H], j= [1..8]" << endl;
    cout << "i=";
    int k2,l2;
    char z;
    cin >> z;
    int inte=int(z);
    if (!cin || (inte<65) || (inte>72))
    {
             cout <<"ERROR. Bad input" << endl;
             system ("pause");
    }
    l2=inte-65;
    cout << "j=";
    int l1;
    cin >> l1;
    if (!cin || l1<1 || l1>8)
    {
             cout <<"ERROR. Bad input" << endl;
             system ("pause");
    }
    k2=fabs(l1-8);
    bool b;
    int pole;
    for (int i=0; i<n; i++)
        for (int j=0; j<n; j++)  
            {
                 if (a[k2][l2]==41)
                 {
                    a[k2][l2]=11; 
                    a[k][l]=0;
                 }
            }
    for (int i=0; i<n; i++)
        for (int j=0; j<n; j++)   
            {
                 if (a[i][j]==41)
                    a[i][j]=0;
                 if (a[i][j]==42)
                    a[i][j]=11;
            }
    
    for (int i=0; i<n; i++)
         {
              for (int j=0; j<n; j++)
                 cout << "  " << setw(2) << a[i][j];
              cout << endl << endl;
         }
   
}
 
  • Ја почнал/а темата
  • #6

maximilian

Gaining Experience
26 март 2008
1,064
74
За довршено, не е довршено, а за ерори не знам зошто ти дава. Ја го компајлирам на Dev C++ и тргнува кај мене. Само дава некои warnings за конвертирање од еден тип у друг (oд int y double)

EDIT: Не е визуелно. Најкомплицирана работа што ја имам искористено тука е рекурсијата :). Башка, у Dev C++ е правена а таблата со шах ми е претставена со бројки, тоа ако е визуелно, PacMan е графичко чудо за ова :D
 
  • Ја почнал/а темата
  • #8

maximilian

Gaining Experience
26 март 2008
1,064
74
Појма немам, ја до сеа немам работено во visual studio, ова е правено на Dev C++
 

fuUuUzZzZy

On your way to fame
14 декември 2007
4,842
885
Ohrid
OMG.. Многу долго ова бе за еден обичен шах..
Дури не се исплаќа толку работа за еден шах.. Јас лично не би се нафатил на ова..
 
  • Ја почнал/а темата
  • #10

maximilian

Gaining Experience
26 март 2008
1,064
74
A бе и ја мислев дека е обичен шах и дека ќе е лесно, ама испадна тешко, ама си сам си го зададив предизвикот, и ќе го решам. Само сега сакам да прашам дали гледате пооптимално решение од ова.
 

vasildb

Intern
17 април 2007
209
6
Абе каков долг код бе луѓе. Не е ништо страшно големината на кодот, секоја посериозна програма има малце и поголем код нели.:))
Иначе за пооптимално решение можеш да користиш Visual C++ за да можеш да го претставиш и графички. Вака некако не е прегледно.
 
  • Ја почнал/а темата
  • #12

maximilian

Gaining Experience
26 март 2008
1,064
74
A бе да, сега за сега никогаш не сум работел со Visual C++, кај и да е ќе почнам :). Сега за сега така ми е замислено, зашто сум ограничен со можностите на С++, а и испити иам сега, нека поминат они, па после со Visual C++. Сега за сега ми е, дали да продолжам на овој начин да го решавам проблемот, или има пооптимално решение.
 

vasildb

Intern
17 април 2007
209
6
Не го разгледав цел код, и не знам баш како работи, но продолжи со ова, сепак тие функции ќе ти се најдат, можеш истите да си ги искористиш во Visual C++ понатаму.
За пооптимално решение не знам, веројатно има пооптимално, побарај по Google некои алгоритми за шах, обавезно има подобар код.
 

loverboy

Intern
6 февруари 2008
147
11
За почеток е добро. Добар проект е да се направи игра шах, но поголем предизвик е да направиш да игра со компјутер. За игра со двајца само треба да дефинираш на кој начин ќе се внесуваат и изнесуваат информациите и дали ќе користиш некаква графика. За почеток е добро, но ти советувам да се заинтересираш малку на кој начин би можело да се изведе да се игра со компјутер ;-) Инаку 400 реда код и не е нешто многу, просечно јас што ги правам програмите се по 300-400 линии :D Една стратегиска игра што ја правев лани а не ја довршив :ha: ми фати 1000 линии код. Да се надоврзам на проблемот што го правиш. Ти треба само една матрица, и секој играш прави измени на матрицата, за секоја фигура треба да дефинираш каде смее а каде не смее да оди, да не направи еден играч грешка потег. Инаку јас планирав да направам шаховска игра ама за да игра против компјутер, разбрав дека има некои интересни натпревари па да учествувам и јас со своја програма :D
Инаку би сакал овде да се надоврзам како би се направила програма која ќе игра со човек. Значи ова е типична стратегиска игра потег-потег а се користи MiniMax алгоритмот. Повеќе за него можете да најдете на google и на wikipedia. Се користи BFS (breadth-first search)
In graph theory, breadth-first search (BFS) is a graph search algorithm that begins at the root node and explores all the neighboring nodes. Then for each of those nearest nodes, it explores their unexplored neighbor nodes, and so on, until it finds the goal.
Исто на wikipedia можете да пронајдете повеќе за ова. Се користи alpha-beta prunning, потоа за оптимизација се користи и хеуристика, но воглавно главниот алгоритам е MiniMax, а се друго е оптимизација. Ќе работи добро програмата и со основниот алгоритам, а за да биде потешко да се победи компјутерот треба оптимизации :D Инаку има еден веб сајт на интернет http://www.codecup.nl
кој е натпревар во правење на стратегиски игри. Едвај чекам да дојде новиот проблем па да се помачам да направам програма за него :) Лани за малку не успеав да стигнам заради факултетот, 90 проценти беше готова програмата, останаа уште некои ситници, ама оваа година се надевам ќе ја направам тип топ :D
Поздрав Maximilian, и со среќа со програмата!

П.С. Не се замарај колку е долг кодот, подолг код за мене значи полесно снаоѓање, бидејќи не користиш скратеници туку пишуваш се. А подобро решение не значи пократок код.
 
  • Ја почнал/а темата
  • #16

maximilian

Gaining Experience
26 март 2008
1,064
74
Фала брат за поддршката, нека заврши последниот испит (наредниот петок) и се фаќам за работа :). Иначе за да развива компјутерот стратегии, можеби и ќе го направам некогаш, ама друг пат :)). А иначе колку за сега знам дека не би требало да е многу тешко, само шо ќе ми одземе време, заради тоа што кодот ќе биде голем, е сеа ми беше дали има некој идеа за пооптимално решение (како шо кажав Х пати погоре :) ). Ти шо мислиш? Вака да ја продолжам, или имаш предлог за друг начин?
 
M

Mr.Alien

Гостин
Можеби овој пост нема да ти помогне многу, но обидувајќи се со гоогле. пронајдов линкови во кои е објаснето кои чекори и по кој редослед треба да се прават кога се програмира шаховска игра, во смисол играње против компјутер. само, многу се за да ги постирам.
 
  • Ја почнал/а темата
  • #18

maximilian

Gaining Experience
26 март 2008
1,064
74
Остави линк за тоа шо си гуглал, ако може. :)
 

loverboy

Intern
6 февруари 2008
147
11
http://www.gamedev.net/reference/programming/features/chess1/

Ова е многу корисна страна. Овде научив на кој принцип работат стратегиските игри како шах. Со детална анализа може да се сфати принципот. Имам уште многу други страни кои ги најдов лани кога барав теорија за павење на стратегиски игри ама сега за сега доволна е оваа како страна која на пријателски начин целосно го опфаќа алгоритмот за шах, иако не се дадени готови кодови, битно е да се сфати логиката :)
 
  • Ја почнал/а темата
  • #23

maximilian

Gaining Experience
26 март 2008
1,064
74
@loverboy
А бе не се битни кодовите, тоа си е само синтаксата на јазикот, битен е алгоритамот, тоа е цела суштина на секоја програма, со 1 алгоритам се прават програми на Х јазици. И тебе и на @Mr.Alien , фала ви за линковите, ќе ги ѕирнам после петок :)
 

no-no

Intern
17 април 2008
4
1
Колега ептен си ја избрзал работата, несакам да те разочарам во твојот обид да решаваш шаховска задача само со употреба на прости типови на податоци, но сепак мислам дека длабоко ќе заглавиш ако не користиш објектно орентиран пристап т.е класи или во најмала мера структури на податоци. И како за крај , не користи обични матрици , имаш контењери во C++ , со кои што можеш многу лесно да манипулуираш, кои што веќе во себе содржаат одлични и оптимизирани функции за пребарување , вметнување и слично.
 
  • Ја почнал/а темата
  • #25

maximilian

Gaining Experience
26 март 2008
1,064
74
А бе баш ваков одговор барав, зашто кога почнав да ја правам бев ограничен со знаењата и можностите на С++. Додуше, и сега неам некои појаки познавања, последно нешто што сме работеле се структури, а класите, наследувањата, конструктори, деструктори само теориски ни се земени. А тоа контењери појма неам шо се :).
Како и да е, фала многу за сугестијата. А вака, можеш да ми објасниш поубаво шо се тоа контењери? Онака, површно...
 

Нови мислења

Последни Теми

Статистика

Теми
43,565
Мислења
823,420
Членови
28,072
Најнов член
josimovskii
На врв Дно