1.假設現在的計算機比Appeal做實驗所用的計算機快1000倍,如果使用相同的總時間(大約一天),對於O(n^2)和O(nlogn)算法,問題規模n個增加到多少?
(1)使用O(nlogn)二叉樹算法時,一天可以處理的問題n的規模10 000個。那麼可知10000log10000/ ( x*logx)=1/1000;即4*Math.pow(10,7)*Math.log(10)=( x*logx);由此寫個算法得到n的近似值
public class t1 {
public static void main(String []args){
int i=0;
double value=4*Math.pow(10,7)*Math.log(10);
double temp;
double before;
while(true){
i++;
temp=i*Math.log(i);
if(temp>value){
before=(i-1)*Math.log(i-1);
break;
}
}
System.out.println(i-1);
System.out.println((i-1)*Math.log(i-1));;
System.out.println(value);
System.out.println(temp);
}
}
運行結果是
5907213
9.21034025786332E7
9.210340371976183E7
9.210341917031801E7
所以速度快1000倍,n的規模由10000變爲了5907213,即規模擴大了大概590倍
(2)使用O(n^2)時,因爲它比0(nlogn)的算法慢十二倍。所以可以得到下列等式(10^4)^2/( n^2 )=1/12/(1/12*1000)得到的近似解爲
316227.7660168379。所以速度快1000倍,n的規模大概只增加了31倍。
3.精度改變對於算法運行速率的影響
下面我寫的就是一個三重循環,每次進行加二,減一的運算。但是結果竟然float比double就快了近300毫秒,這纔是一個簡單的操作並且總運行時間纔是3,4分鐘,如果是複雜的操作並且需要一天的時間,可以預見精度的改變對於算法運行速度的巨大影響
package chapter6;
public class t3 {
public static void testfloat(){
long current=System.currentTimeMillis();
float f=0;
for(int i=0;i<(int)(Math.pow(2, 30));i++){
for(int j=0;i<(int)(Math.pow(2, 30));i++)
for(int k=0;i<(int)(Math.pow(2, 30));i++){
f+=2;
f--;
}
}
System.out.println(System.currentTimeMillis()-current+" 毫秒");
}
public static void testDouble(){
long current=System.currentTimeMillis();
double f=0;
for(int i=0;i<(int)(Math.pow(2, 30));i++){
for(int j=0;i<(int)(Math.pow(2, 30));i++)
for(int k=0;i<(int)(Math.pow(2, 30));i++){
f+=2;
f--;
}
}
System.out.println(System.currentTimeMillis()-current+" 毫秒");
}
public static void main(String []args){
// System.out.println(Math.pow(2, 500));
testfloat();
testDouble();
}
}
下面是在我機器上運行的結果
275970 毫秒
276267 毫秒