<< 猫ページ | Home | Google App Engineをローカルで動かして、Androidからアクセスする。 >>
PR: 転職    お墓    エコ    通販    結婚相談所    シルバー    質屋    葬式    漫画    エステサロン   

NetWalkerのスピードを測定。

NetWalkerの体感速度は、300MHzくらいのx86という印象。丁度家にある古いThinkPad(Pentium2 350MHz)と同じくらい。で、実際のところのCPUパワーがどの程度なのか、クイックソートの計算速度で比べてみた。1000件のデータを、並べ替える処理を10000回実行し、5回の平均を取ってみた。

コードは、C版とJava版を作成。コンパイラオプションや、Javaの実行系も変えながらとってみた。

--- C版 ---
#include <stdio.h>
#include <string.h>
#include <sys/time.h>
#include <stdlib.h>

void myQsort(int data[], int left, int right) {
if (left >= right) return;
int l = left;
int r = right;
int pivot = data[(unsigned int)(left + right) / 2];
while (1) {
while (data[l] < pivot) {
++l;
}
while (data[r] > pivot) {
--r;
}
if (l >= r) break;
int wk = data[l];
data[l] = data[r];
data[r] = wk;
++l; --r;
}

myQsort(data, left, l - 1);
myQsort(data, r + 1, right);
}

typedef struct timeval TIME_VAL;

long getTimeDiffInMillis(TIME_VAL *pStart, TIME_VAL *pEnd) {
long ret = (long)pEnd->tv_sec * 1000 * 1000 + (long)pEnd->tv_usec;
ret -= (long)pStart->tv_sec * 1000 * 1000 + (long)pStart->tv_usec;
return ret / 1000;
}

int main(char **argv) {
const int ITERATION = 10000;
const int SIZE = 1000;
int org_data[SIZE];
int i;
TIME_VAL start, end;

for (i = 0; i < SIZE; ++i) {
org_data[i] = rand();
}

gettimeofday(&start, NULL);

for (i = 0; i < ITERATION; ++i) {
int data[SIZE];
memcpy(data, org_data, sizeof(data));
myQsort(data, 0, SIZE - 1);
}

gettimeofday(&end, NULL);

printf("%ldms\n", getTimeDiffInMillis(&start, &end));
}
--- Java版 ---
import java.util.Random;

public class Qsort {
public static void qsort(int[] data, int left, int right) {
if (left >= right) return;
int l = left;
int r = right;
int pivot = data[(left + right) >>> 1];
while (true) {
while (data[l] < pivot) ++l;
while (pivot < data[r]) --r;
if (l >= r) break;
int wk = data[l];
data[l] = data[r];
data[r] = wk;
++l; --r;
}

qsort(data, left, l - 1);
qsort(data, r + 1, right);
}

public static void main(String[] args) {
int[] data = new int[1000];
Random r = new Random();
for (int i = 0; i < data.length; ++i) {
data[i] = r.nextInt();
}

long start = System.currentTimeMillis();
for (int i = 0; i < 10000; ++i) {
qsort(data.clone(), 0, data.length - 1);
}
System.out.printf("Elapsed %,dms%n", System.currentTimeMillis() - start);
}
}

結果(単位は、ms)。まずは、比較用のデスクトップ(Core 2 Duo 3GHz)。

gcc version 4.3.2 (Ubuntu 4.3.2-1ubuntu12)
最適化無し 1,056
-O3 610

IcedTea6 1.3.1 (6b12-0ubuntu6.5) Runtime Environment (build 1.6.0_0-b12)
OpenJDK 64-Bit Server VM (build 1.6.0_0-b12, mixed mode)
718

Java(TM) SE Runtime Environment (build 1.6.0_10-b33)
Java HotSpot(TM) 64-Bit Server VM (build 11.0-b15, mixed mode)
686

若干OpenJDKの方が遅いようだ。さすがに今どきのJavaは、この手の計算処理なら、ネイティブコードと遜色無い速度で動く。

次にNetWalker

gcc version 4.3.3 (Ubuntu 4.3.3-5ubuntu4)
最適化無し 5,148
-O3 2,272

OpenJDK Runtime Environment (IcedTea6 1.4.1) (6b14-1.4.1-0ubuntu10)
OpenJDK Core VM (build 14.0-b08, interpreted mode)
最適化無し 65.529
-cacao 5,380

ARMの場合、Javaの最適化は、まだ甘いようで、Cに2倍以上の差を付けられている。しかし、この2,272msという結果には、ちょっと驚いた。これだと、Core 2の800MHz相当くらいの実力はあることになる。しかし、どうひいき目に見ても、体感はそんなに速くは感じられない。なぜなんだろう、OSのコンパイル時に最適化オプションが付いていないんだろうか? CPUメータ見てると、何か処理をしている時は、常にふり切っている感じなので、I/O処理がネックとは考えにくい。まだまだ速くなる余地はあるのではないだろうか。

P.S. C版で、開始時間の取得位置が不適切だったのを修正。




コメント追加 トラックバック送信
このサイトの掲載内容は私自身の見解であり、必ずしもIBMの立場、戦略、意見を代表するものではありません。
日本アイ・ビー・エム 花井 志生 Since 1997.6.8