Как указать перегрузку, на которую должен указывать вызываемый объект? [дубликат]


На этот вопрос уже есть ответ здесь:

#include <thread>
struct Callable
{
    void start() {};
    void start(unsigned) {};
};

int main()
{   
    Callable some_object;
    std::thread some_thread( &Callable::start, &some_object );

    some_thread.join();
}

Этот код не компилируется, поскольку &Callable::start неоднозначен. Есть ли способ указать, какая перегрузка должна использоваться в конструкторе std::thread?

4 3

4 ответа:

Вы можете бросить:

using callback_type = void (Callable::*)();

std::thread some_thread(
    static_cast<callback_type>(&Callable::start), &some_object );
//  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

Можно определить указатель на элемент и использовать его в вызове функции

void ( Callable::*p )( unsigned ) = &Callable::start;
std::thread some_thread( p, &some_object );

Вы можете выбрать между перегрузками с помощью приведения:

typedef void (Callable::*voidFunc)();

int main()
{   
    Callable some_object;
    std::thread some_thread( (voidFunc)&Callable::start, &some_object );

Согласно второй части этого ответа , более безопасным вариантом было бы следующее:

void (Callable::*)() start_fun = &Callable::start;
std::thread some_thread( start_fun, &some_object );

Это происходит потому, что вы избегаете статического приведения и получите ошибку компилятора в первой строке, если соответствующая функция-член не будет найдена.