C语言perl中子函数返回值值输入另一个子函数?(哪位帮我改一下)

51CTO旗下网站
C语言是C++的子集吗?
《C语言必须知道的300个问题》本书以基础知识为框架,介绍了C语言各部分知识所对应的常见开发疑难问题,并作了透彻地解析。本书内容包括初识C语言,一个简单的C程序,算法入门,常用数据类型,运算符与表达式,输入/输出函数,选择、分支结构程序设计,循环结构,数组,函数编程基础,指针解析,常用数据结构,位运算操作符,存储管理,预处理和函数类型,文件的读写操作和图形图像处理。本节为大家介绍问题7
C语言是C++的子集吗。
作者:明日科技来源:清华大学出版社| 11:15
问题7& C语言是C++的子集吗?
C语言是C++的子集吗?C++是在C语言的基础上扩展而来并包含所有C语言的内容吗?
从实用角度讲,C++属于C语言的一个超集,基本上兼容ANSI C。但是从编译角度上讲,C语言的有些特性在C++中并不支持。相反,ANSI C继承了C++的几个特性,包括原型和常量。因此,这两种语言并不是另一个的超集或子集;而且它们在一些通用构造的定义上也不同。尽管有这些不同,许多C程序在C++环境中仍能编译,而且许多最新的编译器同时提供C和C++的编译模式。但是,不要把C代码完全当做C++代码来编译,否则在遇到不兼容问题时会给程序带来错误。
C++对C语言的改进如下。
C++对数组定义进行了限制。在C语言中,初始化数组时不作数组溢出判断,这样就容易使数组没有足够大的空间存放数据而产生错误。C++对此作了一些改进,像char str[3]="Jim"这样的表达式就被认为是一个错误,但是它在C语言中是合法的。
在C++中,声明语句可以穿插于语句之间。大家知道,在C语言中,一个语句块中的所有声明必须都放在所有语句的前面,而C++去掉了这个限制,使声明语句可以穿插于语句之间。
C++对C语言的改进最主要表现在对面向对象的扩充上。C语言是一种面向过程的结构化的语言,而C++是面向对象的语言,它在C语言的基础上增加了面向对象的机制,使得C++比C语言更加完善和实用。
C++中存在而C语言中不存在的限制。
在C++中,用户代码不能够调用主函数main()函数,但是在C语言中这是可以的(但是极少出现这种情况)。
C++中对函数原型的声明是严格的,要求必须完整,而在C语言中却没有这么严格。
在C++中,由typedef定义的类型的名字不能与已有的结构名称冲突,但在C语言中却是允许的。
C++规定了更严格的类型处理,例如,当void*指针赋值给另一个类型的指针时,C++要求必须进行强制类型转换,而在C语言中则无需这么做。
C++与C语言中含义不同的特性:
C++对C语言的关键字进行了扩充,增加了至少十几个。这些关键字在C语言中可以作为标识符使用,但是如果这样的C语言代码使用C++编译器进行编译,就会产生错误信息。
在C++中,内层作用域的结构名称将会隐藏外层空间中相同的对象名,在C语言中则不会这样。
在C++中,注释可以使用"//"注释符,而在C语言中则不能使用。
从总体上说,C语言是C++的前身,上面只介绍了它们的一部分不同之处。从上面的介绍可以看出,C++并没有对C语言存在的一些最基本的问题进行改进,它仍然保留了C语言的许多缺陷,而且在此基础上又堆积了大量复杂的东西。不过尽管存在着不少缺陷,C语言和C++都被广泛地使用着,这也说明了其存在的价值。
C和C++的不同之处还有很多,大家要通过实际编程来分析两者的差异,并保持警惕,避免相互使用时出现错误。
【责任编辑: TEL:(010)】&&&&&&
大家都在看猜你喜欢
热点热点头条头条热点
24H热文一周话题本月最赞
讲师:30828人学习过
讲师:269884人学习过
讲师:145693人学习过
精选博文论坛热帖下载排行
本书结合JSP和Servlet的最新规范,从基本的语法和规范入手,以经验为后盾,以实用为目标,以实例为导向,以实践为指导,深入浅出地讲解了JS...
订阅51CTO邮刊下次自动登录
现在的位置:
& 综合 & 正文
五子棋,人机对战,C语言实现。
C语言设计一个人机对战的五子棋程序摘要:五子棋是一种受大众广泛喜爱的游戏,这里介绍五子棋程序的数据结构、评分规则、胜负判断方法,重点分析了搜索,并在传统的博弈算法在五子棋应用中进行一些改进,从而使剪枝更有效,运算性能更好。改进包括:不使用closed表;改变棋盘搜索顺序;增加记录最大棋盘信息的指针。实验证明,这几点改进对提高效率有很高帮助。
关键词:五子棋;极大极小值;剪枝;算法改进
近来随着计算机的快速发展,各种棋类游戏被纷纷请进了电脑,使得那些喜爱下棋,又常常苦于没有对手的棋迷们能随时过足棋瘾。而且这类软件个个水平颇高,大有与人脑分庭抗礼之势。其中战胜过国际象棋世界冠军-卡斯帕罗夫的“深蓝”便是最具说服力的代表;其它像围棋的“手淡”、象棋的“将族”等也以其优秀的人工智能深受棋迷喜爱;而我们今天将向大家介绍的是五子棋的算法。   当我们与电脑对战时,您知道这些软件是怎样象人脑一样进行思考的吗?在这里就以此为例和大家一起探讨探讨。
为了使读者对五子棋搜索复杂度有个形象的认识,举一个中国象棋跟五子棋搜索次数的比较(如图)。可以看出同中国象棋相比,五子棋的分支系数大的多,而且胜负条件判断也复杂一些。在极大的分支系数下,搜索程序的最大搜索深度增加1层,耗费的运算时间都将大量增加。因此设计出一个有效的搜索算法是非常重要的。
某方将帅丧失
某方五个棋子连成一线
文章的组织如下:首先简单介绍用C语言作图的基本方法(Turbo C 2.0环境)以及主循环控制下棋模块,其次介绍设计这个五子棋程序的数据结构,然后介绍了评分算法以及胜负判断,最后重点讨论实现搜索算法。
1.基本的C作图方法及主循环控制模块
Turbo C提供了非常丰富的图形函数,所有的图形函数的原型均建立在graphics.h中,在使用图形函数时要确保有显示器图形驱动程序*.BGI,同时将集成开发环境Options/Linker中的Graphics lib选为on,只有这样才能保证正确使用图形函数。
这个程序调用一个EGA、VGA显示器下能独立图形运行的函数。所谓独立图形运行程序,就是在编译和连接时将相应的驱动程序(*.BGI)直接装入到执行程序,从而能在独立的计算机上运行,避免需要重新编译连接才能运行(请查阅参考书1以及源码)。Turbo C进行画点、画线、封闭图形填充以及图形下文本输出只需要调用graphics.h中相关的函数。
主循环控制模块:控制下棋顺序,当轮到某方下子时,负责将程序转到相应的模块中去,主要担当一个调度者的角色。这个五子棋程序是用键盘控制下棋,所以要用到Turbo C中的bios.h。在一个循环块中等待键盘信息,判断键盘所输入的信息是否需要响应,调用相关的代码进行下棋(参考源码中的main函数部分)。
2.五子棋基本数据结构
为整个棋盘建立一张表格用以记录棋子信息,使用一个15*15的二维数组 chessman[15][15] (15*15是五子棋棋盘的大小),数组的每一个元素对应棋盘上的一个交叉点,用“0”表示空位、“1”代表己方棋子、“2”代表对方棋子。这张表也是今后分析的基础。其次要建立一个结构,主要用于搜索过程中,定义如下:
typedef struct five_chess*
struct five_chess{
int chess[LENGTH][LENGTH];
int record[LENGTH][LENGTH];
x,y表示在某个位置上扩展出来的新节点,layer是表示第几层扩展,用于控制扩展深度。value表示该点上极大极小值,score表示叶子节点的得分,用于推算父辈节点的value,chess这个二维数组表示扩展出来的棋盘信息,record记录在x、y点上扩展过的节点,如果没有扩展record中对应某个值为0。如果record中没有可以扩展的节点,那么该层扩展结束,返回一个特定值。
数组和一个结构构成了程序的基本数据骨架,今后只要再加入一些辅助变量便可以应付自如了。
3.评分规则以及胜负判断
评估一个棋盘的分数,主要通过扫描整个棋盘,对每个点评分。对某个点上评分从四个方向(角度分别为0、45、90、135的四个方向)分别统计,进而累积该点总分,最后得到整个棋盘的分数。实际上对当前的局面按照下面的规则的顺序进行比较,如果满足某一条规则的话,就给该局面打分并保存,然后退出规则的匹配。注意这里的规则是根据一般的下棋规律的一个总结,在实际运行的时候,用户可以添加规则和对评分机制加以修正(源码中选用了其中部分规则)。评分规则如下:
l判断是否能成5, 如果是机器方的话给予30000分,如果是人方的话给予-30000 分;
l判断是否能成活4或者是双死4或者是死4活3,如果是机器方的话给予10000分,如果是人方的话给予-10000分
l判断是否已成双活3,如果是机器方的话给予5000分,如果是人方的话给予-5000 分
l判断是否成死3活3,如果是机器方的话给予1000分,如果是人方的话给予-1000 分
l判断是否能成死4,如果是机器方的话给予500分,如果是人方的话给予-500分
l判断是否能成单活3,如果是机器方的话给予200分,如果是人方的话给予-200分
l判断是否已成双活2,如果是机器方的话给予100分,如果是人方的话给予-100分
l判断是否能成死3,如果是机器方的话给予50分,如果是人方的话给予-50分
l判断是否能成双活2,如果是机器方的话给予10分,如果是人方的话给予-10分
l判断是否能成活2,如果是机器方的话给予5分,如果是人方的话给予-5分
l判断是否能成死2,如果是机器方的话给予3分,如果是人方的话给予-3分
胜负判断实际上是据当前最后一个落子的情况来判断胜负的。实际上需要从四个位置判断,以该子为出发点的水平,竖直和两条分别为 45度角和135度角的线,目的是看在这四个方向是否最后落子的一方构成连续五个的棋子,如果是的话,就表示该盘棋局已经分出胜负。
4.搜索算法的实现
α-β剪枝是在极大极小搜索算法基础上发展起来的,因此先来分析下经典的极大极小搜索过程,如下:
①T:=(s,MAX),OPEN:=(s),CLOSED:=( );开始时树由初始节点构成,OPEN表只含有s。②LOOP1:IF OPEN=( )THEN GO LOOP2;③n:=FIRST(OPEN),REMOVE(n,OPEN),ADD(n,CLOSED);④IF n可直接判定为赢、输或平局THEN f(n):=∞∨-∞∨0,GO LOOP1ELSE EXPAND(n)→{ni},ADD({
},T)IF d(ni)<k THEN ADD({},OPEN),GO LOOP1ELSE计算f(),GO LOOP1;nI达到深度k,计算各端节点f值。⑤LOOP2:IF CLOSED=NIL THEN GO LOOP3ELSE :=FIRST(CLOSED);⑥IF(∈MAX)∧(f(∈MIN)有值)THEN f():=max{f()},REMOVE(,CLOSED);若MAX所有子节点均有值,则该MAX取其极大值。IF (∈MIN)∧(f(∈MAX)有值)THEN f():=min{f()},REMOVE(,CLOSED);若MIN所有子节点均有值,则该MIN取其极小值。⑦GO LOOP2;⑧LOOP3:IF f(s)≠NIL THEN EXIT(END∨M(Move,T));s有值,则结束或标记走步。
MINIMAX过程是把搜索树的生成和格局估值这两个过程分开来进行,即先生成全部搜索树,然后再进行端节点静态估值和倒推值计算,这显然会导致低效率。为了使生成和估值过程紧密结合,采用有界深度优先策略进行搜索,这样当生成达到规定深度的节点时,就立即计算其静态估值函数,而一旦某个非端节点有条件确定其倒推值时就立即计算赋值。这就是所谓的α-β过程。α-β算法归纳如下:
α剪枝:若任一极小值层节点的β值小于或等于它任一先辈极大值居节点的α值,即α(先辈层)≥β(后继层),则可中止该极小值层中这个MIN节点以下的搜索过程。这个MIN节点最终的倒推值就确定为这个β值
β剪枝:若任一极大值层节点的α值大于或等于它任一先辈极小值层节点的β值,即α(后继层)≥β(先辈层),则可以中止该极大值层中这个MAX节点以下的搜索过程。这个MAX节点的最终倒推值就确定为这个α值。
5.算法的改进
这里的算法改进主要是集中于五子棋程序运用上的极大极小、α-β剪枝的改进。这个五子棋的算法流程图如下(以扩展两层为例):
chessman[15][15]s0five_chesman,s0
s1=top()s1-&layer1
s1-&layer1push(s1),s2=top(),s2-&layer1
s2-&layer!=-1score
s2-&layer==-1,pop()max_chess
s1-&layer=-1,max_chess
采用C语言写的代码段如下:
s0=malloc(sizeof(struct five_chess));
for(i=0;i&3000;i++)
close[i]=NULL;
for(i=0;i&LENGTH;i++)
for(j=0;j&LENGTH;j++){
s0-&chess[i][j]=chessman[i][j];
s0-&record[i][j]=chessman[i][j];
s0-&layer=0;
s0-&value=-30000;
s0-&score=-30000;
while(is_empty()!=0){
s1=expand(s0);
if(s1-&layer==-1){
close[num++]=s1;
s1-&value=30000;
s2=expand(s1);
if(s2-&layer==-1){
if(s1-&value&top()-&value){
top()-&value=s1-&
max_chess=s1;
s2-&score=score(s2-&chess);
temps=top();
if(s2-&score&temps-&value)
temps-&value=s2-&
这个程序主要特点有:
l没有使用closed表,而改用一个指针指向得分最大的棋盘信息,并且使用一个记录表登记已经扩展过的结点。这样就不需要对closed表进行大量的访问,很大程度上提高了搜索性能。
l在扩展结点的时候,把棋盘分成三个部分:中间层(坐标5&=x&10,5&=y&10)、第二层(2&=x&12,2&=y&12并且除去中间层的那些点),第三层(0&=x&14,0&=y&14除去中间层和第二层的结点)。把棋盘分成这样三个部分扩展的依据是:越靠近中间位置的结点得分越高,这样先从得分高的结点开始计算,那么剪枝的次数就更多,从而很大程度上提高运算效率。实际上,扩展的最佳算法是以中间结点为中心,采用螺旋式搜索,这样最大程度上提高效率。
l使用一个记录得分最高的棋盘信息的指针typedef struct five_chess *point,这点改进能节省大量空间。因为扩展过程的结点非常多,如果采用这个
【上篇】【下篇】在 SegmentFault,学习技能、解决问题
每个月,我们帮助 1000 万的开发者解决各种各样的技术问题。并助力他们在技术能力、职业生涯、影响力上获得提升。
问题对人有帮助,内容完整,我也想知道答案
问题没有实际价值,缺少关键内容,没有改进余地
并且返回两个维 求助 想不出来怎么写
答案对人有帮助,有参考价值
答案没帮助,是错误的答案,答非所问
题主的问题问的不够清楚。我假设你说的二维数组里面保存是整数,问的是找到二维数组中的最大值,并且返回一个最大值的位置。函数内部两个for循环遍历数组,能找到最大值和位置吧。返回这三个整数的办法?我猜楼主不明白这个。可以new一个整形数组,初始化为最大值及其位置,返回指针。或者,新建一个struct,定义一个全局struct变量,用最大值及其位置初始化这个struct全局变量。
答案对人有帮助,有参考价值
答案没帮助,是错误的答案,答非所问
include &stdio.h&
define COL 3
define ROW 4
int getmax(int a, int num){
for (i = 1; i & i++) {
if (*max & a[i]) {
max = &a[i];
int main(void){
int a[ROW][COL] = {{1, 2, 3}, {4, 5, 6}, {9, 8 ,7}, {0, 0, 0}};
max = getmax((int *)a, sizeof(a) / sizeof(a[0][0]));
printf("max[%d][%d]=%d", ((int)max - (int)a) / sizeof(a[0][0]) / COL,
((int)max - (int)a) / sizeof(a[0][0]) % COL, *max);
其它类型数组,照这个模板改,返回指针,很方便计算出二位数组下标
同步到新浪微博
分享到微博?
关闭理由:
删除理由:
忽略理由:
推广(招聘、广告、SEO 等)方面的内容
与已有问题重复(请编辑该提问指向已有相同问题)
答非所问,不符合答题要求
宜作评论而非答案
带有人身攻击、辱骂、仇恨等违反条款的内容
无法获得确切结果的问题
非开发直接相关的问题
非技术提问的讨论型问题
其他原因(请补充说明)
我要该,理由是:
在 SegmentFault,学习技能、解决问题
每个月,我们帮助 1000 万的开发者解决各种各样的技术问题。并助力他们在技术能力、职业生涯、影响力上获得提升。用C语言编写输入26个英文字母,倒序输出,要求使用子函数做,拜托各位帮我想想,脑子都快不够用了
本回答由提问者推荐
var sogou_ad_id=731547;
var sogou_ad_height=160;
var sogou_ad_width=690;豆丁微信公众号
君,已阅读到文档的结尾了呢~~
C语言练习题和考点分析资料(可编辑),c语言练习题,c语言编程练习题,c语言基础练习题,c语言数组练习题,c语言上机练习题,c语言编辑器,c语言期末复习资料,c语言学习资料,linux下c语言编辑器
扫扫二维码,随身浏览文档
手机或平板扫扫即可继续访问
C语言练习题和考点分析资料(可编辑)
举报该文档为侵权文档。
举报该文档含有违规或不良信息。
反馈该文档无法正常浏览。
举报该文档为重复文档。
推荐理由:
将文档分享至:
分享完整地址
文档地址:
粘贴到BBS或博客
flash地址:
支持嵌入FLASH地址的网站使用
html代码:
&embed src='http://www.docin.com/DocinViewer-4.swf' width='100%' height='600' type=application/x-shockwave-flash ALLOWFULLSCREEN='true' ALLOWSCRIPTACCESS='always'&&/embed&
450px*300px480px*400px650px*490px
支持嵌入HTML代码的网站使用
您的内容已经提交成功
您所提交的内容需要审核后才能发布,请您等待!
3秒自动关闭窗口

我要回帖

更多关于 linux 函数返回值 的文章

 

随机推荐