vc 五子棋代码

win32 控制台五子棋代码:http://blog.youkuaiyun.com/lihan6415151528/archive/2009/06/27/4302353.aspx

win32 应用程序 五子棋代码:

#include<windows.h> #include<stdio.h> #include<math.h> static int nGrid[19][19];//代表19*19个棋位,其中,0代表该棋位无棋子,+1代表黑棋,-1代表白棋。 static int nScore[19][19];//每个棋位的分数。 static int nPlayerNow;//偶数代表玩家,奇数代表电脑。 LRESULT CALLBACK WinPro(HWND hWnd,UINT uMsg,WPARAM wParam,LPARAM lParam);//声明窗口过程函数。 void fnInitInterface(HDC hDC);//初始化棋盘界面;棋盘右方的黑白棋标识,双方所用时间;棋盘下方的提示按钮和提示框。 int fnReCountScore(int a,int b);//返回值为重新计算出的棋位分数 int WINAPI WinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance,LPSTR lpCmdLine,int nCmdShow) { WNDCLASS wndClass; wndClass.cbClsExtra = 0; wndClass.cbWndExtra = 0; wndClass.hbrBackground = (HBRUSH)GetStockObject(LTGRAY_BRUSH); wndClass.hCursor = LoadCursor(NULL,IDC_ARROW); wndClass.hIcon = LoadIcon(NULL,IDI_APPLICATION); wndClass.hInstance = hInstance; wndClass.lpfnWndProc = WinPro; wndClass.lpszClassName = TEXT("ClassName"); wndClass.lpszMenuName = NULL; wndClass.style = CS_HREDRAW | CS_VREDRAW; //注册窗口类 RegisterClass(&wndClass); //创建窗口 HWND hWnd; hWnd = CreateWindow(TEXT("ClassName"),TEXT("五子棋"),WS_OVERLAPPEDWINDOW,0,0,1600,1460,NULL,NULL,hInstance,NULL); //显示和刷新窗口 ShowWindow(hWnd,nCmdShow); UpdateWindow(hWnd); //定义消息结构体,开始消息循环 MSG msg; while(GetMessage(&msg,NULL,0,0)) { TranslateMessage(&msg); DispatchMessage(&msg); } return msg.wParam; } //定义窗口过程函数 LRESULT CALLBACK WinPro(HWND hWnd,UINT uMsg,WPARAM wParam,LPARAM lParam) { int rowMinArea,rowMaxArea,lineMinArea,lineMaxArea;//需要重新计算棋位分数的范围变量 RECT rect; int a,b,temp=0;//调试用的,编写好后,可以删除的!!!!!!!!!!!!!!!!!!!!!!!!!! POINT pt; PAINTSTRUCT ps; TCHAR szBuffer[10]; switch(uMsg) { case WM_PAINT: HDC hDC; hDC = BeginPaint(hWnd,&ps); fnInitInterface(hDC);//初始化棋盘。 //根据nGrid[][]的值,在对应的位置画上对应的棋子。 for(a=0;a<19;a++) for(b=0;b<19;b++) { if(nGrid[a][b] == 1) Ellipse(hDC,(b+1)*20-10,(a+1)*20-10,(b+1)*20+10,(a+1)*20+10); //TextOut(hDC,500+20*b,500+20*a,szBuffer,wsprintf(szBuffer,TEXT("%d"),nGrid[a][b]));//调试用的,编写好后,可以删除的!!!!!!!!!!!!!!!!!!!!!!!!!! TextOut(hDC,500+20*b,20+20*a,szBuffer,wsprintf(szBuffer,TEXT("%d"),nScore[a][b]));//调试用的,编写好后,可以删除的!!!!!!!!!!!!!!!!!!!!!!!!!! } EndPaint(hWnd,&ps); break; case WM_LBUTTONDOWN: pt.x = LOWORD(lParam); pt.y = HIWORD(lParam); //根据鼠标点击的位置,判断出需要绘制棋子的棋位。 if(pt.x >= 10 && pt.x <= 390 && pt.y >= 10 && pt.y <= 390) { if(pt.x%10 >= 5) pt.x = pt.x + (10-pt.x%10); else pt.x = pt.x - pt.x%10; if(pt.y%10 >= 5) pt.y = pt.y + (10-pt.y%10); else pt.y = pt.y - pt.y%10; nGrid[pt.y/20-1][pt.x/20-1] = 1; nScore[pt.y/20-1][pt.x/20-1] = 10; rect.left = pt.x/20*20-10; rect.top = pt.y/20*20-10; rect.right = pt.x/20*20+10; rect.bottom = pt.y/20*20+10; } InvalidateRect(hWnd,&rect,FALSE); //需要重新计算棋位分数的范围 //row的最小值 if((pt.y/20-1)<4) rowMinArea = 0; else rowMinArea = (pt.y/20-1) - 4; //row的最大值 if((pt.y/20-1)>15) rowMaxArea = 19; else rowMaxArea = (pt.y/20-1) + 5; //line的最小值 if((pt.x/20-1)<4) lineMinArea = 0; else lineMinArea = (pt.x/20-1) - 4; //line的最大值 if((pt.x/20-1)>15) lineMaxArea = 19; else lineMaxArea = (pt.x/20-1) + 5; //开始对范围内的棋位进行计算 for(a=rowMinArea;a<=rowMaxArea;a++) for(b=lineMinArea;b<=lineMaxArea;b++) { if( nScore[a][b] != 10 ) nScore[a][b] = fnReCountScore(a,b); } nPlayerNow++; break; case WM_DESTROY: PostQuitMessage(0); break; } return DefWindowProc(hWnd,uMsg,wParam,lParam); } //界面初始化函数 void fnInitInterface(HDC hDC) { TCHAR szBuffer[10]; for(int i=1;i<20;i++) { //画横线 MoveToEx(hDC,20,20*i,NULL); LineTo(hDC,380,20*i); //画竖线 MoveToEx(hDC,20*i,20,NULL); LineTo(hDC,20*i,380); } Rectangle(hDC,58,388,92,408);//提示的方框 Rectangle(hDC,308,388,342,408);//认输的方框 TextOut(hDC,60,390,szBuffer,wsprintf(szBuffer,TEXT("提示"))); TextOut(hDC,310,390,szBuffer,wsprintf(szBuffer,TEXT("认输"))); } //重新计算棋位的分数 int fnReCountScore(int a,int b) { int Score = 0; int x,y; int mBegin,mEnd,nBegin,nEnd;//需要用于重新计算的棋位的数组坐标的范围起点和终点,仅限纵向和横向。 int mInclinedBegin,mInclinedEnd,nInclinedBegin,nInclinedEnd;//需要用于重新计算的棋位的数组坐标的范围起点和终点,仅限左斜向和右斜向。 int nUprightScore = 0;//纵向的分数 int nHorizontalScore = 0;//横向的分数 int nLeftInclinedScore = 0;//左斜向的分数 int nRightInclinedScore = 0;//右斜向的分数 //纵向和横向的范围坐标 //mBegin if(a<4) mBegin = 0; else mBegin = a - 4; //mEnd if(a>15) mEnd = 19; else mEnd = a + 4; //nBegin if(b<4) nBegin = 0; else nBegin = b - 4; //nEnd if(b>15) nEnd = 19; else nEnd = b + 4; //左斜向和右斜向的范围坐标 //mInclinedBegin 和 nInclinedBegin if(a<4 || b<4) { if(a < b) { mInclinedBegin = 0; nInclinedBegin = b - a; } else { mInclinedBegin = a - b; nInclinedBegin = 0; } } else { mInclinedBegin = a -4; nInclinedBegin = b - 4; } //mInclinedEnd 和 nInclinedEnd if(a>15 || b>15) { if(a > b) { mInclinedEnd = 19; nInclinedEnd = 19 - a + b; } else mInclinedEnd = 19 - b + a; nInclinedEnd = 19; } else { mInclinedEnd = a + 4; nInclinedEnd = b + 4; } //纵向的分数 for(x=mBegin;x<=a;x++) { if( (x+4) <= mEnd ) { if(abs(nUprightScore) < abs(nGrid[x][b] + nGrid[x+1][b] + nGrid[x+2][b] + nGrid[x+3][b] + nGrid[x+4][b])) nUprightScore = nGrid[x][b] + nGrid[x+1][b] + nGrid[x+2][b] + nGrid[x+3][b] + nGrid[x+4][b]; } }/* //横向的分数 for(y=nBegin;y<=b;y++) { if( (y+4) <= nEnd ) { if(abs(nHorizontalScore) < abs(nGrid[a][y] + nGrid[a][y+1] + nGrid[a][y+2] + nGrid[a][y+3] + nGrid[a][y+4])) nHorizontalScore = nGrid[a][y] + nGrid[a][y+1] + nGrid[a][y+2] + nGrid[a][y+3] + nGrid[a][y+4]; } } //左斜向的分数 for(x=mInclinedBegin,y=nInclinedEnd;x<=a&&y>=b;x++,y--) { if( ((x+4) <= mInclinedEnd) && ((y-4) >= nInclinedBegin )) { if(abs(nLeftInclinedScore) < abs(nGrid[x][y] + nGrid[x+1][y-1] + nGrid[x+2][y-2] + nGrid[x+3][y-3] + nGrid[x+4][y-4])) nLeftInclinedScore = nGrid[x][y] + nGrid[x+1][y-1] + nGrid[x+2][y-2] + nGrid[x+3][y-3] + nGrid[x+4][y-4]; } } //右斜向的分数 for(x=mInclinedBegin,y=nInclinedBegin;x<=a&&y<=b;x++,y++) { if( ((x+4) <= mInclinedEnd) && ((y+4) <= nInclinedEnd )) { if(abs(nRightInclinedScore) < abs(nGrid[x][y] + nGrid[x+1][y+1] + nGrid[x+2][y+2] + nGrid[x+3][y+3] + nGrid[x+4][y+4])) nRightInclinedScore = nGrid[x][y] + nGrid[x+1][y+1] + nGrid[x+2][y+2] + nGrid[x+3][y+3] + nGrid[x+4][y+4]; } }*/ //比较4个方向分数的绝对值,取绝对值最大的为该棋位的分数 if( abs(Score) < abs(nUprightScore) ) Score = nUprightScore; if( abs(Score) < abs(nHorizontalScore) ) Score = nHorizontalScore; if( abs(Score) < abs(nLeftInclinedScore) ) Score = nLeftInclinedScore; if( abs(Score) < abs(nRightInclinedScore) ) Score = nRightInclinedScore; //返回最终该棋位的分数 return Score; }

运行:

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值