西邮Linux兴趣小组2024纳新面试题
西邮Linux兴趣小组2024纳新面试题0.聪明的吗喽猴子每走一米会消耗掉三根香蕉分别是往前走一米会消耗一根返回起点会消耗一根再搬另外50根会再消耗一根一共消耗三根所以我们只需要找到一个中转站使香蕉的数量小于50根便不会进行往返所以我们走的路程消耗的香蕉要大于50根一米消耗三根所以在50/3约等于17米处作为中转站刚好使剩下的香蕉为49根小于50根则剩下的49根香蕉我们可以直接带回去后面剩余50-1733米每走一米消耗一根香蕉所以最后猴子剩余49-3316根香蕉。1.西邮Linux欢迎你啊int main(){ unsigned int a2024; for( ;a0;a--) printf(%d\n,printf(Hi guys! Join Linux-2%d,printf())); return 0; }unsigned是无符号类型的所以a是永远大于0的所以for循环会一直执行for中的输出是一个嵌套先看最里面的输出的是 输出了0个字符所以%d是0,在printf里面的一共有24个字符所以在输出24,所以输出的%d是2024,而for是一直循环的所以本题代码会一直输出Hi guys! Join Linux-2024。2.眼见不一定为实intmain(){charp0[]I love Linux;constchar*p1I love Linux\0Group;charp2[]I love Linux\0;printf(%d\n%d\n,strcmp(p0,p1),strcmp(p0,p2));printf(%d\n%d\n,sizeof(p0)sizeof(p1),strlen(p0)strlen(p1));return0;}sizeof:运算符计算整个占用的字节包扩字符串中的’\0’strlen库函数统计’\0’之前的字节数第一个输出中比较p0与p1strcmp是比较到第一个’\0’之前所以p0与p1是相等的所以输出0,第二个输出中在’\0’之前也是相等的所以也输出0,第三个输出sizeof是包含整个的p2明显比p1的长所以两个不相等所以输出的是0,第四个输出中是比较p0与p1在’\0’之前的的有效长度两个有效长度相等所以输出1。所以最后输出0 0 0 1。3. 1.1-1.0!0.1intmain(){floata1.0,b1.1,ex0.1;printf(b-aex is %s\n,(b-aex)?ture:false);intAa*10,Bb*10,EXex*10;printf(B-AEX is %s\n,(B-AEX)?ture:false);}float是二进制浮点数所以在运行过程中我们会先将变量转换为二进制再转换过来进行运算这就导致在运算过程中变量的值是近似接近我们原先赋予的值的在第一个输出中三目运算符中b-a只能近似等于ex所以不成立输出’:后面的false,第二个输出中A为a*10变为10.0B为b *10变为11,EX为ex *10,变为10,则这三个全部变为整数整数不存在精度丢失所以三目运算符中B-AEX是正确的我们输出后面的ture,所以最后输出的是b-aex is false B-AEX is ture。4.听说爱用位运算的人技术都不太差intaverage(intnums[],intstart,intend){if(startend)returnnums[start];intmid(startend)/2;intleftAvgaverage(nums,start,mid);intrightAvgaverage(nums,mid1,end);return(leftAvgrightAvg)((leftAvg^rightAvg)1);}mid(startend)/2是算出数中的中间便于后面进行分开然后使用递归将整个分为了两部分并求出两部分的平均值一部分是leftavg,一部分是rightavg最后返回的第一个括号内如果两个二进制的对应位都是1,则相加为10,进一位第二个括号内对应位为一个0,一个1,相加结果为一留在本位整个推导过程便是ab(ab)*2(a^ b),(ab)/2(ab)((a ^ b)1),最后得出平均数第一个if是如果左边的平均数与右边的平均数这两个数字相等便结束这也意味着这个数字就是我们要求的平均数。优点如果ab是一个超出int范围内的值的话普通求平均值会栈溢出而这个函数避免了两个数字的相加从而可以得到结果缺点这个让人不容易理解且代码不适合小数平均数。5.全局还是局部inti1;staticintj15;intfunc(){inti10;if(i5)i;printf(i%d,j%d\n,i,j);returni%j;}intmain(){intafunc();printf(a%d\n,a);printf(i%d,j%d\n,i,j);return0;}在func函数中先把10赋给i如果i大于5,则i加一所以i为11,输出了11,15,返回了i%j11在main函数中static修饰局部变量这个变量只会在开始初始化一次后面不会进行初始化所以在main函数中i1,j15,输出a的值就是函数func算出的余数11,所以a11,后面输出i的值与j的值。所以最后输出的是 i11,j15 a11 i1, j156.指针的修罗场改还是不改这是个问题intmain(intargc,char**argv){inta1,b2;constint*pa;int*constqb;*p3,qa;constint*constra;*r4,rb;return0;}const是修饰变量的被他修饰的变量是不可以被修改的而const有一个原则谁离const最近谁就会被const修饰第一个const int *pa就是指向的对象a不能被修改第二个int *const qb就是q本身不能被修改第三个const int * const ra就是两个都不能被修改所以qa与下面的两个对*r和r的改变是不合理的7.物极必返intmain(intargc,char*argv[]){while(argc0);inta1,bargc,c0;if(--a||bc--)for(inti0;argv[i]!NULL;i)printf(argv[%d]%s\n,i,argv[i]);printf(a%d,b%d,c%d\n,a,b,c);return0;}argc:命令行参数的个数 argv保存参数字符串的指针数组命令行参数有两个所以argc的初始值为2,所以while中的条件一直成立所以argc一直自增直到int的最大值后变为负数为-2147483647,再执行if里面的条件–a为前置自减得出值为0,所以条件为假继续执行||后面的b得出b-2147483646,执行c–得出c-1因为argv的输出在while条件不成立之后所以不会输出所以最后的输出为a0,b-2147483646,c-1。8.指针数组数组指针指针数组intmain(){inta[2]{4,8};int(*b)[2]a;int*c[2]{a,a1};return0;}a,a1,a,a1,*(a1),sizeof(a),sizeof(a)*b,*b1,b,b1,*(*b1),sizeof(*b),sizeof(b)c,c1,c,c1,**(c1),sizeof(c),sizeof(c)看第一组第一组的第一个是输出a也就是a的首地址a[0]所以输出4,第二个是a1则为a[1]所以输出的是8,第三个输出的是整个数组的地址类型为int(*b)[2],第四个为a1,跳过了整个数组所以地址为a2 *4a8,第五个输出 *(a1)等价于a[1]所以输出8,第六个输出a的字节a是整个数组的大小所以输出2 *48,最后一个输出的是a的字节数a的指针所以为8字节第二组中是一个数组指针第一个*b对 *b进行解引用就等价于数组a[0]得到值为4,第二个 *b1,就是a[1]偏移一个int第三个b是数组指针的值也就是a输出a的地址第四个b1跳过整个数组也就是2 *48个字节所以输出的是a8, 第五个 *( *b1)就是a[0]1得到a[1],所以输出的为8,第六个输出 *b的字节 *b就是数组a所以字节为2 *48个字节。最后一个b的字节b是指针在六十四位下是8个字节所以输出8第三组中是一个指针数组第一个c就是c的首元素地址c[0]第二个c1,就是c[1]偏移了8个字节第三个c输出的就是整个数组的地址第四个c1跳过了整个数组所以是2*816个字节第五个**(c1)最后变为 *c[1]变为a[1]所以输出8,第六个c的字节c中含有两个指针所以占了8 *216个字节最后一个c的字节数c是指针所以输出8个字节9.嘻嘻哈哈好玩好玩#defineSQUARE(x)x*x#defineMAX(a,b)(ab)?a:b;#definePRINT(x)printf(嘻嘻结果你猜对了吗包%d滴\n,x);#defineCONCAT(a,b)a##bintmain(){intCONCAT(x,1)5;intCONCAT(y,2)3;intmaxMAX(SQUARE(x11),SQUARE(y2))PRINT(max)return0;}##是宏拼接运算符是把两个标记粘在一起合成一个新名字则代码中CONCAT(x,1)为x1,同理CONCAT(y,2)y2,所以x15, y23,SQUARE(x11)因为没有括号所以运算为x11*x1111,SQUARE(y2)为y2 *y29,所以最后变为MAX(11,9),三目运算符中11大于9,所以输出后面的a所以最后输出的是11,所以最后输出嘻嘻结果你猜对了吗包11滴。10.我写的排序最快intmain(){intarr1[]{2,3,1,3,2,4,6,7,9,2,10};intarr2[]{2,1,4,3,9,6,8};intlen1sizeof(arr1)/sizeof(arr1[0]);intlen2sizeof(arr2)/sizeof(arr2[0]);result result;your_sort(arr1,len1,arr2,len2,result);for(inti0;ireslut.len;i){printf(%d,result.arr[i]);}free(result.arr);return0;}typedefstruct{int*arr;intlen;}result;voidbubble_sort(int*a,intn){for(inti0;in-1;i){for(intj0;jn-1-i;j{if(a[j]a[j1]){intaa[j];a[j]a[j1];a[j1]t;}}}}voidyour_sort(intarr1[],intlen1,intarr2[],intlen2,result*res){inttotallen1len2;int*tmp(int*)malloc(total*sizeof(int));intk0;for(inti0;ilen1;i)tmp[k]arr1[i];for(inti0;ilen2;i)tmp[k]arr2[i];bubble_sort(tmp,total);int*uniq(int*)malloc(total*sizeof(int));intuniq_len0;for(inti0;itotal;i){if(uniq_len0||tmp[i]!uniq[uniq_len-1]){uniq[uniq_len]tmp[i];}}free(tmp);res-arruniq;res-lenuniq_len;}11.猜猜我是谁intmain(){void*a[]{(void*)1,(void*)2,(void*)3,(void*)4,(void*)5};printf(%d\n,*((char*)a1));printf(%d\n,*(int*)(char*)a1);printf(%d\n,*((int*)a2));printf(%lld\n,*((longlong*)a3));printf(%d\n,*((short*)a4));return0;}第一个输出中强制将a转换为char*类型所以后面加一是向后移动一个字节void总共八个字节首地址向后移动一个字节是0,第二个输出中先取的是char*的首地址然后强制转换为Int类型加四个字节得到值为一后面再进行加一得到值为2,在第三个输出中也是先转为int*类型的后面加2代表向后移动了2 *48个字节正好到a[1]也就是(void *)2,最后输出2,第四个输出中 long long的字节为8,加三就代表移动了3*824个字节刚好移动到a[3](void *)4,所以最后输出的是4,最后一个short占据2个字节后面加4一共个移动了2*48个字节刚好跳过a[0]输出的是a[1]所以最后输出的是2所以最后输出的是0 2 2 4 212.结构体变小写奇遇记uniondata{inta;doubleb;shortc;};typedefstructnode{longlonga;uniondata b;void(*change)(structnode*n);charstring[0];}Node;voidfunc(Node*node){for(size_ti0;node-string[i]!\0;i)node-string[i]tolower(node-string[i]);}intmain(){constchar*sWELCOME TO XIYOULINUX_GROUP!;Node*p(Node*)malloc(sizeof(Node)(strlen(s)1)*sizeof(char));strcpy(p-string,s);p-changefunc;p-change(p);printf(%s\n,p-string);return0;}char string[0]是柔性数组也就是零长度数组只能放在结构体的最后一个且在计算结构体大小的时候是不将他计入计算的union是联合体他的大小取决于联合体里面最大成员的大小在代码中union里的最大成员为double占了8个字节所以union的字节为8,long long占据的字节为8,void(*change)是函数指针占据8个字节最后一个是柔性数组不计入计算所以结构体的大小是88824,主函数中先是给了一串大写字母后面malloc一次分配整个内存再用函数strcpy将s复制到柔性数组后面再将函数指针指向func函数p-change§就等价于调用funcp,在func函数中遍历整个字符串直到i为’\0’时结束循环在循环中我们将字符串中的字母全部变为小写所以最后输出的welcome toxiyoulinux_group!