簡體   English   中英

c ++:錯誤:'class std :: result_of中沒有名為'type'的類型

[英]c++: error: no type named ‘type’ in ‘class std::result_of<void (*(std::unordered_map

以下是使用兩個線程插入哈希表進行測試的簡單程序。 對於測試,不使用鎖定。

#include <iostream>
#include <unordered_map>
#include <thread>

using namespace std;

void thread_add(unordered_map<int, int>& ht, int from, int to)
{
    for(int i = from; i <= to; ++i)
        ht.insert(unordered_map<int, int>::value_type(i, 0));
}

void test()
{
    unordered_map<int, int> ht;
    thread t[2];

    t[0] = thread(thread_add, ht, 0, 9);
    t[1] = thread(thread_add, ht, 10, 19);

    t[0].join();
    t[1].join();

    std::cout << "size: " << ht.size() << std::endl;
}

int main()
{
    test();
    return 0;
}

但是,編譯時會出錯。

$ g++ -std=c++11 -pthread test.cpp
...
/usr/include/c++/4.8.2/functional:1697:61: error: no type named ‘type’ in ‘class std::result_of<void (*(std::unordered_map<int, int>, int, int))(std::unordered_map<int, int>&, int, int)>’
       typedef typename result_of<_Callable(_Args...)>::type result_type;
...

花了一段時間,但仍然無法糾正它。 謝謝。

我可以使用MSVC2013成功編譯您的代碼。 但是, thread()可以將其參數的副本傳遞給新線程。 這意味着如果你的代碼會在你的編譯器上編譯,那么每個線程都會使用自己的ht副本運行,所以在最后, mainht將是空的。

GCC不會使用這個奇怪的消息進行編譯。 你可以通過使用帶線程的引用包裝器來擺脫它:

t[0] = thread(thread_add, std::ref(ht), 0, 9);
t[1] = thread(thread_add, std::ref(ht), 10, 19);

這將成功編譯。 並且線程使用的每個引用都將引用相同的對象。

但是,很有可能會出現運行時錯誤或意外結果。 這是因為兩個線程正在嘗試插入ht unordered_map不是線程安全的,因此這些競爭條件可能會導致ht達到不穩定狀態(即UB,即潛在的segfault)。

為了使其正常運行,您必須保護您的concurent訪問:

#include <mutex>
...
mutex mtx;   // to protect against concurent access

void thread_add(unordered_map<int, int>& ht, int from, int to)
{
    for (int i = from; i <= to; ++i) {
        std::lock_guard<std::mutex> lck(mtx);  // protect statements until end of block agains concurent access
        ht.insert(unordered_map<int, int>::value_type(i, 0));
    }
}

這個錯誤確實很神秘,但問題是thread_add通過引用獲取它的第一個參數,但是你按值傳遞它。 這會導致仿函數類型推斷錯誤。 如果你想通過引用傳遞一些東西,比如std::bindstd::thread的main函數,你需要使用引用包裝器( std::ref ):

void test()
{
    // ...

    t[0] = thread(thread_add, std::ref(ht), 0, 9);
    t[1] = thread(thread_add, std::ref(ht), 10, 19);

    // ...
}

[實例]

暫無
暫無

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

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