2012-04-25 39 views
1

我一直在使用pthreads,但已经意识到如果我使用1个线程,或者如果我将任务分解为1/N的N,我的代码将独立地花费相同的时间量线程。为了举例说明我我的代码减少到这个例子:同时采用单线程和多线程代码

#include <stdio.h> 
#include <stdlib.h> 
#include <pthread.h> 

#include <boost/progress.hpp> 

#define SIZEEXEC 200000000 

using namespace boost; 
using std::cout; 
using std::endl; 

typedef struct t_d{ 
    int intArg; 
} Thread_data; 

void* function(void *threadarg) 
{ 
    Thread_data *my_data= (Thread_data *) threadarg; 
    int size= my_data->intArg; 

    int i=0; 
    unsigned rand_state = 0; 
    for(i=0; i<size; i++) rand_r(&rand_state); 
    return 0; 
} 

void withOutThreads(void) 
{ 
    Thread_data* t1= new Thread_data(); 
    t1->intArg= SIZEEXEC/3; 
    function((void *) t1); 

    Thread_data* t2= new Thread_data(); 
    t2->intArg= SIZEEXEC/3; 
    function((void *) t2); 

    Thread_data* t3= new Thread_data(); 
    t3->intArg= SIZEEXEC/3; 
    function((void *) t3);  
} 

void withThreads(void) 
{ 
    pthread_t* h1 = new pthread_t; 
    pthread_t* h2 = new pthread_t; 
    pthread_t* h3 = new pthread_t; 
    pthread_attr_t* atr = new pthread_attr_t; 

    pthread_attr_init(atr);  
    pthread_attr_setscope(atr,PTHREAD_SCOPE_SYSTEM); 

    Thread_data* t1= new Thread_data(); 
    t1->intArg= SIZEEXEC/3; 
    pthread_create(h1,atr,function,(void *) t1); 

    Thread_data* t2= new Thread_data(); 
    t2->intArg= SIZEEXEC/3; 
    pthread_create(h2,atr,function,(void *) t2); 

    Thread_data* t3= new Thread_data(); 
    t3->intArg= SIZEEXEC/3; 
    pthread_create(h3,atr,function,(void *) t3); 

    pthread_join(*h1,0); 
    pthread_join(*h2,0); 
    pthread_join(*h3,0); 
    pthread_attr_destroy(atr); 
    delete h1; 
    delete h2; 
    delete h3; 
    delete atr; 
} 

int main(int argc, char *argv[]) 
{ 
    bool multThread= bool(atoi(argv[1])); 

    if(!multThread){ 
     cout << "NO THREADS" << endl; 
     progress_timer timer; 
     withOutThreads(); 
    } 
    else { 
     cout << "WITH THREADS" << endl; 
     progress_timer timer; 
     withThreads(); 
    } 

    return 0; 
} 

无论是编码是错误的或有对我的系统不允许进行并行处理的东西。我在Ubuntu 11.10上运行x86_64-linux-gnu,gcc 4.6,英特尔®至强®CPU E5620 @ 2.40GHz×4

感谢您的任何建议! (1)progress_timer计时器不允许我测量“真实”时间的差异,以及(2)我在“功能”中给出的任务似乎不是足以让我的机器用1或3个线程给出不同的时间(这很奇怪,在这两种情况下我都会有10秒的时间...)。我试图分配内存,使它更重,是的,我看到了一个区别。虽然我的其他代码更复杂,但它仍然有很好的机会运行+ - 同时有1或3个线程。谢谢!

+2

'功能'实际上*做*什么?编译器是否有可能优化所有东西? – 2012-04-25 13:06:03

+0

另外,请注意,您并未使用一致的“intArg”值。 – 2012-04-25 13:06:52

+0

您是否正在进行优化或不进行优化? – Tobias 2012-04-25 13:09:00

回答

2

这是预期的。您正在测量CPU时间,而不是挂钟时间。

time ./test 1 
WITH THREADS 
2.55 s 


real 0m1.387s 
user 0m2.556s 
sys  0m0.008s 

实时时间少于用户时间,与您的测量时间相同。实时是你的挂钟显示的,用户和系统是在所有CPU合并的合并的用户和内核模式下花费的CPU时间

time ./test 0 
NO THREADS 
2.56 s 


real 0m2.578s 
user 0m2.560s 
sys  0m0.008s 

您的测量时间,实时和用户时间都几乎相同。

1

罪魁祸首似乎是progress_timer或者说是对它的理解。

尝试用此替换main()。这告诉程序不需要时间progress_timer报告,也许它报告总系统时间?

#include <sys/time.h> 
void PrintTime() { 
    struct timeval tv; 

    if(!gettimeofday(&tv,NULL)) 
     cout << "Sec=" << tv.tv_sec << " usec=" << tv.tv_usec << endl ; 

} 

int main(int argc, char *argv[]) 
{ 
    bool multThread= bool(atoi(argv[1])); 

    PrintTime(); 
    if(!multThread){ 
     cout << "NO THREADS" << endl; 
     progress_timer timer; 
     withOutThreads(); 
    } 
    else { 
     cout << "WITH THREADS" << endl; 
     progress_timer timer; 
     withThreads(); 
    } 
    PrintTime(); 

    return 0; 
} 
+0

谢谢!我弄错了 – lourencoj 2012-04-25 15:20:54