簡體   English   中英

模板 class 中的部分特化模板 static constexpr

[英]Partially specialized template static constexpr in template class

(一個玩具,最小的不工作示例)

下一個代碼不能用 cpp20/17 編譯:

template<typename TSomeTemplate>
struct A
{
    static constexpr size_t B = 1;

    template<typename T, typename... Ts>
    static constexpr size_t C = 4;

    template<typename T>
    static constexpr size_t C<T> = B;
};

int main()
{
    A<int>::C<int>;

    return 0;
}

關於結構中的最后一行,出現“表達式未計算為常量”的錯誤。 但是,它確實以完全專業化或不引用 B 的方式進行編譯:

template<typename TSomeTemplate>
struct Works
{
    static constexpr size_t B = 1;

    template<typename T, typename... Ts>
    static constexpr size_t C = 4;

    template<>
    static constexpr size_t C<int> = B;
};

template<typename TSomeTemplate>
struct AlsoWorks
{
    static constexpr size_t B = 1;

    template<typename T, typename... Ts>
    static constexpr size_t C = 4;

    template<typename T>
    static constexpr size_t C<T> = 2;
};

為什么會這樣? 我怎樣才能使第一個結構工作?

你不能這樣專攻,你可以使用 SFINAE 或者你可以嘗試類似的東西:

template<typename TSomeTemplate>
struct A
{
    static constexpr size_t B = 1;

    template<typename T, typename... Ts>
    static constexpr size_t C = sizeof...(Ts) == 0 ? B : 4;
};

我能夠通過添加模板關鍵字來編譯您的代碼。

template<typename TSomeTemplate>
struct A
{
    static constexpr size_t B = 1;

    template<typename T, typename... Ts>
    static constexpr size_t C = 4;

    template<typename T>
    static constexpr size_t C<T> = B;
};

int main()
{
    A<int>::template C<int>;

    return 0;
}

正如這里所引用的。

類似地,在模板定義中,不是當前實例化成員的依賴名稱不被視為模板名稱,除非使用了消歧關鍵字 template 或除非它已被建立為模板名稱:

我看不出代碼有什么問題。

template<typename T>
static constexpr size_t C<T> = B;

這是C變量模板的部分特化,在 class scope 內部也是允許的。 它也比主模板更專業。

B顯然是一個常量表達式,因為它之前已被定義為constexpr變量。 即使它僅被聲明為const ,它仍然可以在常量表達式中使用(因為它是整數類型)。 編譯器將其拒絕為不是常量表達式是錯誤的。

似乎這里只有一些編譯器錯誤在起作用(GCC 似乎不喜歡 class scope 中的變量模板部分特化,MSVC 似乎對B的 constness 有問題。Z9375884CF4ED31C834A626C32 不抱怨)

GCC 和 MSVC 拒絕代碼是錯誤的,因為程序格式正確。

B是一個常量表達式,可以在C的部分特化期間用作初始化器。 這是一個 msvc 錯誤,此處報告為:

使用 constexpr static 數據成員作為初始化程序時,MSVC 拒絕有效代碼


此外,我們可以為C提供部分專業化(如您所做的那樣)。 這是一個 gcc 錯誤報告為:

GCC 拒絕涉及變量模板部分特化的有效代碼

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM