1.下面程序把“hello”这个字符输出,请指出其中的错误:
void Test()
{
char pcArray[10];
strncpy(pcArray, "hello", 5);
printf("%s\n", pcArray);
return;
}
问题: 不会直接输出"hello"的,hello的后面还可能有随机值
原因:因为strncpy的第三个参数指定为5时,只拷贝5个字符即h、e、l、l、o,后面没有拷过去‘\0’,所以当pcArray这个数组的内容是随机值的时候,只覆盖前5个,后面的内容没有找到‘\0’,所以输出的是随机值。
修改:把5改为6
2.
#define BUFFER_SIZE 256
void GetMemory(char **ppszBuf)
{
if(NULL==ppszBuf)
{
assert(0);
return;
}
ppszBuf = (char *)malloc(BUFFER_SIZE);
return;
}
void Test()
{
char *pszBuf = NULL;
GetMemory(&pszBuf);
strncpy(pszBuf, "hello world\r\n");
printf("%s ", pszBuf);
free(pszBuf);
return;
}
问题: ①程序执行过程中会发生崩溃 ②程序中有内存泄露
原因①:GetMemory函数在实现的时候并没有把动态开辟空间的地址存放到pszBuf中,所以strcpy拷贝时,pszBuf依然为 NULL,拷贝失败
原因②:GetMemory函数在返回之后,动态开辟的内存地址存放在ppszBuf指针变量中,但函数返回之后ppszBuf变量销毁,发生内存泄露
修改:在GetMemory函数内部,把动态开辟的内存的地址存放在*ppszBuf中
3.请指出下面这段程序中的错误:
unsigned long FUNC_B(unsigned long ulCount)
{
unsigned long ulSum = 0;
while (0 <= ulCount)
{
ulSum += ulCount;
ulCount;
}
return ulSum;
}
问题: 会出现死循环
原因:因为unsigned long ulCount为无符号数,而无符号数是恒大于0的,即ulCount>=0恒成立,因此会出现死循环
4.下面程序期望输出str=hello world,指出其中错误
char* GetStr(char *p)
{
p = "hello world";
return p;
}
void main()
{
char *str = NULL;
if (NULL != GetStr(str))
{
printf("\r\n str=%s", str);
}
return;
}
问题:当GetStr函数返回之后并没有接收它的返回值,所以函数返回之后并没有得到hello world的首字符的地址,str依然为空指针,所以打印时不会打印出来我们想要的内容
修改:让str接收一下GetStr函数的返回值,即把if语句括号里面的改为:NULL !(str= GetStr(str))
5.下面代码中,函数Test执行完毕后,希望输出1,指出错误:
void VarInit(unsigned char *pucArg)
{
*pucArg = 1;
return;
}
void Test()
{
unsigned long ulGlobal;
VarInit((unsigned char*)&ulGlobal);
printf("%lu", ulGlobal);
return;
}
问题:把unsigned long指针强制转换为unsigned char*指针,而unsigned char*指针解引用后,只能访问四个字节中的一个字节,所以不会输出1
6.指出下面程序错误的地方:
LONG A()
{
if (条件1)
{
return;
}
return VOS_OK;
}
VOID B()
{
if (A())
{
DoSomeThing1();
}
else
{
DoSomeThing2();
}
return;
}
错误:LONG A在条件1的时候,返回的值写得不够明确,返回值不可预测
7.找出下面题目中的错误
#define ID_LEN 32
struct STR_A
{
char aucID[ID_LEN];
int iA;
};
struct STR_B
{
char *paucID;
int iB;
};
void funcA(struct STR_A stA, struct STR_B *pstB)
{
pstB->paucID = stA.aucID;
}
void main()
{
STR_A stA = { 0 };
STR_B stB;
strcpy(stA.aucID, "12345");
func(stA, &stB);
printf("%s\n", stB.paucID);
}
错误:funcA函数在调用的时候,stA采用的是值传递,所以形参stA是实参stA的一份临时拷贝,而stB传参时传的是它的地址,pstB里面存的是stB的地址,函数内部pstB->paucID指向了形参stA里面的一块临时空间,当函数返回之后,形参stA销毁,外面的stB里面的paucID保存好了形参srA里面aucID的地址,这是一个危险的操作,会导致函数返回之后paucID成为野指针。
8.
#define MAX_LEN 2
void ConvertCode(_UC *p_byte, _UC num)
{
_UL i = 0;
for (i = 0; i < num; i++)
{
p_byte[i] = ((p_byte[i] & 0xF0 >> 4) | ((p_byte[i] & 0x0F << 4);
}
}
void main()
{
_UC *str = NULL_PTR;
ConvertCode(str, MAX_LEN);
}
错误:对空指针的解引用操作,访问内存失败
9.指出下面函数的性能问题
#define MAX_PRAM_LENGTH 10000
typedef struct
{
unsigned char ucCommand;
unsigned short usLength;
unsigned char Para[MAX_PRAM_LENGTH];
}DEBUG_MSG;
void PrintDebufMsg(DEBUG_MSG DebugMessage)
{
int i;
printf("\nCommand=%d", DebugMessage.ucCommand);
for (i = 0; i < DebugMessage.usLength&&i < MAX_PRAM_LENGTH; i++)
{
printf("\nPara[%d]=0x%x", i, DebugMessage.Para[i]);
}
}
问题:结构体过大,传参时采用值传递的形式,会使得函数在调用过程中,参数压栈的系统开销过大,从而降低程序的性能。