c/c++语言开发共享在没有双重评估的情况下在Clang中实现min()和max()

min函数的经典预处理器版本看起来像

 #define min(a, b) ((a) < (b) ? (a) : (b)) 

这使你可以进行双重评估 – 你做min(f(), g()) ,忘记fg有副作用,你必须花费数小时试图找出你的函数运行两次的原因。 为了防止这种情况,你可以做到

 #define min(a, b) ({__typeof__(a) _a = (a);  __typeof__(b) _b = (b);  _a < _b ? _a : _b;}) 

这在GCC下工作得很好,但是如果你通过-Wgnu设置的Clang运行它 – 这组警告属于-pedantic的保护伞 – 你会得到像

 test.c:5:10: error: use of GNU statement expression extension [-Werror,-Wgnu] int a = min(3, 7); ^ test.c:1:22: note: expanded from macro 'min' # define min(a, b) ({__typeof__(a) _a = (a); __typeof__(b) _b = (b); _a < _b ? _a : _b;}) 

是否有可能以防止双重评估的方式定义这些宏, 并且可以接受Clang under -pedantic ? (是的,你可以用-Wno-gnu禁用警告,在这种情况下,Clang处理语句表达没有问题。我问,因为我像clang -pedantic ,对我自己的好处太挑剔了。)

编辑:我在C工作。我也标记了这个C ++,因为我认为解决方案可能适用于C ++以及C.哎呀 – 忘了模板! 抱歉模棱两可。

    如果你真的用C ++编写,那么就不要使用预处理器

     template  const T min(const T& a, const T& b) { return (b < a) ? b : a; } 

    (注意我已经交换了ba ,所以如果两者相等,你就得到左手操作数。)

    否则不,不是真的 。

    我认为这可以作为C11解决方案。

     inline int min(int const x, int const y) { return y < x ? y : x; } inline unsigned minu(unsigned const x, unsigned const y) { return y < x ? y : x; } inline long minl(long const x, long const y) { return y < x ? y : x; } inline unsigned long minul(unsigned long const x, unsigned long const y) { return y < x ? y : x; } inline long long minll(long long const x, long long const y) { return y < x ? y : x; } inline unsigned long long minull(unsigned long long const x, unsigned long long const y) { return y < x ? y : x; } inline float minf(float const x, float const y) { return y < x ? y : x; } inline double mind(double const x, double const y) { return y < x ? y : x; } inline long double minld(long double const x, long double const y) { return y < x ? y : x; } #define MIN(X, Y) (_Generic((X) + (Y),  int: min,  unsigned: minu,  long: minl,  unsigned long: minul,  long long: minll,  unsigned long long: minull,  float: minf,  double: mind,  long double: minld)((X), (Y))) 

    Simple发布的C11解决方案看起来很理想,但是如果你没有C11编译器,你仍然可以定义一个具有内在类型安全性的宏(因为无论如何都像C一样安全):

     #define MIN(type, X, Y) min_ ## type(X, Y) 

    此宏将仅允许传递已实现的类型,否则您将收到编译器错误。

    例:

     #define MIN(type, X, Y) min_ ## type(X, Y) long min_long (long x, long y); char min_char (char x, char y); float min_float (float x, float y); int main() { long min_l = MIN (long, 5L, 10L); char min_c = MIN (char, 'A', 'B'); float min_f = MIN (float, 666.66f, 3.14f); printf("%ldn", min_l); printf("%cn", min_c); printf("%fn", min_f); } char min_char (char x, char y) { return x < y ? x : y; } long min_long (long x, long y) { return x < y ? x : y; } float min_float (float x, float y) { return x < y ? x : y; } 

    现在,如果你用MIN(int, 1, 2)执行上面的宏,你会得到一个编译器错误:“ min_int ,不存在这样的函数”。

    需要了解更多c/c++开发分享在没有双重评估的情况下在Clang中实现min()和max(),也可以关注C/ C++技术分享栏目---计算机技术网(www.ctvol.com)!

      以上就是c/c++开发分享在没有双重评估的情况下在Clang中实现min()和max()相关内容,想了解更多C/C++开发(异常处理)及C/C++游戏开发关注计算机技术网(www.ctvol.com)!)。

      本文来自网络收集,不代表计算机技术网立场,如涉及侵权请联系管理员删除。

      ctvol管理联系方式QQ:251552304

      本文章地址:https://www.ctvol.com/c-cdevelopment/979060.html

      (0)
      上一篇 2021年12月12日
      下一篇 2021年12月12日

      精彩推荐