我写了一个小程序,通过检查2到5E + 15的每个整数,找到前5个出租车编号(到目前为止只知道6个)。出租车编号的定义是here。
然而,我的节目花了8分钟才到达3E + 7。由于出租车(3)大约是8E + 7,我不愿意让它继续运行而不先优化它。
我在HP 8560w,i7 2600qm四核,16GB RAM上使用Ubuntu 16.10上的NetBeans 8。但是,Java仅使用1个核心,即使在给予极高优先级时,总CPU功率也最多为25%。我该如何解决这个问题?
public class Ramanujan
{
public static void main(String[] args)
{
long limit;
//limit = 20;
limit = 500000000000000000L;
int order = 1;
for (long testCase = 2; testCase < limit; testCase++)
{
if (isTaxicab(testCase, order))
{
System.out.printf("Taxicab(%d) = %d*****************************\n",
order, testCase);
order++;
}
else
{
if (testCase%0x186a0 ==0) //Prints very 100000 iterations to track progress
{
//To track progress
System.out.printf("%d \n", testCase);
}
}
}
}
public static boolean isTaxicab(long testCase, int order)
{
int way = 0; //Number of ways that testCase can be expressed as sum of 2 cube numbers.
long i = 1;
long iUpperBound = (long) (1+Math.cbrt(testCase/2));
//If testCase = i*i*i + j*j*j AND i<=j
//then i*i*i cant be > testCase/2
//No need to test beyond that
while (i < iUpperBound)
{
if ( isSumOfTwoCubes(testCase, i) )
{
way++;
}
i++;
}
return (way >= order);
}
public static boolean isSumOfTwoCubes(long testCase,long i)
{
boolean isSum = false;
long jLowerBound = (long) Math.cbrt(testCase -i*i*i);
for (long j = jLowerBound; j < jLowerBound+2; j++)
{
long sumCubes = i*i*i + j*j*j;
if (sumCubes == testCase)
{
isSum = true;
break;
}
}
return isSum;
}
}
答案 0 :(得分:0)
程序本身只会在你并行化之前使用一个核心。
您需要学习如何使用线程。
您的问题是embarrassingly parallel。并行化太多(即创建太多线程)将是有害的,因为每个线程都会产生开销,因此您需要注意确切的并行化方式。
如果由我决定,我会初始化一个工作线程列表,其中每个线程有效地执行isTaxicab()
,并在每个工作人员可用时简单地为其分配一个testCase
。
您可能希望编码,以便您可以轻松地尝试工作人员数量。