簡體   English   中英

轉換 std::function<void ()> 作廢 (*)()</void>

[英]Convert std::function<void ()> to void (*)()

所以我在 C++ 中有一個成員 function 接受一個std::function<void>我想將它傳遞給一個wiringPi function:

void my_class::on_change(std::function<void()> func) const
{
    wiringPiISR(
        wiring_pi_pin_number_,
        INT_EDGE_BOTH,
        func);
}

我收到錯誤cannot convert 'std::function<void()>' to 'void (*)()' in initialization 我在網上查看過,我只發現有一百行指針和引用轉換並且不在 pi 上編譯的東西。 在這里尋求任何幫助。 我應該一直使用void (*)()嗎? 這似乎是錯誤的方法。 我可以找到很多關於將void (*)()轉換為std::function<void>但不是相反的方法..

PS:我是 c++ 的菜鳥。 我的主要語言是 C# 和其他一些高級語言,所以仍在學習這門語言,不確定我在這里缺少什么..

將 std::function<void ()> 轉換為 void (*)()

你不能。

我應該一直使用 void (*)() 嗎?

是的。

從技術上講,使用 std::function 可以工作,但您必須依賴全局 state 以及使用 std::function 的好處可能不值得花這么多錢。

這似乎是錯誤的方法。

鑒於您使用的 API 的限制,它不是。

這是一個如何做到這一點的例子。

template<class Sig> using pfunc_t=Sig*;
template<class Sig>
struct callback_entry{
  pfunc_t<Sig> pf = nullptr;
  std::function<Sig> f;
};
trmplate<class Sig, std::size_t N>
using callback_table = std::array< callback_entry<Sig>, N >;

template<class Sig, std::size_t N, callback_table<Sig,N>* ptable, class R, class...Args, std::size_t...Is>
callback_table<Sig,N> make_table( std::index_sequence<Is...> ){
  return {{
    {[](Args... args)->R{ return (*ptable)[Is].f(std::forward<Args>(args)); }}...
  }};
}

template<std::size_t N, class R, class...Args>
callback_table<R(Args...), N> callbacks = make_table<R(Args...), N, &callbacks<N,R,Args...>, R, Args...>(std::make_index_sequence<N>{});

template<std::size_t N, class R, class...Args>
pfunc_t<R(Args...)> register_callback( std::function<R(Args...)> f ){
  for(auto&& entry:callbacks<N,R,Args...>){
    if (entry.f) continue;
    entry.f=std::move(f);
    return entry.pf;
  }
}
template<std::size_t N, class R, class...Args>
void recycle_callback( pfunc_t<R(Args...)> pf ){
  for(auto&& entry:callbacks<N,R,Args...>){
    if (pf!=entry.pf) continue;
    entry.f=nullptr;
  }
}

很多錯別字,可能還有語法錯誤,但我希望這個想法很清楚。

我們制作了一個由 function 指針和固定大小的 std 函數組成的全局數組。 function 指針知道它們的索引,因此它們查找標准 function 並運行它。 注冊查找未使用的 std function,填充它,並返回 function 指針。

保持 N 低,因為它會吃掉可執行代碼 memory 和運行時 memory。 但是,如果它太低,您將用完回調。

要將std::function<void()>轉換為void(*)() ,請使用std::function::target<>() function。

目標 function 返回指向存儲的可調用 function 目標的指針,如下面的代碼所示。

void f()
{
    cout << "f()" << endl;
}

void f1(void(*p)())
{
    p();
}

int main() {
    
    // Convert std::function<void()> to void(*)()
    
    std::function<void()> fp = &f;
    auto p1 = fp.target<void(*)()>();
    void (*p2)() = *p1;
    p2();
    
    f1(p2);
}

Output:

f()

f()

暫無
暫無

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

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