簡體   English   中英

function 模板參數和采用“自動”的 function 參數有什么區別?

[英]What's the difference between a function template argument and a function argument taking 'auto'?

我看不出這兩者之間有什么區別,有人可以告訴我是否有區別嗎?

template <typename Arg1>
void templatedFuncAlsoTakingAutoArg(Arg1 arg1, auto arg2)
{
    // Both types are known at compile time for constexpr
    static constexpr decltype(arg1) variable1 = decltype(arg1)();
    static constexpr decltype(arg2) variable2 = decltype(arg2)();

    // And both types work with constexpr if so that invalid code
    // can appear within constexpr statements
    // If I pass in a double for arg1 or arg2 this still compiles
    if constexpr (std::is_integral_v<decltype(arg1)>)
    {
        arg1.non_existent_member = 7;
    }

    if constexpr (std::is_integral_v<decltype(arg1)>)
    {
        arg2.non_existent_member = 7;
    }
}

我想知道的是,如果它歸結為寫一個 function 如果我這樣寫會有什么區別:

template <typename Arg>
void likeThis(Arg arg){}

或者:

void orLikeThis(auto arg) {}

在模板版本中,您具有能夠直接引用類型的優勢,但在“自動”版本中,您始終可以使用 decltype 獲取類型,對吧? 那么有什么區別呢? 在引擎蓋下是無論如何都采用 auto 實際上是模板的版本,並且以與編譯器執行模板相同的方式實例化?

但是在“自動”版本中,無論如何您總是可以使用 decltype 獲取類型,對嗎?

不必要。 概念上沒有任何改變,但template / typename版本更靈活一些。

請參閱在typename中引入的通用 lambda,使用auto而不是template /類型名語法。

在 C++20 中引入了模板 lambda 因為你不能做如下的事情

[]<std::size_t ... Is>(std::index_sequence<Is...>)
 { return (Is + ...); }
 (std::make_index_sequence<10u>{});

以一種簡單的方式,使用auto

編輯: C++20 引入了auto作為模板的語法糖的用法。 以下僅適用於以前的 C++ 標准


重要的是要記住, C++ 是一種靜態類型語言。

使用auto就像是在說“弄清楚這里的 go 是什么類型,並假裝我把它寫出來了。” 這意味着具有auto的變量仍將解析為特定類型。 並不意味着您可以在運行時提供您想要的任何類型並期望它能夠解決,就像使用動態類型語言一樣。

對於這種功能,您應該使用模板。 但是請記住,您仍然沒有在運行時提供任意類型,並希望代碼能夠解決這個問題。 在編譯時,C++ 需要知道可以使用 function 的類型,然后它將為這些不同類型生成不同版本的 function。

例如,如果您使用auto

orLikeThis("one");
orLikeThis(1.0f);

...將無法編譯。 編譯器必須假設auto解析為單一類型,但由於代碼同時提供了字符串和浮點數,現在它無法將其解析為單一類型。

然而,

likeThis<string>("one")
likeThis<float>(1.1f)

應該編譯。 編譯器將創建兩個不同版本的 function 來處理不同的輸入類型,但為方便起見,您可以簡單地提供單個 function,然后只提供使用的類型。

因此,要回答您關於差異是什么的問題,歸結為auto是語法糖,模板允許您在“相同”function 中使用多種類型。


TLDR; 如果您希望使用多種類型,請使用模板; 如果您只想避免輸入完整類型,請使用auto (或者,如果您使用的是 C++20, auto將適用於這兩種用例)。

暫無
暫無

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

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