C语言摘录.docx
- 文档编号:595578
- 上传时间:2023-04-29
- 格式:DOCX
- 页数:27
- 大小:25.70KB
C语言摘录.docx
《C语言摘录.docx》由会员分享,可在线阅读,更多相关《C语言摘录.docx(27页珍藏版)》请在冰点文库上搜索。
C语言摘录
乘除从右到左?
1.题目:
请补充函数fun(char *s),该函数的功能是把字符串中的内容逆置。
例如:
字符串中原有的字符串为abcde,则调用该函数后,串中的内容为edcba。
注意:
部分源程序如blank.c给出。
请勿改动主函数main和其他函数中的任何内容,仅在fun函数的横线上填入所编写的若干表达式或语句。
#include
#include
#include
#defineN81
voidfun(char*s)
{
inti=0,t,n=strlen(s);
for(;___1___;i++)
{
t=*(s+i);
___2___;
___3___;
}
}
main()
{
chara[N];
clrscr();
printf("Enterastring:
");
gets(a);
printf("Theoriginalstringis:
");
puts(a);
fun(a);
printf("\n");
printf("Thestringaftermodified:
");
puts(a);
}
3
分析:
将字符串中的内容逆置主要思路分析如下:
(1)在字符串第一个字母位置和最后一个字母位置各自设置一个指示器A和B,它们分别指向第一个字母和最后一个字母,然后A位置的字母和B位置的字母进行互换。
(2)互换结束之后指示器A移动到第二个字母,而指示器B移动到倒数第二个字母,即指示器A往后移动一个字母位置,而指示器B往前移动一个字母位置,然后A位置的字母和B位置的字母进行互换。
(3)互换结束之后指示器A往后再次移动一个字母位置,而指示器B再次往前移动一个字母位置,然后A位置的字母和B位置的字母进行互换。
(4)以上过程反复进行,只有指示器B的位置小于指示器A的位置,即指示器B指向的位置在指示器A指向的位置的左边的情况下才结束,所以以上过程可以使用循环语句实现,循环终止条件可以判断指示器B的位置是否小于指示器A的位置。
为了实现以上思路,我们观察fun函数。
fun函数的功能就是将传入的s参数作为字符串进行内容逆置,它的逆置方法和我们分析的思路是一致的。
它使用了for循环语句进行循环,循环体中使用指针s+i作为指示器A,而指示器B使用s+n-1-i表示。
其中i每次循环加一,而n=strlen(s),为传入的字符串的长度。
strlen函数可以得到s参数的字符串中包含的字母个数。
为什么指针s+i可以作为指示器A呢?
由于指针s对应main函数传入的a数组,而C语言中数组名称就是一个指向数组第一个元素的指针,所以数组a的名称a就是一个char类型的指针,即为char*a;。
所以指针s指向传入的字符串的第一个字母,所以可以使用s作为指示器A的初始值。
而每次循环i都加一,在C语言语法中,一个指针加上一个整数表示一个新指针,该指针指向原指针向后移动所加上整数个数的位置,所以s+1指向字母"b",s+2指向字母"c",依次类推。
那为什么s+n-1-i可以作为指示器B呢?
如果传入的字符串为"abcde",s指针指向字母"a",n为字符串为"abcde"的长度,即字符串"abcde"的字母个数,即为5。
一个指针加上一个整数表示一个新指针,该指针指向原指针向后移动所加上整数个数的位置,所以s+5表示指向从字母"a"向后移动5个位置的新指针,即字母"e"后面一个位置,而我们希望指示器B指向字母"e",所以s+n-1才是指示器B的初始值。
每次循环i都加一,在C语言语法中,一个指针减去一个整数表示一个新指针,该指针指向原指针向前移动所减去整数个数的位置。
例如s+n-1指向字母"e",s+n-1-1指向字母"d",s+n-1-2指向字母"c",依次类推。
进行逆置的for循环终止条件是判断指示器A的位置是否在指示器B的位置的右边,那么循环继续的条件就是指示器A的位置应该在指示器B的位置的左边。
根据C语言的语法,指针P1在指针P2的左边可以使用P1 所以fun函数第一个填空处应该填写指示器A<指示器B,即s+i 分析到这里,fun函数剩下的两个填空应该填写什么呢? for循环体中应该进行指示器A和指示器B两个位置的字母互换。 t=*(s+i);语句先把指示器A位置的字母保存在t变量中,然后将指示器B位置的字母覆盖指示器A位置的字母,然后将预先保留在t变量中的指示器A位置的字母覆盖指示器B位置的字母,这样即完成两个位置的字母互换。 根据C语言的语法,取得指针指向位置的值应该使用*运算符。 所以指示器A位置的字母使用*(s+i)表示,而指示器B位置的字母使用*(s+n-1-i)表示,所以第二处填空处应该填写*(s+i)=*(s+n-1-i),而第三处填空处应该填写*(s+n-1-i)=t。 程序注解如下: #include #include #include #defineN81 /*fun函数的功能是把字符串中的内容逆置*/ voidfun(char*s) { /*定义存放要逆置的字符串的字符数组*/ inti=0,t,n=strlen(s); for(;s+i { t=*(s+i); *(s+i)=*(s+n-1-i); *(s+n-1-i)=t; } } main() { /*定义存放要逆置的字符串的字符数组*/ chara[N]; /*clrscr函数定义在conio.h头文件中,所以需要#include /*clrscr函数的作用是进行清屏*/ /*所谓清屏是指将已经显示在DOS窗口的所有内容清除*/ clrscr(); /*在已经进行清屏的DOS窗口中显示"Enterastring: "的提示信息*/ printf("Enterastring: "); /*gets函数定义在stdio.h头文件中,所以需要#include /*gets函数的作用是接收用户从键盘上输入字符串,然后放入参数a数组中*/ gets(a); /*在DOS窗口中显示"Theoriginalstringis: "的提示信息*/ printf("Theoriginalstringis: "); /*puts函数定义在stdio.h头文件中,所以需要#include /*puts函数的作用是将参数a数组中的内容输出到DOS窗口*/ puts(a); /*fun函数的作用是将a数组中的字符串进行逆置*/ fun(a); /*输出换行符,可以使DOS窗口输出信息的位置移动到下一行*/ printf("\n"); /*在新的一行输出"Thestringaftermodified: "提示信息*/ printf("Thestringaftermodified: "); /*输出参数a数组中的内容,即进行逆置之后的结果*/ puts(a); } 2. 请补充函数fun,它的功能是: 计算并输出n(包括n)以内能被3或7整除的所有自然数的倒数之和。 例如,在主函数中从键盘给n输入30后,输出为: s=1.226323。 注意: 部分源程序如blank.c给出。 请勿改动主函数main和其他函数中的任何内容,仅在fun函数的横线上填入所编写的若干表达式或语句。 #include doublefun(intn) { inti; doublesum=0.0; if(n>0&&n<=100) { for(i=1;i<=n;i++) if(i%3==0||i%7==0) sum+=1.0/i; } returnsum; } main() { intn; doubles; printf("\nInputn: "); scanf("%d",&n); s=fun(n); printf("\n\ns=%f\n",s); } 3. 题目: 给定程序的功能是分别统计字符串中大写字母和小写字母的个数。 例如,给字符串ss输入: AaaaBBb123CCccccd,则输出结果应为: upper=5,lower=9。 注意: 部分源程序如blank.c给出。 请勿改动主函数main和其他函数中的任何内容,仅在横线上填入所编写的若干表达式或语句。 #include voidfun(char*s,int*a,int*b) { while(*s) { if(*s>='A'&&*s<='Z') ___1___; if(*s>='a'&&*s<='z') ___2___; s++; } } main() { char s[100]; int upper=0,lower=0; printf("\nPleaseastring: "); gets(s); fun(s, &upper,&lower); printf("\nupper=%d lower=%d\n",___3___); } 分析: 题目要求统计字符串中大写字母和小写字母的个数,所以在main函数中使用gets函数接收从键盘上输入的字符串s,然后将s传入fun函数,在fun函数中统计传入的字符串s中大写字母和小写字母的个数。 这里需要注意的是在main函数中upper、lower变量分别记录大写字母和小写字母的个数。 这两个int类型的变量要在fun函数中统计字符串s中大写字母和小写字母的个数的时候进行增加的,然后退出fun函数回到main函数中upper、lower变量应该分别是大写字母和小写字母的个数。 然而,根据C语言的语法,普通int类型的变量的值在某函数(例如fun函数)中进行变化之后退出该函数,在main函数中该变量将丢失在那个函数(例如fun函数)的变化而直接恢复到进入函数(例如fun函数)之前的值,也就是说在函数(例如fun函数)的变化都是无效的。 这显然不是我们所希望的,因为我们希望在fun函数中统计大小写字母的过程中upper、lower变量的值得到改变,退出fun函数直接输出upper、lower变量就可以看到大小写字母的个数了。 那如何解决这种问题呢? 根据C语言的语法,以上问题可以通过使用指针解决。 以上的问题是由于参数传递方式为传值方式所导致的,可以通过将传入的参数改为指针类型改变参数传递方式为传地址方式。 所以fun函数的函数头为以下: voidfun(char*s,int*a,int*b) 分别对应upper、lower的a变量和b变量为指针类型,相应的main函数中传入fun函数的参数为&upper,&lower。 这样在fun函数中操作a、b指针才能达到预期效果。 在fun函数中,a指针所指向的内存地址中存放了记录大写字母个数的值,而b指针所指向的内存地址中存放了记录小写字母个数的值。 在fun函数中,我们通过*a、*b引用a、b指针所指向的内存地址中存放的大、小写字母个数的值,当发现大写或者小写字母的时候将*a或者*b加一。 退出fun函数的时候,形式参数a、b由于超出作用域而消失,但是它们指向的内存地址中的值还保留着,这些值在main函数中可以分别通过upper、lower引用,从而解决了函数参数退出函数之后恢复原值的问题。 程序注解如下: #include /*s参数表示传入的字符串,a、b参数表示大写字母和小写字母的个数*/ /*s是一个指针,指向传入的字符串的第一个字母*/ voidfun(char*s,int*a,int*b) { /*while(*s)是while(*s! =’\0’)的简写方式*/ /*s指针指向的字母不为’\0’,就是说循环检查到字符串结束符才退出循环*/ while(*s) { /*判断s指针指向的字母是否是大写字母,如果是就把*a加一*/ if(*s>='A'&&*s<='Z') (*a)++; /*判断s指针指向的字母是否是小写字母,如果是就把*b加一*/ if(*s>='a'&&*s<='z') (*b)++; /*s指针往后移动一个字母位置,准备判断下一个字母是否为大小写字母*/ s++; } } main() { char s[100]; /*upper、lower变量分别记录大写字母和小写字母的个数*/ int upper=0,lower=0; printf("\nPleaseastring: "); /*gets函数定义在stdio.h中,所以需要#include /*gets函数接收键盘输入的字符串,将其放入参数s数组中*/ gets(s); /*取存放upper变量、lower变量的地址,将其作为指针传入fun函数*/ fun(s, &upper,&lower); /*输出在fun函数中改变的upper、lower变量,也就是大小写字母个数*/ printf("\nupper=%d lower=%d\n",upper,lower); } 14 #include #include voidfun(char*s) { /*i变量指示小写字母插入字符串s的位置,初始值为0,表示第一个位置*/ inti=0; /*初始化p指针,将其指向s字符串第一个字符*/ char*p=s; /*while(*p)是while(*p! ='\0')的简写方式*/ /*while循环中p指针不断往后移动,逐一检查所指字符是否是小写字母*/ while(*p) { /*判断p指针所指向的字符是否是小写字母*/ /*判断依据是p指针所指向的字符的ASCII码值是否在'a'和'z'之间*/ if(*p>='a'&&*p<='z') { /*是小写字母,则将其放入字符串s的前面部分,位置由i决定*/ s[i]=*p; /*i加一,为下一个小写字母指示在字符串s中的存放位置*/ i++; } /*p指针往后移动,指向下一个字符位置的字符*/ p++; } /*在提取出来的小写字母的后面加上字符串结束标记'\0'*/ /*这样才能形成新的字符串,并取代原字符串*/ s[i]='\0'; } main() { charstr[80]; /*clrscr函数用于清除输出窗口中已经显示的内容*/ /*clrscr函数定义在conio.h,所以需要#include /*在输出窗口输出提示信息"Enterastring: "*/ printf("\nEnterastring: "); /*使用gets函数接收键盘输入的字符串,输入的字符串存入str数组*/ /*gets函数定义在stdio.h中,所以需要#include gets(str); /*将键盘输入的字符串输出在输出窗口*/ printf("\n\nThestringis: \%s\n",str); /*将键盘输入的字符串传入fun函数进行处理*/ fun(str); /*将fun函数处理结果输出在输出窗口*/ printf("\n\nThestringofchangingis: \%s\n",str); } 15. 15 分析: 题目要求判断字符ch是否与串str中的某个字符相同;若相同,什么也不作,若不同,则插在串的最后。 我们可以使用指针在字符串中从第一个字符开始向后面移动,程序检查指针在移动过程中所指向的字符是否与字符ch相同,如果发现有不同的字符则将指针不断往后移动。 这样的结果分为以下两种: (1)在str字符串后面发现和ch字符相同的字符,那么停止往后移动指针,进入判断if(*str! =ch),由于ch字符与str指针当前指向的字符相同,则if语句的条件不能得到满足,fun函数执行结束,体现了题目关于"若相同,什么也不作"的要求。 (2)在str字符串后面一直没有发现和ch字符相同的字符,那么指针str一直往后移动到字符串的结束标记'\0'。 此时str[0]表示的是字符串最后的'\0'。 设置str[0]为ch字符,从而将ch字符插入原字符串的最后。 设置str[1]为字符串结束标记'\0',从而声明了新的字符串的最后位置。 这里需要注意以下C语言的语法: 数组名同时也是指向数组第一个元素的指针。 如果这个指针在数组中移动,该指针所指向的数组元素则成为新数组的第一个元素。 为了说明这个问题,可以看以下程序。 voidfunc(char*b) { printf("str=%s\n",b); b++; printf("str=%s\n",b); b[0]='k'; printf("str=%s\n",b); } main() { chara[]="abcd"; func(a); } 在func函数中两次输出结果如下: str=abcd str=bcd str=kcd 以上程序在func函数中将b指针往后移动一个字母,而b参数代表main函数的a数组名的,所以此时b指向的字符串为"bcd",b[0]='b',b[0]='c',b[0]='d'。 执行b[0]='k';之后,b向的字符串为"kcd"。 这里掌握的原则就是指针同时可以理解为数组名,数组名同时也可以理解为指针,这正是C语言灵活的地方。 程序注解如下: #include #include /*fun函数判断字符串str中是否存在某一个字符与字符ch相同*/ /*若存在相同,什么也不作。 若不存在,则将字符ch插在字符串str的最后*/ voidfun(char*str,charch) { /*while(*str&&*str! =ch)相当于while(*str! ='\0'&&*str! =ch)*/ /*在str中找不到和字符ch相同的字符,则指向字符串的str指针往后移动*/ while( *str&&*str! =ch)str++; /*在str中找不到和字符ch相同的字符,将ch字符放入字符串的最后*/ if(*str! =ch) { /*经过以上移动,str指针已经移动到字符串的最后位置的结束标记位置*/ /*例如,字符串为"abc",此时str指向字符c后面的'\0'*/ /*由于数组名同时也是指针,所以str[0]表示的是"abc"最后的'\0'*/ /*将ch字符覆盖字符串"abc"最后的'\0'*/ str[0]=ch; /*字符串结束标记'\0'也可以用0来表示,两者值是一样的*/ /*在ch字符后面设置字符串结束标记'\0'的值,切断后面字符,形成新串*/ str[1]=0; } } main() { char s[81], c; printf("\nPleaseenterastring: \n"); gets(s); printf("\nPleaseenterthecharactertosearch: "); /*getchar函数用于从键盘上输入一个单一的字符,输入的字符被返回给c*/ c=getchar(); fun(s,c); printf("\nTheresult is%s\n", s); } 18 分析: 题目要求查找str字符串中值为x的元素,返回找到值为x的元素个数,并把这些值为x的元素下标依次保存在数组bb中。 程序注解如下: #include #include #defineN20 /*bb数组中存放str字符串中和ch字符相同的字符的下标*/ /*bb数组可以容纳20个元素,这里只要个数大小足够大就可以了*/ intbb[N]; intfun(char*str,charch) { /*i是记录p指针所指字符在str字符串中的下标*/ /*str是字符串,同时也是数组,下标从0开始,所以i初始值设置为0*/ /*n是记录bb数组中下一个新加入的下标保存到的位
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 语言 摘录