下面代码的结果是:(D)
#include <stdio.h>
int main()
{
int i = 1;
int ret = (++i)+(++i)+(++i);
printf("ret = %d\n", ret);
return 0;
}
A. 10 B. 12 C. 9 D. 程序错误
答案解析:
表达式(++i)+(++i)+(++i),只有操作符的优先级和结合性,没法确定唯一计算路径
所以这个表达式可能因为计算顺序的差异导致结果是不一致的,所以表达式是错误的表达式。
可以在VS和Linux gcc测试,结果可能有差异。
关于表达式求值说法不正确的是:(D)
A. 表达式求值先看是否存在整形提升或算术转换,再进行计算
B. 表达式真正计算的时候先看相邻操作符的优先级决定先算谁
C. 相邻操作符的优先级相同的情况下,看操作符的结合性决定计算顺序
D. 只要有了优先级和结合性,表达式就能求出唯一值
答案解析:
D: 错误,有了优先级和结核性,表达式也有可能有不同的计算机路径,导致计算结果的差异。
下面代码的结果是:A
#include <stdio.h>
int i;
int main()
{
i--;
if (i > sizeof(i))
{
printf(">\n");
}
else
{
printf("<\n");
}
return 0;
}
A. > B. < C. 不输出 D. 程序有问题
答案解析:
C语言中,0为假,非0即为真。
全局变量,没有给初始值时,编译其会默认将其初始化为0。
i的初始值为0,i--结果-1,i为整形,sizeof(i)求i类型大小是4,按照此分析来看,结果应该选择B,但是sizeof的返回值类型实际为无符号整形,因此编译器会自动将左侧i自动转换为无符号整形的数据,-1对应的无符号整形是一个非常大的数字,超过4或者8,故实际应该选择A
计算求和求Sn=a+aa+aaa+aaaa+aaaaa的前5项之和,其中a是一个数字,例如:2+22+222+2222+22222
/*思路:
通过观察可以发现,该表达式的第i项中有i个a数字,因此:
假设第i项为temp,则第i+1项为temp*10+a
具体参考以下代码*/
int main()
{
int a = 0;
int n = 0;
int i = 0;
int sum = 0;
int tmp = 0;
scanf("%d%d", &a, &n);
for(i=0; i<n; i++)
{
tmp = tmp*10+a;
sum += tmp;
}
printf("%d\n", sum);
return 0;
}
打印水仙花数
求出0~100000之间的所有“水仙花数”并输出。
“水仙花数”是指一个n位数,其各位数字的n次方之和确好等于该数本身,如:153=1^3+5^3+3^3,则153是一个“水仙花数”。
/*思路:
此题的关键在于只要知道判断一个数据是否为水仙花数的方式,问题就迎刃而解。假定给定一个数据data,具体检测方式如下:
1. 求取data是几位数
2. 获取data中每个位置上的数据,并对其进行立方求和
3. 对data中每个位上的数据立方求和完成后,在检测其结果是否与data相等即可,
相等:则为水仙花数
否则:不是
具体实现参考以下代码。*/
int main()
{
int i = 0;
for(i=0; i<=999999; i++)
{
int count = 1;
int tmp = i;
int sum = 0;
//判断i是否为水仙花数
//1. 求判断数字的位数
while(tmp/10)
{
count++;
tmp = tmp/10;
}
//2. 计算每一位的次方和
tmp = i;
while(tmp)
{
sum += pow(tmp%10, count);
tmp = tmp/10;
}
//3. 判断
if(sum == i)
printf("%d ", i);
}
return 0;
}
使用指针打印数组内容
写一个函数打印arr数组的内容,不使用数组下标,使用指针。
arr是一个整形一维数组。
int main()
{
int arr[] = {1,2,3,4,5,6,7,8,9,10};
//在这里完成代码
// 分析:因为数组中存储的元素类型是int类型的,因此只要给一个int的指针,依次取索引数组中的每个元素即可
int* p = arr; // 数组名代表数组首元素的地址
for(int i = 0; i < sizeof(arr)/sizeof(arr[0]); ++i)
{
printf("%d ", *p); // *p: 取到p所指向位置的元素
++p; // 获取p的下一个位置
}
return 0;
}
下面程序要求输出结构体中成员a的数据,以下不能填入横线处的内容是(B)
#include < stdio.h >
struct S
{
int a;
int b;
};
int main( )
{
struct S a, *p=&a;
a.a = 99;
printf( "%d\n", __________);
return 0;
}
A. a.a B. *p.a C. p->a D. (*p).a
答案解析:
结构体类型变量需要访问其成员时,用.运算符,如果是指向结构体变量的指针访问时,需要用->,或者先对指针解引用,取到指向的结构体类型的变量,再通过.访问,但是要注意优先
如有以下代码:则下面的叙述不正确的是:(D )
struct student
{
int num;
char name[32];
float score;
}stu;
A. struct 是结构体类型的关键字 B. struct student 是用户定义的结构体类型
C. num, score 都是结构体成员名 D. stu 是用户定义的结构体类型名
答案解析:
A:正确,在C语言中需要自定义类型时,要用到struct关键字
B:正确:在C语言中,用struct定义的结构体,定义结构体类型变量时,需要用struct student
C:正确:结构体中的变量名称,称之为结构体的成员
D:错误:stu是定义的结构体类型变量,不是名称,如果想要让stu为结构体类型名称时,必须在结构体定义时添加 typedef关键字
关于二级指针描述描述正确的是:( B)
A. 二级指针也是指针,只不过比一级指针更大 B. 二级指针也是指针,是用来保存一级指针的地址
C. 二级指针是用来存放数组的地址 D. 二级指针的大小是4个字节
答案解析:
A:错误,二级指针是指针,不能说起比一级指针大,只能说二级指针指向的空间中存储的也是一个地址
B:正确
C:错误,数组的地址一般用一级指针存储,或者用数组指针接收
D:二级指针是指针,但是否占4个字节不一定,要看具体的系统
下面关于指针运算说法正确的是:( C)
A. 整形指针+1,向后偏移一个字节 B. 指针-指针得到是指针和指针之间的字节个数
C. 整形指针解引用操作访问4个字节 D. 指针不能比较大小
答案解析:
注意:此题是有问题的,说法不严谨,如果将整形指针理解成int*类型的指针,那么一下说法解析如下
A:错误,整形指针+1,向后便宜一个整形类型的大小,即4个字节
B:错误,两个指针相减,指针必须指向一段连续空间,减完之后的结构代表两个指针之间相差元素的个数
C:正确,整形指向的是一个整形的空间,解引用操作访问4个字节
D:指针中存储的是地址,地址可以看成一个数据,因此是可以比较大小的
下列程序段的输出结果为(C)
unsigned long pulArray[] = {6,7,8,9,10};
unsigned long *pulPtr;
pulPtr = pulArray;
*(pulPtr + 3) += 3;
printf(“%d,%d\n”,*pulPtr, *(pulPtr + 3));
A. 9,12 B. 6,9 C. 6,12 D. 6,10
答案解析:
unsigned long pulArray[] = {6,7,8,9,10};
unsigned long *pulPtr;
pulPtr = pulArray;
// 数组名代表数组首元素地址,因此pulptr指向的是数组中第一个元素的位置
*(pulPtr + 3) += 3;
// pulptr+3访问的是数组中第三个元素(数组下标从0开始),故将9改为9+3=12
printf(“%d,%d\n”,*pulPtr, *(pulPtr + 3));
// 打印第一个和第三个元素,因此:打印6和12
喝汽水问题
【题目内容】喝汽水,1瓶汽水1元,2个空瓶可以换一瓶汽水,给20元,可以多少汽水(编程实现)。
/*思路:
1. 20元首先可以喝20瓶,此时手中有20个空瓶子
2. 两个空瓶子可以喝一瓶,喝完之后,空瓶子剩余:empty/2(两个空瓶子换的喝完后产生的瓶子) + empty%2(不够换的瓶子)
3. 如果瓶子个数超过1个,可以继续换,即重复2*/
int main()
{
int money = 0;
int total = 0;
int empty = 0;
scanf("%d", &money);
//方法1
total = money;
empty = money;
while(empty>1)
{
total += empty/2;
empty = empty/2+empty%2;
}
return 0;
}
打印菱形
【题目内容】用C语言在屏幕上输出以下图案:
![](https://i-blog.csdnimg.cn/blog_migrate/61a2440342319b5f038832b18d7f3622.png)
/*思路:
仔细观察图形,可以发现,此图形中是由空格和*按照不同个数的输出组成的。
上三角:先输出空格,后输出*,每行中
空格:从上往下,一行减少一个
*:2*i+1的方式递增
下三角:先输出空格,后输出*,每行中
空格:从上往下,每行多一个空格
*: 从上往下,按照2*(line-1-i)-1的方式减少,其中:line表示总共有多少行
按照上述方式,将上三角和下三角中的空格和*分别输出即可。 */
int main()
{
int line = 0;
int i = 0;
scanf("%d", &line);//7
//打印上半部分
for(i=0; i<line; i++)
{
//打印一行
//打印空格
int j = 0;
for(j=0; j<line-1-i; j++)
{
printf(" ");
}
//打印*
for(j=0; j<2*i+1; j++)
{
printf("*");
}
printf("\n");
}
//打印下半部分
for(i=0; i<line-1; i++)
{
//打印一行
int j = 0;
for(j=0; j<=i; j++)
{
printf(" ");
}
for(j=0; j<2*(line-1-i)-1; j++)
{
printf("*");
}
printf("\n");
}
return 0;
}
字符串逆序
【题目内容】写一个函数,可以逆序一个字符串的内容。
/*思路:该题比较简单,请参考代码*/
void Reverse(char* str)
{
char* left = str;
char* right = str + strlen(str)-1;
while(left < right)
{
char temp = *left;
*left = *right;
*right = temp;
++left;
--right;
}
}
int main()
{
char str[101] = {0};
while(gets(str))
{
Reverse(str);
printf("%s\n", str);
memset(str, 0, sizeof(str)/sizeof(str[0]));
}
return 0;
}