0

I'm confused about starting a thread with a member function. I know I need to pass a class object as the second parameter. But someone passed the object to the thread(), and someone passed an address, and I had tried to pass a reference. Both of them are compiling OK. So I am confused about which one is correct.

class X
{
    public:
        void do_lengthy_work(){
            std::cout << "1:1" << std::endl;
        }
};


int main(){
    X my_x;
    std::thread t(&X::do_lengthy_work, std::ref(my_x)); // pass reference
    std::thread t(&X::do_lengthy_work, &my_x);          // pass address
    std::thread t(&X::do_lengthy_work, my_x);           // pass object
    t.join();
    return 0;
}
Remy Lebeau
  • 555,201
  • 31
  • 458
  • 770
Kevin eyeson
  • 375
  • 4
  • 8
  • 2
    The first two are equivalent. The third one passes a copy of `my_x`. You can ensure it by writing `this` into `std::cout`. – 273K Jul 06 '22 at 18:31
  • 1
    All three are correct. Use whichever makes sense in the context where the thread is being created. – Pete Becker Jul 06 '22 at 19:16

1 Answers1

1

The thread constructor begins executing the thread according to the rules of std::invoke. So all 3 of the lines of code you show will do something.

The first two lines (ref and pointer) are fine if you expect the lifetime of the object to be longer than the lifetime of the thread. As you can see from the link to std::invoke above, they are equivalent. Otherwise, the third line copies the object into the thread. This means that the original object now doesn't matter and can be destroyed, but also means that any results will not be visible in the the original object, only the copy.

user3188445
  • 4,062
  • 16
  • 26