目录
12、用预处理指令#define 声明一个常数,用以表明1 年中有多少秒(忽略闰年问题)
13、写一个" 标准" 宏MIN ,这个宏输入两个参数并返回较小的一个。
15、嵌入式系统中经常要用到无限循环,你怎么样用C编写死循环呢?
1、考察指针偏移和栈的知识
2、大小端问题导致的输出不确定
char c ;
int i;
i = c = -125 ;
printf("%d \n " , i ) ;
A:一定输出-125
B:一定不能输出-125
C:可能输出-125 // 正选
D:输出%d
解答:本题乍一看,输出-125! 再仔细一看 char类型表示范围是-128~127之间,也没有溢出。但其实这里考察的点不在这里,因为这里没有指明具体的运行平台,在aInt = aChar = -120这行代码中,aInt = aChar这里将8字节数据的char类型变量放到32个字节的int变量中,因为大小端存储导致不同的结果,即-120这个数字对应的八个位的二进制码是放到int变量的高位还是低位。
当然肯定是会编译过去的,对于本人是在Win7下(小端)运行的,结果妥妥的为-125;
3、strcpy 使用时需要注意的问题
//问:下面是一个简单的密码保护功能,你能在不知道密码的情况下将其破解吗?
#include<stdio.h>
int main(int argc, char *argv[])
{
int flag = 0;
char passwd[10];
memset(passwd,0,sizeof(passwd));
strcpy(passwd, argv[1]);
if(0 == strcmp("LinuxGeek", passwd))
{
flag = 1;
}
if(flag)
printf("\n Password cracked \n");
else
printf("\n Incorrect passwd \n");return 0; }
//破解上述加密的关键在于利用攻破strcpy()函数的漏洞。所以用户在向“passwd”缓存输入随机密码的时候并没有提前检查“passwd”的容量是否足够。
//所以,如果用户输入一个足够造成缓存溢出并且重写“flag”变量默认值所存在位置的内存的长“密码”,即使这个密码无法通过验证,flag验证位也变成了非零,也就可以获得被保护的数据了。
//应对策略:建议使用 strncpy()函数
4、main()的返回类型
//下面的代码能 编译通过吗?如果能,它有什么潜在的问题吗?
void main(void) // int main()更佳
{
char *ptr = (char*)malloc(10);
if(NULL == ptr)
{
printf("\n Malloc failed \n");
return;
}
else
{
// Do some processing
free(ptr);
}
return;
}
//这段代码的错误在大多数编译器里会被当作警告。main()的返回类型应该是“int”而不是“void”,好多人都习惯写成void,
因为“int”返回类型会让程序返回状态值。
5、这段代码会输出什么?(作用域)
//这段代码会输出什么?
int i = 2 , j ,k ;
int main(void)
{
int i , j = j ; // 打印输出的话i=2,j=0
printf("%d\n" , j ) ;
// 打印输出的话i和j为随机值
j = i ++ ;
if( i + j < 3)
int k = 1 ;
printf("%d\n" , k++ ) ;
return 0 ;
}
答案:未定义,0
// 分析 :main函数中重新声明变量i和j,i,j的值未初始化,因此用j给本身赋值结果未定义
// if语句中声明k变量,此时k变量的作用域仅到if语句结束
6、以下代码中的两个sizeof用法有问题吗?
//数组作为参数传给函数时传的是指针而不是数组,传递的是数组的首地址
void Upper( char str[] ) // 将str中的小写字母转换为大写字母 这里可以将长度传进来
{
cout <&l