筆者最近在閱讀《c和c++程式設計師面試祕籍》時有了一些收穫,特總結一下,分享給大家。
第一題:i++與++i的區別:
#include<stdio.h>
int main()
{
int i=8;
/*第7行*/ printf("%d
",++i);
/*第8行*/ printf("%d
",--i);
printf("%d
",i++);
printf("%d
",i--);
printf("%d
",-i++);
printf("%d
",-i--);
printf("%d
",i);
return 0;
}
建議大家先自己做一下,做過對比之後才能有驚奇的發現:
程式第7行,i先自增,再被輸出列印因此輸出為9,i的值也變為9
程式第8行,i先自減,再被輸出列印因此輸出為8,i的值也變為8
程式第9行,先列印輸出當前i的值8,i再自增,i的值變為9,大家要注意,列印和自增 的順序,千萬別入坑
程式第10行,先列印輸出當前i的值9,i再減,i的值變為8,注意同上
程式第11行,先列印-i,為-9,i再自增1,此時i的值變為9
程式第12行,先列印-i,為-8,i再自減1,此時i的值變為8
第二題:i++和++i的區別:
我查閱了一下資料,將大家的看法總結一下:
如果沒有用到返回值的話,區別在於效率。
若i是內建的數值型別,兩者完全一樣。
若i是一些自定義的類,如iterator,++i的效率 > = i++的效率對於後者推薦都用++i;對於前者,用哪個是程式風格問題,i++的好處是更符合人類思維習慣,++i的好處是每次都用這種形式就不用考慮i的型別。
大家需要注意的是,字首式(++i)可以返回物件的引用,而字尾(i++)必須返回物件的值,所以在大物件的時候產生複製開銷,引起效率低。
答案如下:
內建資料型別的情況,效率沒有區別
自定義資料型別的情況,++i的效率較高
第三題:有符號變數與無符號變數的值的轉換:
#include<stdio.h>
char getChar(int x,int y)
{
char c;
unsigned int a = x;
(a+y>10)?(c = 1):(c = 2);
return c;
}
int main()
{
char c1 = getChar(7,4);
char c2 = getChar(7,3);
char c3 = getChar(7,-7);
char c4 = getChar(7,-8);
printf("c1 = %d
",c1);
printf("c2 = %d
",c2);
printf("c3 = %d
",c3);
printf("c4 = %d
",c4);
return 0;
}
這題的考點是當表示式中存在有符號型別和無符號型別時,所有的運算元都自動轉化成無符號數,也就是原數的補碼
c1 = 1
c2 = 2
c3 = 2
而c4 = 1
因為-8的原碼是1000_1000,補碼為1111_1000
與7相加0000_0111值為1111_1111差1就正好溢位。
第四題:不使用任何中間變數將a,b中的值進行交換
法一:
#include<stdio.h>
void swap1(int a,int b)
{
a =a+b;
b =a-b;
a =a-b;
printf("after swap
");
printf("a1 = %d,b1 = %d",a,b);
};
int main()
{
int a1 =1,b1 =2;
swap1(a1,b1);
return 0;
}
此時輸出結果為a1 =2,b1 =1;
法二:
#include<stdio.h>
void swap2(int a,int b)
{
a =a^b;
b =a^b;
a =a^b;
printf("after swap
");
printf("a1 = %d,b1 = %d",a,b);
};
int main()
{
int a2 =3,b2 =4;
swap2(a2,b2);
return 0;
}
此時輸出結果為a2 =4,b2 =3;
總結一下,法一採用了加減法來達到交換a,b的目的。這種方法的缺點是a+b,和a-b運算時可能會導致溢位
法二,採用按位異或的方式交換a,b。按位異或運算子”^”的功能是將參與運算的兩數各對應的二進位制位相異或,如果對應的二進位制位相同,則為0,不同為1。這樣運算三次就可交換a,b的值。