操作系统 C语言实现多线程判断完全数
操作系统经典大作业…我写代码水平极差,当时搜这道题没搜到自己能看懂的代码,于是自己写了一个能让自己简单看懂的C程序,代码可以直接在dev c++运行,在VS2013上还需要配置,懒得弄了呜呜呜
一、程序功能
实现一个多线程程序测试一个数是否是完全数。如果一个数N的所有因数(不包括N本身)的和还是N,则N是一个完全数。如6和28。输入是一个整数N,如果N是完全数则输出true,否则输出false。主程序从命令行中读取数字N和P,创建P个线程,将1~N这N个数分给各个线程,保证两个线程不会分到相同的数。每个线程判断这些数是否是N的因数,如果是,则将该数存入一个共享的缓冲区中。在父进程中用合适的同步方法,等待所有线程执行完毕后,判断N是否是完全数,即判断是否N的所有因数之和还是N。(提示:你可以将测试的数限制在1至N的平方根来加速计算过程。)
二、程序实现及源代码
本程序采用C语言实现,程序源代码如下:
#include<stdio.h>
#include<pthread.h>
#include<math.h>
int a[100]={0};//存放判断后的因子
int n;
pthread_mutex_t mutex=PTHREAD_MUTEX_INITIALIZER;//初始化一个互斥锁
int x=0;
int j=0;
int sum=0;
int isPerfectNum(void *arg)//反馈消息
{
pthread_mutex_lock(&mutex);//设置加锁
x++;
printf("%d号线程\n",x);
if(x==1) //1是任何一个数的因子
{
printf("%d是因子\n",1);
sum+=1; //把1加进sum里
printf("sum = %d\n",sum);
printf("\n");
}
else if(n%x==0)
{
if(n/x==x) //例如判断出4的一个因子是2,4/2=2,所以只用加1次
{
printf("%d是因子\n",x);
a[j]=x;
sum=sum+x;
printf("sum = %d\n",sum);
printf("\n");
}
else //例如判断出10的一个因子是2,则10/2=5,5也一定是因子
{
printf("%d %d是因子\n",x,n/x);
a[j]=x;
j++;
a[j]=n/x;
sum=sum+x+(n/x);
printf("sum = %d\n",sum);
printf("\n");
}
}
pthread_mutex_unlock(&mutex);//线程处理完,解锁
if(sum==n) return 1;
else return 0;
}
int main()
{
int i=0;
int sum=1;
printf("please input N\n");
scanf("%d",&n);
pthread_t th;
for(i=1;i<=sqrt(n)-1;i++)
{//创建根号n个线程,第i号线程判断i是否是因子,
//如果是则判断n/i是否与i相等,相等则只加i到sum
//不相等则加两个因子到sum,将时间复杂度缩短到根号n
pthread_create(&th,NULL,isPerfectNum,NULL);
}
pthread_join(th,NULL);
if(isPerfectNum(n))
printf("%d 是完全数\n",n);
else
printf("%d 不是完全数",n);
return 0;
}
三、程序功能测试
本程序运行平台为Dev c++,一共测试三组数据(28,496,8119),可以看出代码时间复杂度为根号N,且能正确判断完全数。