任务通常需要处理数据,我们可以将数据(或指向数据的指针或引用)作为参数传递给任务,例如:

    1. void f(vector<double>& v); //处理v的函数
    2. struct F{ //处理v的函数对象
    3. vector<double>& v;
    4. F(vector<double>& vv):v{vv}
    5. void operator()(); //调用运算符,见3.4.3节
    6. }
    7. int main()
    8. {
    9. vector<double> some_vec{1,2,3,4,5,6,7,8,9};
    10. vector<double> vec2{1,2,3,4,5,6,7,8,9};
    11. thread t1{f,some_vec}; //f(some_vex)在一个独立线程中执行
    12. thread t2{F{vec2}}; //F{vec2}()在一个独立线程中执行
    13. t1.join();
    14. t2.join();
    15. }

    显然,F{vec2}将一个指向参数(一个向量)的引用保存在F中。F现在就可以使用向量了,并希望在它运行的时候其他任务不会访问vec2——将vec2以传值方式传递就可以消除这个风险。
    上面代码用{f,some_vec}初始化一个线程,它使用了 thread的可变参数模板构造函数,接受一个任意的参数序列(见28.6节)。编译器检查第一个参数(函数或函数对象)是否可用后续的参数来调用,如果检查通过,就构造一个必要的函数对象并传递给线程。因此,F::operator()f()执行相同的算法,两个任务的处理大致相同:它们都为 thread构造了一个函数对象来执行任务。