什么时候实例化 constexpr 函数模板?

When are constexpr function templates instantiated?

我正在研究一项提案,使功能 header 功能 constexpr 成为可能。 (std::invoke, std::reference_wrapper, std::bind, std::mem_fn, std::not_fn)

我了解到添加 constexpr 会破坏现有代码,因为 constexpr 函数是急切实例化的。

template<class T>
int f(T){
    return T::not_existing_member;
}

template<class T>
constexpr int g(T){
    return T::not_existing_member;
}

int main(){
    decltype(f(0)) a; // Well-formed
    decltype(g(0)) b; // Ill-formed if the function body is instantiated
}

GCC 编译此代码,clang 不编译。我在 my proposal 中描述了如何使用 std::bind.

的示例处理带有重载的急切实例化

你能告诉我编译器必须以及允许实例化一个函数时,在标准中的什么地方有描述吗模板?

更准确地说,我想知道在以下示例中,GCC 和 clang 的相同行为是否由标准强制执行或是否由实现定义:

template<class T>
struct Foo{
    constexpr int f(){
        return 0;
    }

    constexpr int f()const{
        return T::not_existing_member;
    }
};

int main(){
    /* constexpr */ Foo<int> foo;
    foo.f(); // Ill-formed with, Well-formed without constexpr by the standard?
}

如果 foo 不是 constexpr,GCC 和 clang 都会编译代码,如果是,则都拒绝它。

示例 #1 有效 CWG issue 1581。目前还没有完全指定正确的行为 应该 是什么。方向似乎是 constexpr 实例化应该是急切的,但这需要在未来的某个时候明确。

示例 #2 很简单:调用 int Foo<int>::f() const 格式错误。当您的 foo 对象是 const 时会发生这种情况,但当它不是 const 时则不会。 class模板的成员函数只在使用的时候实例化,如果你的Foo<int>对象是非const的,我们从不实例化const成员函数,所以代码很好-形成。 constexpr 与此处无关。