一道C面试题的思考

一、前言

C语言真的是学无止境的感觉,大部分同学大学都会开设C语言课程。很多人把C语言二级过了就感觉入门了;对于那些在做嵌入式开发的工程师,几乎每天都要接触C语言,很多人会感觉自己C语言学得很溜了。那好,咱们用一道C语言面试题来测试一下。

二、面试题

首先给出题目:
定义一个宏,求两个数中的最大数

OK,很多人应该能很快写出

#define  MAX(x,y)  x > y ? x : y

接下来我们写一个测试程序

#define MAX(x,y) x > y ? x : y
int main(void)
{
    printf("max=%d",MAX(1,3)); //测试通过
    printf("max=%d",MAX(4,1));//测试通过
    printf("max=%d",MAX(2,2));//测试通过
    printf("max=%d",MAX(3!=3,1!=2)); //好像不是我们要的结果
    return 0;
}

我们会发现第四个测试不是我们的要结果了。这是因为宏展开后,就变成了这个样子:

printf("max=%d",3!=3>1!=2?3!=3:1!=2);

这个时候大于号(>)的优先级更高,所以就出现了问题了。

优化上面的代码

可能很多人已经想到了解决方法了,比较有经验的工程师基本也比较少犯上面的错误。
加上括号就可以解决上面的问题了。

#define MAX(x,y) (x) > (y) ? (x) : (y)

OK,接下来我们再写一个测试程序

#define MAX(x,y) (x) > (y) ? (x) : (y)
int main(void)
{
    printf("sum =%d", 7 + MAX(3,4));
    return 0;
}

运行结果:
在这里插入图片描述
并不是我们所期望的11。我们将其展开后为:

7 + (3) > (4) ? (3) : (4);

这个时候加号(+)的优先级又比大于号(>)高,所以就出现了这种结果。

那我们就继续加个括号

#define MAX(x,y) ((x) > (y) ? (x) : (y))

到这里算是比较完整的了,在面试中要是能写出这个,那算基本功还是比较扎实的了。

那我们再写一个测试程序

#define MAX(x,y) ((x) > (y) ? (x) : (y))
int main(void)
{
    int i = 3;
    int j = 4;
    printf("max=%d",MAX(i++,j++));
    return 0;
}

运行结果:
在这里插入图片描述
这里面的j会做两次自增运算, 所以打印出来的结果是做了一次自增后的结果。

继续优化

#define MAX(type,x,y)({     \
    type _x = x;        \
    type _y = y;        \
    _x > _y ? _x : _y; \
})
int main(void)
{
    int i = 4;
    int j = 5;
    printf("max=%d\n",MAX(int,i++,j++));
    printf("max=%f\n",MAX(float,3.2,3.4));
    return 0;
}

到这里基本算比较完美了!是不是很折腾, 程序的bug就是这样一步一步修复的过程。

三、总结

如果你能一下就写出最后的代码,那说明你确实是666了,通过上面的一步一步分析是为了告诉大家,C语言真的有很多东西可以让我们去琢磨!我们也还有很长的路要走。

欢迎大家关注我的微信公众号!!
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值