簡體   English   中英

是否需要一個實現來診斷同一 TU 內同一顯式專業化的重復定義的 ODR 違規?

[英]Is an implementation required to diagnose ODR-violations of duplicated definitions of the same explicit specialization within the same TU?

考慮一個模板化實體,例如 (A) 一個 function 模板,和 (B) 一個 class 模板的成員枚舉。

// (A)
template<auto>
int f();

// (B)
template <auto>
struct T { enum class E; };

由於此類模板實體的相同顯式專業化的重復定義,是否需要實施來診斷 ODR 違規? 或者,換句話說, [basic.def.odr]/1是否適用於明確的專業化?


例如 GCC 和 Clang 都將以下程序診斷為格式錯誤:

// Single translation unit;
// primary template of 'f' declared as in (A) above.
template<>
int f<0>() { return 0; }

template<>
int f<0>() { return 1; }  
  // GCC & Clang - error: redefinition of 'int f() [with auto <anonymous> = 0]'

而只有 Clang 將后續程序診斷為格式錯誤,而 GCC 接受它:

// Single translation unit;
// primary template of 'T' defined as in (B) above.
template<>
enum class T<0>::E { ex };

template<>
enum class T<0>::E { ey };
  // Clang only - error: redefinition of 'E'

格式錯誤的 NDR,還是格式錯誤? (/兩個編譯器都正確,還是 GCC 錯誤?)


在各種 GCC 和 Clang 版本上測試,對於-std=c++17-std=c++2a ,結果相同

由於此類模板實體的相同顯式專業化的重復定義,是否需要實施來診斷 ODR 違規?

是的。

盡管[temp.spec]/5.2指定程序中顯式專業化的多個定義格式錯誤(同時引用 [basic.def.odr])NDR(不需要診斷),但單個 TU 中的多個定義屬於[basic.def.odr]/1 ,例如 class 模板的顯式特化(對於某些設置的模板參數)是 class。

任何翻譯單元都不得包含多個變量的定義,function、class 類型、枚舉類型或模板。

違反 [basic.def.odr]/1 不是 NDR,實現應對其進行診斷,GCC 和 Clang 對違反 ODR 的顯式專業化(在同一 TU 內)這樣做:

  • function 模板,以及
  • class 模板,以及
  • 變量模板,和
  • class 模板的成員函數,以及
  • class 模板的 static 數據成員,以及
  • class 模板的成員類。

但是,對於 class 模板的成員枚舉的明確專業化,只有 Clang 將其診斷為 TU 本地 ODR 違規,這是問題中使用的非常示例。

因此,這個成員枚舉的未診斷案例是 GCC 錯誤(作為此問題的一部分提交):

暫無
暫無

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

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