考慮下面這個簡單的例子重載轉換運算模板
struct C
{
template <typename T> operator T() {return 0.5;}
operator int() {return 1;}
operator bool() {return false;}
};
int main()
{
C c;
double x = c;
std::cout << x << std::endl;
}
當鏗鏘編譯,它提供了以下錯誤
test.cpp:11:12: error: conversion from 'C' to 'double' is ambiguous
double x = c;
^ ~
test.cpp:4:5: note: candidate function
operator int() {return 1;}
^
test.cpp:5:5: note: candidate function
operator bool() {return false;}
^
test.cpp:3:27: note: candidate function [with T = double]
template <typename T> operator T() {return 0.5;}
^
1 error generated.
其他編譯器生成類似的錯誤,例如,GCC和英特爾ICLC
如果我刪除operator int
和operator bool
。它編譯得很好,並按預期工作。如果只刪除其中的一個,即保留模板運算符並說operator int
,則始終選擇非模板版本。
我的理解是,只有當模板和非模板重載函數相同時,它們都是完全匹配或者兩者都需要相同的轉換序列,則非模板版本纔是首選。但是在這種情況下,編譯器似乎沒有看到運算符模板爲完美匹配。當存在bool
和int
重載時,自然會認爲它們是不明確的。
總之,我的問題是,爲什麼運營商模板在這種情況下不被認爲是完美匹配?
你對標準的「怪異閱讀」非常有趣,實際上對我來說意義重大。如果我理解正確,操作符int是否比模板更好取決於哪個是F1,哪個是F2。如果我們考慮F1 = op int,則F2 = op,那麼在第3項我們確定F1比F2更好並停止。但是,如果我們考慮F1 = op ,F2 = op int,則在第2項我們確定F1更好並停止。但是如果它們有三個,那麼op int和op bool就不會比其他的更好,因此也就不會含糊不清 –
2013-02-21 00:37:29