簡體   English   中英

具有可變高階函數的過載分辨率

[英]Overload resolution with variadic higher order functions

假設我有一個可變高階函數

template<typename F, typename ...Args>
void execution(F func, Args&&... args)
{
    func(std::forward<Args>(args)...);
}

然后為這個重載集

void f() {}
void f(int arg) {}

過載分辨率是不可能的

int main()
{
    execution(f, 1);
    execution(f);
    return 0;
}

然而,如果只提供兩者中的任何一個,程序就會編譯

  1. 為什么會這樣? 為什么模板參數推斷失敗?
  2. 如果我從集合中刪除f()並用f(arg, arg2)替換它仍然存在問題 有解決方法,還是我總是要提供函數的類型作為模板參數?

     execution<void()>(f); 

在進行模板類型推導時,編譯器不會分析在函數內部如何使用類型。 因此,在推導模板參數時,編譯器看不到不同模板參數之間的關系。 因此,額外的可變參數模板參數根本不重要,問題可以減少到

template<typename Func> void execution(Func func);

void f();
void f(int);

execution(f);

使用此最小化代碼,顯然為什么模板參數推斷失敗應該是顯而易見的。

您可以通過使第一個參數明確依賴於剩余的模板參數來解決此問題,例如:

template<typename... Args>
 void execution(void (*func)(Args ...), Args ... args)
{
  func(std::forward<Args>(args) ...);
}

您需要一個重載集對象。 這是一個表示f函數的整個重載集的對象:

struct f_overload_set {
  template<typename...As>
  auto operator()(As&&...as)->
    decltype(f(std::declval<As>()...))
  { return f(std::forward<As>(as)...); }
};

現在將f_overload_set{}傳遞給template函數。

template的函數值參數必須是值,並且在當前的C ++中,沒有表示函數的整個重載集的第一類值。 符號f在每個使用點消除歧義為一個重載:但這需要在使用點立即上下文。 上面推斷消歧,直到我們有方便的論點。

沒有特定的功能'f'可用:

簡化它:

template<typename F>
void execution(F func)
{}

void f() {}
void f(int arg) {}

int main()
{
    execution(f);
    return 0;
}

您有兩個函數'f'可用於模板參數扣除/替換

暫無
暫無

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

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