我的小游戏之2048

  八月初心血来潮,花了一天时间写了一个控制台版的2048。代码很烂,玩到后面会有延迟现象。先做下记录,以后有时间把移动和合并的代码再优化下。

  代码如下: 

  1 #include<iostream>
  2 #include <iomanip>
  3 #include<cstring>
  4 #include<cstdlib>
  5 #include<ctime>
  6 using namespace std;
  7 
  8 class Board {
  9     public:
 10         int board[4][4];  //棋盘数组 
 11         int n;  //已存在数字个数 
 12         Board();  //构造函数
 13         void randx();  //随机生成数字2/4
 14         void print();  //打印棋盘
 15         bool check();  //检查是否GameOver 
 16         bool up();  //向上操作 
 17         bool down();  //向下操作
 18         bool left();  //向左操作
 19         bool right();  //向右操作
 20 };
 21 
 22 Board::Board()  //构造函数 
 23 {
 24     memset(board,0,sizeof(board));  //初始化为0 
 25     n=0;    
 26 }
 27 void Board::randx()  //随机生成数字2/4 
 28 {
 29     while(true)
 30     {
 31         srand(time(NULL)); 
 32         int x=rand()%16;  //产生随机次序 
 33         if(board[x/4][x%4]==0)
 34         {
 35             srand(time(NULL)); 
 36             board[x/4][x%4]=rand()%2==0?2:4;  //产生随机数字2/4 
 37             n++;
 38             break;
 39         }
 40     }
 41 }
 42 void Board::print() //打印棋盘 
 43 {
 44     int i,j,k;
 45     for(i=0;i<4;i++)
 46     {
 47         for(k=0;k<33;k++)  //打印棋盘符'-' 
 48             cout<<'-'; 
 49         cout<<endl;
 50         for(j=0;j<4;j++)
 51         {
 52             if(board[i][j]==0)  //打印棋子 
 53                 cout<<"| "<<setw(6)<<" ";
 54             else
 55                 cout<<"| "<<setw(5)<<board[i][j]<<" ";
 56         }
 57         cout<<"|"<<endl;
 58     }
 59     for(k=0;k<33;k++)
 60             cout<<'-'; 
 61     cout<<endl;
 62 } 
 63 bool Board::check()  //检查是否GameOver 
 64 {
 65     bool flag=true;
 66     for(int i=0;flag==true,i<4;i++) 
 67         for(int j=0;flag==true,j<4;j++)
 68         {
 69             if(j<3&&board[i][j]==board[i][j+1])  //是否存在左右相等 
 70                 flag=false;
 71             if(i<3&&board[i][j]==board[i+1][j])  //是否存在上下相等 
 72                 flag=false;
 73         } 
 74     return flag;
 75 }
 76 bool Board::up()  //向上操作
 77 {
 78     int i,j;
 79     bool flag=false;
 80     for(j=0;j<4;j++){
 81         if(board[0][j]&&board[1][j]&&board[2][j]&&board[3][j])
 82             continue;
 83         for(i=1;i<=3;i++)
 84         {
 85             if(board[i][j]==0)
 86                 continue;
 87             int k=0;
 88             while(k<i&&board[k][j])k++;
 89             if(k<i)
 90             {
 91                 board[k][j]=board[i][j];
 92                 board[i][j]=0;
 93                 flag=true;
 94             }
 95         }
 96     }
 97     for(j=0;j<4;j++)  //向上合并 
 98     {
 99         if(board[0][j]&&board[1][j]&&board[0][j]==board[1][j])  //上1上2相等 
100         {
101             board[0][j]*=2;
102             flag=true;
103             if(board[2][j]&&board[3][j]&&board[2][j]==board[3][j])
104             {
105                 board[1][j]=board[2][j]*2;
106                 board[2][j]=board[3][j]=0;
107                 n-=2;
108             }
109             else
110             {
111                 board[1][j]=board[2][j];
112                 board[2][j]=board[3][j];
113                 board[3][j]=0;
114                 n--;
115             }
116         }
117         else
118         {
119             if(board[1][j]&&board[2][j]&&board[1][j]==board[2][j])  //中间相等 
120             {
121                 board[1][j]*=2;
122                 board[2][j]=board[3][j];
123                 board[3][j]=0;
124                 flag=true;
125                 n--;
126             }
127             else
128             {
129                 if(board[2][j]&&board[3][j]&&board[2][j]==board[3][j])  //下1下2相等 
130                 {
131                     board[2][j]*=2;
132                     board[3][j]=0;
133                     flag=true;
134                     n--;
135                 }
136             }
137         }
138     }
139     return flag;
140 }
141 bool Board::down()  //向下操作
142 {
143     int i,j;
144     bool flag=false;
145     for(j=0;j<4;j++){
146         if(board[0][j]&&board[1][j]&&board[2][j]&&board[3][j])
147             continue;
148         for(i=2;i>=0;i--)
149         {
150             if(board[i][j]==0)
151                 continue;
152             int k=3;
153             while(k>i&&board[k][j])k--;
154             if(k>i)
155             {
156                 board[k][j]=board[i][j];
157                 board[i][j]=0;
158                 flag=true;
159             }
160         }
161     }
162     for(j=0;j<4;j++)  //向下合并 
163     {
164         if(board[3][j]&&board[2][j]&&board[3][j]==board[2][j])  //下1下2相等 
165         {
166             board[3][j]*=2;
167             flag=true;
168             if(board[1][j]&&board[0][j]&&board[1][j]==board[0][j])
169             {
170                 board[2][j]=board[1][j]*2;
171                 board[1][j]=board[0][j]=0;
172                 n-=2;
173             }
174             else
175             {
176                 board[2][j]=board[1][j];
177                 board[1][j]=board[0][j];
178                 board[0][j]=0;
179                 n--;
180             }
181         }
182         else
183         {
184             if(board[2][j]&&board[1][j]&&board[2][j]==board[1][j])  //中间相等 
185             {
186                 board[2][j]*=2;
187                 board[1][j]=board[0][j];
188                 board[0][j]=0;
189                 flag=true;
190                 n--;
191             }
192             else
193             {
194                 if(board[1][j]&&board[0][j]&&board[1][j]==board[0][j])  //上1上2相等 
195                 {
196                     board[1][j]*=2;
197                     board[0][j]=0;
198                     flag=true;
199                     n--;
200                 }
201             }
202         }
203     }
204     return flag;
205 }
206     
207 bool Board::left()  //向左操作
208 {
209     int i,j;
210     bool flag=false;
211     for(i=0;i<4;i++){
212         if(board[i][0]&&board[i][1]&&board[i][2]&&board[i][3])
213             continue;
214         for(j=1;j<=3;j++)
215         {
216             if(board[i][j]==0)
217                 continue;
218             int k=0;
219             while(k<j&&board[i][k])k++;
220             if(k<j)
221             {
222                 board[i][k]=board[i][j];
223                 board[i][j]=0;
224                 flag=true;
225             }
226         }
227     }
228     for(i=0;i<4;i++)  //向左合并 
229     {
230         if(board[i][0]&&board[i][1]&&board[i][0]==board[i][1])  //左1左2相等 
231         {
232             board[i][0]*=2;
233             flag=true;
234             if(board[i][2]&&board[i][3]&&board[i][2]==board[i][3])
235             {
236                 board[i][1]=board[i][2]*2;
237                 board[i][2]=board[i][3]=0;
238                 n-=2;
239             }
240             else
241             {
242                 board[i][1]=board[i][2];
243                 board[i][2]=board[i][3];
244                 board[i][3]=0;
245                 n--;
246             }
247         }
248         else
249         {
250             if(board[i][1]&&board[i][2]&&board[i][1]==board[i][2])  //中间相等 
251             {
252                 board[i][1]*=2;
253                 board[i][2]=board[i][3];
254                 board[i][3]=0;
255                 flag=true;
256                 n--;
257             }
258             else
259             {
260                 if(board[i][2]&&board[i][3]&&board[i][2]==board[i][3])  //右1右2相等 
261                 {
262                     board[i][2]*=2;
263                     board[i][3]=0;
264                     flag=true;
265                     n--;
266                 }
267             }
268         }
269     }
270     return flag;
271 }
272 bool Board::right()  //向右操作
273 {
274     int i,j;
275     bool flag=false;
276     for(i=0;i<4;i++){
277         if(board[i][0]&&board[i][1]&&board[i][2]&&board[i][3])
278             continue;
279         for(j=2;j>=0;j--)
280         {
281             if(board[i][j]==0)
282                 continue;
283             int k=3;
284             while(k>j&&board[i][k])k--;
285             if(k>j)
286             {
287                 board[i][k]=board[i][j];
288                 board[i][j]=0;
289                 flag=true;
290             }
291         }
292     }
293     for(i=0;i<4;i++)  //向右合并 
294     {
295         if(board[i][3]&&board[i][2]&&board[i][3]==board[i][2])  //右1右2相等 
296         {
297             board[i][3]*=2;
298             flag=true;
299             if(board[i][1]&&board[i][0]&&board[i][1]==board[i][0])
300             {
301                 board[i][2]=board[i][1]*2;
302                 board[i][1]=board[i][0]=0;
303                 n-=2;
304             }
305             else
306             {
307                 board[i][2]=board[i][1];
308                 board[i][1]=board[i][0];
309                 board[i][0]=0;
310                 n--;
311             }
312         }
313         else
314         {
315             if(board[i][2]&&board[i][1]&&board[i][2]==board[i][1])  //中间相等 
316             {
317                 board[i][2]*=2;
318                 board[i][1]=board[i][0];
319                 board[i][0]=0;
320                 flag=true;
321                 n--;
322             }
323             else
324             {
325                 if(board[i][1]&&board[i][0]&&board[i][1]==board[i][0])  //左1左2相等 
326                 {
327                     board[i][1]*=2;
328                     board[i][0]=0;
329                     flag=true;
330                     n--;
331                 }
332             }
333         }
334     }
335     return flag;
336 }
337 int main()
338 {
339     while(true)
340     {
341         system("cls");  
342         cout<<"Welcome To 2048 !"<<endl;
343         cout<<"Press w(up)/s(down)/a(left)/d(right)"<<endl;
344         Board b;
345         b.randx();  //随机产生两个数字 
346         b.randx();
347         b.print(); 
348         char ch;
349         while(true)
350         {
351             bool flag=false; //判断是否改变标志 
352             cin>>ch;
353             switch(ch)
354             {
355                 case 'w':  //向上操作
356                     flag=b.up();
357                     break;
358                 case 's':  //向下操作
359                     flag=b.down();
360                     break;
361                 case 'a':  //向左操作
362                     flag=b.left();
363                     break;
364                 case 'd':  //向右操作
365                     flag=b.right();
366                     break;
367                 default:
368                     break;        
369             }
370             if(flag)  //无改变则不随机产生数字 
371             { 
372                 b.randx();
373             }
374             system("cls"); 
375             b.print();
376             if(b.n==16&&b.check())  //判断是否GameOver 
377                 break;
378         }
379         cout<<"Sorry ! Game Over !"<<endl;
380         cout<<"Try again ?(y/others)"<<endl;
381         cin>>ch;
382         if(ch!='y')
383         break;
384     }
385     return 0;
386 }
原文地址:https://www.cnblogs.com/levicode/p/3925840.html