C++毕业课程设计报告.docx
《C++毕业课程设计报告.docx》由会员分享,可在线阅读,更多相关《C++毕业课程设计报告.docx(27页珍藏版)》请在冰豆网上搜索。
C++毕业课程设计报告
(此文档为word格式,下载后您可任意编辑修改!
)
青岛理工大学
C++面向对象课程设计报告
院(系):
_________
专业:
__
学生姓名:
___
班级:
学号:
题目:
_________
起讫日期:
__________
设计地点:
_______
指导老师:
____
一.游戏概述...........................................3
1.1.游戏介绍.........................................3
1.2.游戏玩法.........................................3
1.3.运行环境.........................................3
2.具体步骤........................................3
2.1.棋盘设计.........................................3
2.2.棋子设计.........................................4
2.3.电脑算法.........................................6
2.4.胜负判断.........................................8
3.游戏运行图......................................11
4.总结............................................13
41.自我总结..........................................13
4.2.程序的不足和需要改进的地方.......................14
致谢...............................................14
附录一参考文献....................................15
附录二程序源代码..................................15
1.游戏概述
1.1.游戏介绍
五子棋是一种两人对弈的纯策略型棋类游戏,是起源于中国古代的传统黑白棋种之一。
发展于日本,流行于欧美。
容易上手,老少皆宜,而且趣味横生,引人入胜;不仅能增强思维能力,提高智力,而且富含哲理,有助于修身养性。
1.2.游戏玩法
黑白双方依次落子,由黑先下,当棋盘上有三个子时,如果此时白方觉得开的局不利于自已可以提出交换,黑方无条件接受!
也可以不交换,主动权在白方!
然后继续下棋,任一方先在棋盘上形成横向、竖向、斜向的连续的相同颜色的五个棋子的一方为胜。
1.3.运行环境
Windows7VC++6.0
2.具体步骤
2.1.棋盘设计
棋盘和棋子可以用GDI来实现,棋盘用GDI划线,基本上就是LineTo(x,y),MoveTo(x,y),一个棋盘就出来了。
具体代码如下
在OnPaint()函数的else内加入如下代码
CPaintDCdc(this);
dc.SelectStockObject(BLACK_PEN);
inti,j;
for(i=40;i<=530;i=i+35)
{
dc.MoveTo(i,40);
dc.LineTo(i,530);
}
for(j=40;j<=530;j=j+35)
{
dc.MoveTo(40,j);
dc.LineTo(530,j);
}}
2.2.棋子设计
至于如何画棋子,就用GDI来画圆,然后填充上不同的颜色,黑子、白子也就实现了。
这里的棋子不应该是一个独立的量,它有自己的区域,应该能判断鼠标是不是点击到了这个区域,当点击这个区域的时候是否应该显示,应该显示什么颜色的旗子……把这么多东西集合在一起,应该定义一个类,于是Cqiz这个类就出现了。
Cqiz有四个变量如下:
intflag;
CRectrect;
inty;
intx;
x,y表示这个区域的中心,rect为以x,y为中心的边长为30的矩形,flag用来表示该对象的状态(0:
空白1:
黑子-1:
白字)。
然后又定义了5个成员函数
boolisWhite();//如果为白子,返回true
CRectgetRect();//获得该对象对应的CRect
boolisBlack();//如果为黑子,返回true
boolisEmpty();//如果为空,返回true
boolisOn(CPointpoint);//如果该点出在该区域返回true,用来判断鼠标单击对应的区域。
定义了一个vector容器
vectorqz;
在OnInitDialog()内对qy进行初始化
inti,j,k;
Cqizq;
for(i=60,k=0;i<=550;i=i+35,k++)
for(j=60;j<=550;j=j+35)
{
q.x=i;
q.y=j;
qz[k].push_back(q);
}
当鼠标单击的时候,判断单击的是哪一个区域,如果该区域为空则修改区域状态
voidCWuZiQiDlg:
:
OnLButtonDown(UINTnFlags,CPointpoint)
{
//TODO:
Addyourmessagehandlercodehereand/orcalldefault
inti,j;
for(i=0;i<15;i++)
for(j=0;j<15;j++)
if(qz[i][j].isOn(point)&&!
over&&qz[i][j].isEmpty())
{
qz[i][j].flag=1;
x=i;y=j;
ison=true;
Invalidate();//引发重绘
return;
}
CDialog:
:
OnLButtonDown(nFlags,point);
}
2.3.电脑算法
在OnLButtonUp()中实现ai,电脑走棋
voidCWuziqidlgDlg:
:
OnLButtonUp(UINTnFlags,CPointpoint)
{
//TODO:
Addyourmessagehandlercodehereand/orcalldefault
inti,j,m,n,score=0;
for(i=0;i<15;i++)
for(j=0;j<15;j++)
if(ison&&!
over&&qz[i][j].isEmpty())
{
x=i;y=j;
if(getScore()>=score)
{
score=getScore();
m=i;n=j;
}
}
if(ison&&!
over)
{
if(score<=1&&qz[7][7].flag==0)
{
qz[7][7].flag=-1;
x=7;
y=7;
}
else
{
qz[m][n].flag=-1;
x=m;y=n;
}
}
ison=false;
Invalidate();
CDialog:
:
OnLButtonUp(nFlags,point);
}
OnPaint()函数中实现绘制,每次先把棋盘画好,然后遍历各区域,如果不为空就绘制相应的棋子。
还要判断是否有一方获胜,如果有就结束游戏。
这个程序主关键的是算分,对不同的走法进行算法,得分最高的为要真正要走的。
判断是否能成5,如果是机器方的话给予900000分,如果是人方的话给予400000分;
判断是否能成活4或者是双死4或者是死4活3,如果是机器方的话给予150000分,如果是人方的话给予70000分;
判断是否已成双活3,如果是机器方的话给予30000分,如果是人方的话给予15000分;
判断是否成死3活3,如果是机器方的话给予1000分,如果是人方的话给予1000分;
判断是否能成死4,如果是机器方的话给予500分,如果是人方的话给予500分;
判断是否能成单活3,如果是机器方的话给予200分,如果是人方的话给予200分;
判断是否已成双活2,如果是机器方的话给予100分,如果是人方的话给予100分;
判断是否能成死3,如果是机器方的话给予50分,如果是人方的话给予50分;
判断是否能成双活2,如果是机器方的话给予10分,如果是人方的话给予10分;
判断是否能成活2,如果是机器方的话给予5分,如果是人方的话给予5分;
判断是否能成死2,如果是机器方的话给予3分,如果是人方的话给予3分。
下五子棋不光要进攻,还要防守,所以要先对假设那些空的格子下自己的棋子能得多少分,得出一个最高分,然后假设这些格子放上对方的棋子,得出一个最高分,如果进攻的最高分大于等于防守的最高分,则进攻,否则先进行防守。
2.4.胜负判断
根据上面的介绍,如果有一方的5个棋子连成一线,那么这方就胜利了。
if(Win(x,y)&&!
over)
{
if(qz[x][y].flag==1)
MessageBox("你赢了!
");
else
MessageBox("电脑赢!
");
over=true;
first=false;
ison=false;
}
boolCWuZiQiDlg:
:
Win(intx,inty)
{
if(qz[x][y].flag==0)
returnfalse;
intcount1=0,count2=0,i,j;
for(i=0;i<15;i++)
{
if(qz[i][y].flag==qz[x][y].flag)
count1++;
else
count1=0;
if(qz[x][i].flag==qz[x][y].flag)
count2++;
else
count2=0;
if(count1==5||count2==5)
returntrue;
}
count1=count2=1;
i=x+1;
j=y-1;
while(i<15&&j>=0&&qz[i][j].flag==qz[x][y].flag)
{
count1++;
i++;
j--;
}
i=x-1;
j=y+1;
while(i>=0&&j<15&&qz[i][j].flag==qz[x][y].flag)
{
count1++;
i--;
j++;
}
i=x-1;
j=y-1;
while(i>=0&&j>=0&&qz[i][j].flag==qz[x][y].flag)
{
count2++;
i--;
j--;
}
i=x+1;
j=y+1;
while(i<15&&j<15&&qz[i][j].flag==qz[x][y].flag)
{
count2++;
i++;
j++;
}
if(count1==5||count2==5)
returntrue;
returnfalse;
}
三.游戏运行图
四.总结
4.1.自我总结
根据这2个周的C++程序编写,使我对了C++有了新的认识,原来学会了C++可以编写好多好玩的游戏,一开始拿着这个程序不知道怎么下手,可以说是什么都不知道,然后看了孙鑫的MFC视频,但是还是感觉懂不到,因为自己的C语言功底比较差的原因吧,看到同学们都做出自己的程序来了,心里也跟着慌张起来,自己什么都不会,然后去上网看了看怎么做五子棋,才知道了要先从什么地方入手。
要先画棋盘,然后再棋子,最后再实现电脑的算法,就这样一步一步的,向同学们求教,在同学们的孜孜教诲下,才勉强完成了这个程序,但是功能不够强大,没有华丽的画面,就是一个简单的棋盘。
通过这2个周的学习,让我知道了很多很多,生活中也如此,很多东西不是自己生下来就能会的,要通过自己慢慢的去问,慢慢的摸索才能够得到答案。
4.2.程序的不足和需要改进的地方
这个程序有需要改进的地方,一个真正的五子棋是要分难度的,但是这个程序里始终就只有1个难度,没有供人们选的地方,这是这个程序不足的地方。
电脑智能部分还不够完善,应该使电脑更加智能。
致谢
逾尺的札记和研究纪录凝聚成这么薄薄的一本,高兴和欣慰之余,不禁感慨系之。
记得鲁迅在一篇文章里写道:
“人类的奋战前行的历史,正如煤的形成,当时用大量的木材,结果却只是一小块”。
倘若这一小块有点意义的话,则是我读书生活的最好纪念,也令我对于即将迈入的新生活更加充满信心。
做完了这次试验,压抑了很久的心情得到了缓解,我们都不懂的地方,就问班上其他的人,在这里也感谢他们,感谢所有在这个程序上帮助过我的和给我建议的人,有了你们我才能把这个程序编写出来。
最后,感谢老师给了我们这样一个机会,让我们了解很多东西,了解了我们所学的东西原来可以做一些很有趣的小游戏,更让我们懂得了许多东西,谢谢你们!
参考文献
1.MFC孙鑫视频20全集
2.《C++面向对象程序设计》
3.CharlesPetzold 著,Windows程序设计.北京博彦科技发展有限公司译.北京.北京大学出版社,1998
4.杨祥金,杨丹等.Windows程序设计教程.北京:
清华大学出版社,2007
5.CharlesPrterzold.ProgrammingWindowsbyCharlesPrterzold.MicrosoftPress,1998
6.何立起著,陆东晖,杜坚贞改编.BorlandC++Windows程序设计.北京:
人民邮电出版社,1994
7.Vc+++游戏编程作者:
王鹏生2001.12
程序源代码如下
#include"stdafx.h"
#include"WuZiQi.h"
#include"WuZiQiDlg.h"
#ifdef_DEBUG
#definenewDEBUG_NEW
#undefTHIS_FILE
staticcharTHIS_FILE[]=__FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
//CAboutDlgdialogusedforAppAbout
classCAboutDlg:
publicCDialog
{
public:
CAboutDlg();
//DialogData
//{{AFX_DATA(CAboutDlg)
enum{IDD=IDD_ABOUTBOX};
//}}AFX_DATA
//ClassWizardgeneratedvirtualfunctionoverrides
//{{AFX_VIRTUAL(CAboutDlg)
protected:
virtualvoidDoDataExchange(CDataExchange*pDX);//DDX/DDVsupport
//}}AFX_VIRTUAL
//Implementation
protected:
//{{AFX_MSG(CAboutDlg)
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
};
CAboutDlg:
:
CAboutDlg():
CDialog(CAboutDlg:
:
IDD)
{
//{{AFX_DATA_INIT(CAboutDlg)
//}}AFX_DATA_INIT
}
voidCAboutDlg:
:
DoDataExchange(CDataExchange*pDX)
{
CDialog:
:
DoDataExchange(pDX);
//{{AFX_DATA_MAP(CAboutDlg)
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CAboutDlg,CDialog)
//{{AFX_MSG_MAP(CAboutDlg)
//Nomessagehandlers
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
//CWuZiQiDlgdialog
CWuZiQiDlg:
:
CWuZiQiDlg(CWnd*pParent/*=NULL*/)
:
CDialog(CWuZiQiDlg:
:
IDD,pParent)
{
//{{AFX_DATA_INIT(CWuZiQiDlg)
//NOTE:
theClassWizardwilladdmemberinitializationhere
//}}AFX_DATA_INIT
//NotethatLoadIcondoesnotrequireasubsequentDestroyIconinWin32
m_hIcon=AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}
voidCWuZiQiDlg:
:
DoDataExchange(CDataExchange*pDX)
{
//{{AFX_DATA_MAP(CWuZiQiDlg)
//NOTE:
theClassWizardwilladdDDXandDDVcallshere
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CWuZiQiDlg,CDialog)
//{{AFX_MSG_MAP(CWuZiQiDlg)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_WM_LBUTTONDOWN()
ON_WM_LBUTTONUP()
ON_BN_CLICKED(IDC_BUTTON1,OnButton1)
ON_BN_CLICKED(IDC_BUTTON2,OnButton2)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
//CWuZiQiDlgmessagehandlers
BOOLCWuZiQiDlg:
:
OnInitDialog()
{
CDialog:
:
OnInitDialog();
//Add"About..."menuitemtosystemmenu.
//IDM_ABOUTBOXmustbeinthesystemcommandrange.
ASSERT((IDM_ABOUTBOX&0xFFF0)==IDM_ABOUTBOX);
ASSERT(IDM_ABOUTBOX<0xF000);
CMenu*pSysMenu=GetSystemMenu(FALSE);
if(pSysMenu!
=NULL)
{
CStringstrAboutMenu;
strAboutMenu.LoadString(IDS_ABOUTBOX);
if(!
strAboutMenu.IsEmpty())
{
pSysMenu->AppendMenu(MF_SEPARATOR);
pSysMenu->AppendMenu(MF_STRING,IDM_ABOUTBOX,strAboutMenu);
}
}
inti,j,k;
Cqizq;
for(i=40,k=0;i<=530;i=i+35,k++)
for(j=40;j<=530;j=j+35)
{
q.x=i;
q.y=j;
qz[k].push_back(q);
}
ison=false;
over=false;
first=false;
x=0;y=0;
//Settheiconforthisdialog.Theframeworkdoesthisautomatically
//whentheapplication'smainwindowisnotadialog
SetIcon(m_hIcon,TRUE);//Setbigicon
SetIcon(m_hIcon,FALSE);//Setsmallicon
//TODO:
Addextrainitializationhere
returnTRUE;//returnTRUEunlessyousetthefocustoacontrol
}
voidCWuZiQiDlg:
:
OnSysCommand(UINTnID,LPARAMlParam)
{
if((nID&0xFFF0)==IDM_ABOUTBOX)
{
CAboutDlgdlgAbout;
dlgAbout.DoModal();
}
else
{
CDialog:
:
OnSysCommand(nID,lParam);
}
}
//Ifyouaddaminimizebuttontoyourdialog,youwillneedthecodebelow
//todrawtheicon.ForMFCapplicationsusingthedocument/viewmodel,
//thisisautomaticallydoneforyoubytheframework.
voidCWuZiQiDlg:
:
OnPaint()
{
if(IsIconic())
{
CPaintDCdc(this);//devicecontextforpainting
SendMessage(WM_ICONERASEBKGND,(WPARAM)dc.GetSafeHdc(),0);
//Centericoninclientrectangle
intcxIcon=GetSystemMetrics(SM_CXICON);
intcyIcon=GetSystemMetrics(SM_CYICON);
CRectrect;
GetClientRect(&rect);
intx=(rect.Width()-cxIcon+1)/2;
inty=(rect.Height()-cyIcon+1)/2;
//Drawtheico