微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

模板 – C:为什么这个constexpr不是编译时常数

在以下C 11代码中,最后一次调用arraySize会导致编译错误.显然这是因为y是一个运行时大小的数组,并且arraySize模板参数N不能被推导出来.我不明白为什么x是一个编译时间大小的数组,但是y结束运行时大小. arraySize模板函数直接从Scott Meyers的“有效现代C”项目1中获取.
#include <cstddef>

template<typename T,std::size_t N>
constexpr std::size_t arraySize(T(&)[N]) noexcept { return N; }

struct S
{
    char c[10];
};

int main()
{
    S s;
    S* ps = &s;

    char x[arraySize(s.c)];
    char y[arraySize(ps->c)]; // why is y a runtime sized array?

    arraySize(x);
    arraySize(y); // error !?

    return 0;
}

解决方法

在C中,错误不是调用arraySize(y),而是声明y本身.

数组声明中的边界必须是“转换的常量表达式”.

如果你的编译器接受y的声明,后来告诉你y是运行时绑定的数组,它不是一个C编译器. C的任何批准版本中没有运行时间限制的数组,也没有当前的草案.

arraySize(sc)和arraySize(ps-> c)之间的显着差异在于ps-> c与(* ps).c相同,* dereference操作符需要在ps上进行lvalue-to-rvalue转换,不是一个恒定的表达(也不是& s,见下文).表达式的其余部分不涉及到lvalue-to-rvalue转换,数组lvalue直接由引用绑定.

A constant expression is either a glvalue core constant expression whose value refers to an entity that is a permitted result of a constant expression (as defined below),or a prvalue core constant expression whose value is an object where,for that object and its subobjects:

  • each non-static data member of reference type refers to an entity that is a permitted result of a constant
    expression,and

  • if the object or subobject is of pointer type,it contains the address of an object with static storage duration,the address past the end of such an object (5.7),the address of a function,or a null pointer value.

An entity is a permitted result of a constant expression if it is an object with static storage duration that is either not a temporary object or is a temporary object whose value satisfies the above constraints,or it is a
function.

显然,ps包含具有自动存储持续时间的对象的地址,因此它不能被声明为constexpr.但是如果你改变S,一切都应该开始工作S * ps =& s;静态S; constexpr S * ps =& s;

(另一方面,你会认为arraySize(s.c)的参数也不是一个常量表达式,因为它是一个引用,而不是静态存储持续时间的对象)

原文地址:https://www.jb51.cc/c/114984.html

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐