gpt4 book ai didi

c++ - static constexpr 指向函数的指针,编译器之间的区别

转载 作者:可可西里 更新时间:2023-11-01 16:37:39 26 4
gpt4 key购买 nike

回答this question时,我用 gcc ( code compiled ) 和 clang ( code rejected ) 尝试了以下代码:

typedef long (*func)(int);

long function(int) { return 42; }

struct Test
{
static constexpr func f = &function;
};

template<func c>
struct Call
{
static void f()
{
c(0);
}
};

int main()
{
Call<Test::f>::f();
}

我不确定哪个编译器是正确的,虽然我认为 Test::f 的 constexpr 初始化是可以的。错误 clang 输出是:

error: non-type template argument for template parameter of pointer type 'func'
(aka 'long (*)(int)') must have its address taken
  1. 哪个编译器是正确的?
  2. 如果 clang 是正确的,为什么,这个错误的真正含义是什么?

编辑:“为什么”,参见DyP's question .

最佳答案

14.3.2 Template non-type arguments [temp.arg.nontype]

A template-argument for a non-type, non-template template-parameter shall be one of:

[...]

— a constant expression (5.19) that designates the address of an object with static storage > duration and external or internal linkage or a function with external or internal linkage, including function templates and function template-ids but excluding non-static class members, expressed (ignoring parentheses) as & id-expression, except that the & may be omitted if the name refers to a function or array and shall be omitted if the corresponding template-parameter is a reference; [...]

(n3485,强调我的)

我不知道为什么它受到限制,但我认为这可能与函数地址在编译时不可用有关(可能有替代模板实例化目的)。


编辑:由于 Synxis 的后续问题(评论)而增强了答案

constexpr func = &function;

^ 这是合式的;您可以使用函数的地址来初始化 constexpr 对象。问题是明确禁止使用指针作为非类型模板参数,而不是 &identifier:

形式
using My_Call     = Call < &function >;  // fine

constexpr func mypointer = &function; // fine
using My_Ind_Call = Call < func >; // forbidden, argument not of form `&id`

关于c++ - static constexpr 指向函数的指针,编译器之间的区别,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15867399/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com