多线程搜索素数

时间:2013-06-01 21:34:25

标签: c multithreading cpu-cores

我有这个代码计算输入数字以下的素数数量:

#include<stdio.h>
#include<Math.h>

int is_prime(long num)
{
    int k = 1, a = 0, b = 0;
    long sr;
    switch(num)
        {
        case 1: return 0;
        case 2: return 1;
        case 3: return 1;
        case 4: return 0;
        case 5: return 1;
        case 6: return 0;
        case 7: return 1;
    }
    if (num % 2 == 0) return 0;
    if (num % 3 == 0) return 0;
    sr = (int) sqrt(num);
    while (b < sr) {
        a = (6 * k) - 1;
        b = (6 * k) + 1;
        if (num % a == 0)
            return 0;
        if (num % b == 0)
            return 0;
        k += 1;
    }
    return 1;
}

void main()
{
    int j;
    long num=0;
    printf("insert your number to check for prime numbers\n");
    scanf("%ld",&num);
    for (j = 0; j<num; j++){
        if (is_prime(j))
            printf("%d is a prime\n", j);
    }
}

挑战的一部分 - 有人问我是否可以通过多核处理加速计算,我回答是的。例如,如果我想检查低于100的素数,我会使用第一个线程来计算2-50,第二个线程用于计算51-99。

他说我必须考虑一下,因为在第一个核心上运行2-50时存在基本错误,而在第二个核心上运行51-99则等于100.

有人知道他是对的吗?如果是这样,那么为多核架构做这件事的正确方法是什么?

3 个答案:

答案 0 :(得分:4)

一般来说,计算is_prime(n + k)的工作量大于计算is_prime(n)的工作量。你将所有最简单的工作交给一个核心,把所有最艰苦的工作交给另一个核心,这意味着你不可能达到理想的2倍速度,如果你把它分得更均匀(例如天真,一个偶数,一个奇数,所以工作量大致均匀分开。除非不这样做;我希望你能抓住明显的缺陷,那里:)

答案 1 :(得分:0)

我这样做的方式就是这样:

   void threadfunction()
   {
       for(;;)
       {
          number = pick_next_number();   // Should be atomic. 
          if (number > maxnumber)
              return;
          if (is_prime(number))
              printf("%d\n", number);
       }
   }

然后基本上只需要运行尽可能多的这些。

一些问题是printf不是线程安全的,即使printf是线程安全的,它也可能无序输出数字。因此,您需要修复这些问题 - 例如,在数组中使用原子存储,并在执行结束时简单地打印它们。

答案 2 :(得分:0)

通过使用素数定理,即π(x)~x / ln(x)

,你可以得到一个非常接近于小于N的素数的近似值。

π(x)是与pi常数无关的素数计数函数。