簡體   English   中英

C ++函數模板:參數類型和返回類型必須使用&嗎?

[英]C++ function template: Must use & for argument type and return type?

我正在學習使用功能模板。 我發現,如果我將參數類型聲明為引用,則程序將運行。 但是,如果參數類型不是引用,則會出錯。 例如:

下面的代碼打印正確的結果,並且沒有錯誤。

#include <iostream>
using namespace std;

template <typename T>
T & max (T & a, T & b){
    return a>b?a:b;
}

int main(int argc, char const *argv[])
{
    cout << max(1,2) << endl;
    return 0;
}

但是,如果我刪除了代碼中的所有“ & ”,即如下更改上述程序:

#include <iostream>
using namespace std;

template <typename T>
T  max (T  a, T  b){
    return a>b?a:b;
}

int main(int argc, char const *argv[])
{
    cout << max(1,2) << endl;
    return 0;
}

此代碼將導致以下錯誤。

a.cpp: In function ‘int main(int, const char**)’:
a.cpp:11:17: error: call of overloaded ‘max(int, int)’ is ambiguous
  cout << max(1,2) << endl;
                 ^
a.cpp:5:4: note: candidate: T max(T, T) [with T = int]
 T  max (T  a, T  b){
    ^~~
In file included from /usr/include/c++/7/bits/char_traits.h:39:0,
                 from /usr/include/c++/7/ios:40,
                 from /usr/include/c++/7/ostream:38,
                 from /usr/include/c++/7/iostream:39,
                 from a.cpp:1:
/usr/include/c++/7/bits/stl_algobase.h:219:5: note: candidate: constexpr const _Tp& std::max(const _Tp&, const _Tp&) [with _Tp = int]
     max(const _Tp& __a, const _Tp& __b)

為什么? 謝謝大家的幫助!

在第一個示例中不考慮引用參數版本,因為這些常量不適合可修改的左值引用。 還要感謝using namespace std;的不當建議using namespace std; ,您可以改用std版,它將起作用。 您可以在第一個版本中刪除您的max代碼,並且該代碼仍然可以使用,因為一旦這些引用觸發取消資格,就不會考慮該代碼。

總之,第一個版本不考慮你的max的代碼,因為它不符合,那么std::max來代替(這符合資格)。 在第二個版本中,使用值參數的代碼和使用const-references的std::max版本都可以使用,因此結果含糊不清。

在std名稱空間中已定義具有相同(或兼容)名稱和參數類型的函數(模板)。

去掉

using namespace std;

並在cout和endl前面加上std :::

std::cout << max(1,2) << std::endl;

否則,您將用std名稱空間中的所有名稱污染全局名稱空間。

有一個模板化的max()函數可以接受名稱空間std參數(在標准標頭<algorithm> )。 盡管該標准不要求#include <iostream>引入該功能,但也不禁止該功能。 您的標准編譯器確實通過<iostream>對其進行了介紹。

using指令( using namespace std )使std::max()模板被視為代碼中匹配函數的候選對象。

在您的第一個代碼示例中,調用max(1,2)std::max()相匹配,因為它接受const引用,並且比接受非const引用的函數更好。 它恰好產生您期望的輸出。

在您的第二個代碼示例中,按值傳遞,編譯器沒有理由偏愛您的max()std的一個(按值傳遞或按const引用傳遞對於傳遞像12這樣的int常量都同樣有效) 。 因此,編譯器抱怨模棱兩可。

問題在於:使用不同的編譯器(或其標准庫),您的代碼可能會以不同的方式失敗,因為不需要<iostream>聲明std::max() ,並且並非所有實現都可以。

刪除using指令,您的代碼中std::max()的潛在用法將消失-在任何一個代碼示例中, std::max()都不會被視為候選。 您的第一個示例將無法編譯,因為不能使用非const引用來傳遞文字值。 第二個將編譯並產生您期望的輸出。 在符合標准的C ++編譯器之間,此行為將是一致的(並且不影響諸如<iostream>類的標准頭文件是否聲明std::max() )。

暫無
暫無

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

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