【问题标题】:Throw an error/warning when supplying wrong argument type to C function向 C 函数提供错误的参数类型时引发错误/警告
【发布时间】:2021-05-26 20:09:11
【问题描述】:

我有这个代码:

#include <stdint.h>

void something(float a);

int main()
{
   uint8_t a = 28;
   
   something(a);

   return 0;
}

void something(float a)
{
   
   printf("%f\n", a);
}

我正在使用类似的函数将不同类型的变量记录到文件中,并且我想收到一条错误/警告消息,因为我正在使用错误的参数类型调用函数 something(而不是 uint8_t浮动)。

我怎样才能做到这一点?

【问题讨论】:

  • 代码是有效的,因为 uint8_t 可以隐式转换为 float 而不会丢失价值。
  • How can I achieve this? 为什么不先创建 struct something_arg { float a; } 然后再要求 void something(struct something_arg arg)
  • @dbush 我在使用 void something (uint8_t a) 时没有收到警告;并传递一个浮点参数(除了 printf 警告)。

标签: c function gcc types


【解决方案1】:

老派的技巧是将函数更改为使用指针,因为 C 中的指针的类型规则比整数和浮点要严格得多。

#include <stdio.h>
#include <stdint.h>

void something(const float* a);

int main()
{
   uint8_t a = 28;
   
   /* gcc -std=c11 -pedantic-errors */
   something(&a); // error: passing argument 1 of 'something' from incompatible pointer type
   something(a);  // error: passing argument 1 of 'something' makes pointer from integer without a cast

   return 0;
}

void something(const float* a)
{
   printf("%f\n", *a);
}

现代 C 版本:

#include <stdio.h>
#include <stdint.h>

void something_float (float a);

#define something(x) _Generic((x), float: something_float)(x)

int main()
{
   uint8_t a = 28;
   
   something(a); // error: '_Generic' selector of type 'unsigned char' is not compatible with any association

   return 0;
}

void something_float (float a)
{
   printf("%f\n", a);
}

【讨论】:

  • 很好地使用_Generic
  • 谢谢!我从来没有遇到过_Generic,我一定会调查的!
  • @godo 它是在 C11 中引入的,在 C17 中有一些错误修复。我建议为此使用最新版本的 gcc 或 clang。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2018-01-01
  • 1970-01-01
  • 2017-05-28
  • 1970-01-01
  • 2021-05-03
  • 2012-03-04
  • 2017-04-08
相关资源
最近更新 更多