【问题标题】:Typecheck with Macro使用宏进行类型检查
【发布时间】:2018-10-30 05:16:39
【问题描述】:

我找到了这段代码,并且我理解它的作用(如果 var 是 float 的类型,则打印)但我不明白如何:

#include <stdio.h>
#include <stdlib.h>

#define typename(x) _Generic((x), float: "float")

#define isCompatible(x, type) _Generic(x, type: true, default: false)

int main(){
  float var; 
  if(isCompatible(var, float))
    printf("var is of type float!\n");
}

什么是typename(x)?为什么从来不叫? 我也无法理解这个结构:

_Generic(x, type: true, default: false)

这里有没有办法不将 float 作为参数传递并使其隐含?

if(isCompatible(var, float))

【问题讨论】:

  • “隐含”是什么意思?这似乎与这一点无关。
  • @interjay 我的意思是,如果我总是想知道数据是否是浮点类型,我认为没有必要将 float 作为参数传递并在另一个中定义宏方式。
  • 如果你想知道一个变量是否与类型 T 兼容,显然你需要告诉编译器 T 是什么。如果您只想要一个仅适用于floatIsCompatibleWithFloat 宏,您可以在其中硬编码float 而不是将其设为参数。
  • @interjay 这正是我想做的,但你所说的“铁杆漂浮在那里”是什么意思?

标签: c types macros c11


【解决方案1】:

我怀疑您想查看 _Generic here 的文档 - 这是 C11 功能 (C11 标准 (ISO/IEC 9899:2011) s 6.5.1.1 Generic selection (p: 78-79) ))。另请参阅接受的答案here

在这个例子中,isCompatible 宏调用_Generic 并且(通过type: true)如果x(第一个参数)与type 类型兼容,则返回true,否则false .

不使用宏typename,但如果参数与float 兼容,则返回文本float。至于为什么有定义但未使用的东西,您必须询问代码的作者。

【讨论】:

    【解决方案2】:

    为什么永远不会调用typename 这个问题你应该问代码 sn-p 的开发者...

    _Generic 关键字是 C11 功能。 这个想法是根据变量的类型生成不同的代码。

    C 没有像 Java 这样的 typeof 运算符,因此在 Java 中看起来像

    ...
    if(typeof(p) == typeof(double)) {
        System.out.println("Got type 1");
    } 
    if(typeof(p) == typeof(char)) {
         System.out.println("Got type 2");
    }
    ...
    

    可以通过C11中的_Generic来实现

    #include <stdio.h>
    
    #define PRINT_MY_TYPE_NUMBER(x) _Generic((x), \
        double: printf("Got type 1\n"),\
        char: printf("Got type 2\n") \
    )
    
    int main(int c, char** v) {
    
        double p = 10;
    
        PRINT_MY_TYPE_NUMBER(p));
    
    }
    

    注意_Generic 不支持任意类型,只支持“简单”类型。

    isCompatible(variable, type) 背后的想法是如果variable 的类型与type 兼容,则返回true。它依赖于 type 被传递,因此它依赖于 type 被传递,使 type 隐式传递呈现 isCompatible 无用恕我直言。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-07-13
      • 1970-01-01
      • 2020-03-20
      • 1970-01-01
      • 2013-02-25
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多