关于多核程序设计技术一书中的cache利用~

1个取n以下素数的代码~
inline long Strike(bool composite[],long i,long stride,long limit)
{
	for (;i<limit;i+=stride)
	composite[i]=true;
	return i;
}
long CacheUnfriendlySieve(long n)
{
	long count=0;
	long m=(long)sqrt((double)n);
	bool* composite=new bool[n+1];
	memset(composite,0,n);
	for (long i=2;i<=m;++i)
	{
		if (!composite[i])
		{
			++count;
			Strike(composite,2*i,i,n);
		}
	}
	for (long i=m+1;i<=n;++i)
	{
		if (!composite[i])
		{
			++count;
		}
	}
	delete[] composite;
	return count;
}


外层用于找到素数,Strike内层循环删除合数

重构该程序后

long CacheFriendlySieve(long n)
{
	long count=0;
	long m=(long)sqrt((double)n);
	bool* composite=new bool[n+1];
	memset(composite,0,n);
	long *factor=new long[m];
	long *striker=new long[m];
	long n_factor=0;
	for (long i=2;i<=m;++i)
	{
		if (!composite[i])
		{
			++count;
			striker[n_factor]=Strike(composite,2*i,i,m);
			factor[n_factor++]=i;
		}
	}
	for (long window=m+1;window<=n;window+=m)
	{
		long limit=min(window+m-1,n);
		for (long k=0;k<n_factor;++k)
		{
			striker[k]=Strike(composite,striker[k],factor[k],limit);
			for (long i=window;i<=limit;++i)
			{
				if (!composite[i])
				{
					++count;
					//下面两句是我自己补充的,感觉是作者漏掉了,不知道是不是~~
					striker[n_factor]=Strike(composite,2*i,i,limit);//更新
					factor[n_factor++]=i;
				}
			}
		}
		delete striker;
		delete factor;
		delete composite;
		return count;
	}
}


上面的代码中

factor数组用于存放m中的素数。striker数组用于存放最后一个未删除的合数。将程序划分为大小sqrt(n)的 窗口,每个中重复处理多余的合数,并重新保存未删除的合数,后面还要更新factor中的素数。因为素数数量不多,后面那个循环中的自循环也不大,factor数组里面的前面部分得到很大的重用,cache效率高~~

你可能感兴趣的:(cache,delete)