6.5.2 基本表达式
6.5.2 基本表达式
基本表达式包括:
- 标识符;
- 常量;
- 字符串字面量;
- 圆括号括起的表达式;
- 泛型选择。
作为基本表达式使用的标识符,必须有一个当前可见的普通标识符声明,并且该声明指明的是对象或函数。
指代对象的标识符基本表达式是左值;指代函数的标识符基本表达式是函数设计符。
常量本身就是基本表达式。它的类型由
6.4.4的规则决定。字符串字面量也是基本表达式。它是一个左值,其类型由
6.4.5的规则决定。括号表达式与括号内部原表达式的类型、值和语义完全相同;括号只影响分组,不单独引入新的语义。
泛型选择同样属于基本表达式,其类型和值由所选中的关联表达式决定。
6.5.2.1 泛型选择
- 泛型选择的语法形式是:
c
_Generic(controlling-expression, associations...)1
一个泛型选择:
- 最多只能有一个
default关联; - 每个
type-name都必须是完整对象类型,且不能是可变修改类型; - 同一个泛型选择中,不允许出现两个兼容类型关联。
- 最多只能有一个
控制表达式的类型,要按“已做左值转换、数组到指针转换、函数到指针转换之后”的类型来判断。
若没有
default关联,则控制表达式类型必须与关联列表中的恰好一个类型兼容。若存在与控制表达式类型兼容的类型关联,就选择那一项;否则选择
default关联。控制表达式不会被求值。未被选中的其他关联表达式也都不会被求值。
泛型选择的类型和值,与最终被选中的那个结果表达式完全一致;若该结果表达式是左值、函数设计符或
void表达式,泛型选择也相应具有同样性质。
标准示例
c
#define cbrt(X) _Generic((X), \
long double: cbrtl, \
default: cbrt, \
float: cbrtf \
)(X)1
2
3
4
5
2
3
4
5
NOTE
_Generic 的核心不是“运行时分派”,而是“编译期按类型选分支”,并且控制表达式不会真的执行。