ソートロジック大会
猪突猛進のいのしし年です。
お世話になります。
出会いの経験
・ポケットコンピュータにてベーシックと出会う
・先輩(キキョウ屋)からZ80マシン入手 ROMベーシックと出会う
・外付けFDDドライブを入手 DISKベーシックと出会う
・MS-DOSと出会う
・アセンブラと出会う ハンドアセンブル全盛 Z80なら16進数で、ある程度読める書ける、IPL等改造して楽しんでいた
・マクロアセンブラプログラマーズハンドブックと出会う マクロアセンブラにはまる
・社内でコボルと出会う 仕事でプログラムに携わる 趣味ではやらなくなる
・社内で系統が変わる また、趣味でプログラミングを始める
・アクティブベーシックと出会う・・・・・(アクティブベーシック掲示板)
出会いはたのしいですね
そんなわけで20台前半から始め、20数年 46歳のAB初心者です。
追伸:プログラミング関係です。
マティさんの800万件ソート実行中にtempフォルダを見てください。
何をやっているのか、非常に楽しいことが起こっています。
ずっと見入ってしまいました。
追伸:プログラミング掲示板が質問版になっていました。申し訳ありません。
出会いの経験
・ポケットコンピュータにてベーシックと出会う
・先輩(キキョウ屋)からZ80マシン入手 ROMベーシックと出会う
・外付けFDDドライブを入手 DISKベーシックと出会う
・MS-DOSと出会う
・アセンブラと出会う ハンドアセンブル全盛 Z80なら16進数で、ある程度読める書ける、IPL等改造して楽しんでいた
・マクロアセンブラプログラマーズハンドブックと出会う マクロアセンブラにはまる
・社内でコボルと出会う 仕事でプログラムに携わる 趣味ではやらなくなる
・社内で系統が変わる また、趣味でプログラミングを始める
・アクティブベーシックと出会う・・・・・(アクティブベーシック掲示板)
出会いはたのしいですね
そんなわけで20台前半から始め、20数年 46歳のAB初心者です。
追伸:プログラミング関係です。
マティさんの800万件ソート実行中にtempフォルダを見てください。
何をやっているのか、非常に楽しいことが起こっています。
ずっと見入ってしまいました。
追伸:プログラミング掲示板が質問版になっていました。申し訳ありません。
コーヒーブレイク終了
お世話になります。
マージソートの構造を理解できました。
arさんのマージソートを参考に非再帰版を作成しました。
速度的には追い越すことはできませんでした。
どなたかご援助をお願いします。(質問版)
2005年08月26日(金) 22の投稿
マージソートの構造を理解できました。
arさんのマージソートを参考に非再帰版を作成しました。
速度的には追い越すことはできませんでした。
[ここをクリックすると内容が表示されます]
ワーク配列をグローバル領域に定義してください。
コード: 全て選択
Dim Work[TableSize] As Long
コード: 全て選択
Sub Sort(ByVal S As Long,ByVal E As Long)
Dim Bunkatu As Long
Bunkatu=1
While Bunkatu<E
Bunkatu=Bunkatu*2
For i=S To E Step Bunkatu
For j=i To i+(Bunkatu\2)-1
Work[j-i]=Index[j]
Next j
k=0
l=i
While (k<Bunkatu\2) And (j<=i+Bunkatu-1) And (j<=E)
If lstrcmp(KeyTable[Work[k]],KeyTable[Index[j]])>0 Then
Index[l]=Index[j]
j=j+1
Else
Index[l]=Work[k]
k=k+1
End If
l=l+1
Wend
For j=k To Bunkatu\2-1
Index[l+(j-k)]=Work[j]
Next j
Next i
Wend
End Sub
ここをクリックすると実行速度比較が表示されます。 [ここをクリックすると内容が表示されます]
ヘルプ:河川屋さんのヒープソートが実行できません。実行環境 (ActiveBasic Ver.4.10~4.11.03)
(Cpu Pentium4 周波数2.66GHz メモリ256MByte)
テストcsvファイル 5桁のランダム数字も5桁のランダム文字もソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 1,000 5,000 10,000 50,000 100,000 記事
arさん ラディックス 0.010 0.030 0.060 0.250 0.551 ラディックス最速
arさん マージ 0.010 0.060 0.120 0.411 0.892 マージ最速
arさん クイック 0.010 0.050 0.110 0.410 0.952 クイック最速
omasu マージ(arさん版) 0.030 0.160 0.380 2.123 4.527
omasu マージ(非再帰) 0.030 0.170 0.380 2.233 4.797
omasu クイック(中級編) 0.050 0.190 0.421 2.493 5.398
omasu クイック(入門編) 0.040 0.210 0.450 2.834 6.639
マティさん クイック改4(800万件) 0.050 0.080 0.120 0.821 6.649
〃 〃 800万件 2080.631秒 最大件数ソート可能
イグトランスさん クイック 0.040 0.241 0.521 3.235 6.709
マティさん クイック(初級編) 0.040 0.250 0.510 3.275 7.200
omasu シェル4(0.8975+0.45) 0.060 0.261 0.581 3.616 7.861 シェル最速
omasu シェル3(0.8975+¥3) 0.060 0.290 0.681 4.627 9.223
omasu コーム2(挿入法1.4) 0.091 0.391 0.822 4.767 10.705 コ-ム最速
omasu シェル2(クヌース大大先生) 0.050 0.311 0.721 4.907 11.677
河川屋さん コム(挿入法) 0.070 0.411 0.901 5.958 12.308
河川屋さん 改シェル法(クヌース大先生) 0.060 0.361 0.721 5.057 12.528
omasu コーム2(バブル1.4) 0.130 0.400 0.922 5.578 12.899
omasu シェル(ノーマル) 0.070 0.351 0.851 5.748 13.149
omasu コーム(ノーマル) 0.121 0.450 1.032 6.359 13.620
omasu 単純挿入法(バイナリサーチ) 0.080 0.811 2.895 65.595 261.576 単純挿入法最速
omasu マージ(非再帰・非ワーク) 0.060 0.531 1.853 39.176 155.784
omasu シェル(選択法) 0.381 4.747 13.770 177.305 ―――――――
omasu シェル(ノーマル・再帰) 0.661 14.801 60.006 ――――――― ―――――――
omasu 単純挿入法 0.862 18.778 77.031 ――――――― ―――――――
omasu シェーカー(バブル) 1.191 27.880 116.237 ――――――― ――――――― シェーカー最速
omasu 単純選択法 1.432 36.603 143.632 ――――――― ――――――― 単純選択法最速
omasu バブル 1.482 38.215 150.567 ――――――― ――――――― バブル最速
トーナメント法 ただいま勉強中です。
ヒープ ただいま勉強中です。
テストcsvファイル 5桁のランダム数字をソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 1,000 5,000 10,000 50,000 100,000 記事
河川屋さん (PJ)クイック(改2) 0.080 0.140 0.271 0.801 1.142 クイック最速
河川屋さん (PJ)クイック(改1) 0.020 0.130 0.170 0.732 1.151 クイック最速
河川屋さん (PJ)クイック(ノーマル版) 0.130 0.160 0.210 0.831 1.192 クイック最速
マティさん (PJ)コーム 0.010 0.060 0.120 0.581 1.643 コーム最速
どなたかご援助をお願いします。(質問版)
2005年08月26日(金) 22の投稿
[ここをクリックすると内容が表示されます]
コード: 全て選択
Sub Sort(ByVal S As Long,ByVal E As Long)
l=(E\2)+1
k=E
While l>0'1
l=l-1
Furuiotoshi() ' SHIFT
Wend
While k>0'1
Swap(Index[1],Index[k])
k=k-1'1
Furuiotoshi() ' SHIFT
Wend
'
' ヒープソート(河川屋さん原本)
' L=(N\2)+1 : R=N
' WHILE L>1
' L=L-1 : GOSUB 3500'SHIFT
' WEND
' WHILE R>1
' SWAP DAT(1),DAT(R)
' R=R-1 : GOSUB 3500'SHIFT
' WEND
' RETURN
End Sub
'
' 篩い落とし
'
Sub Furuiotoshi()
Dim X As Long
i=l
j=2*l
X=Index[l]
IF (j<k) And (lstrcmp(KeyTable[Index[j]],KeyTable[Index[j+1]])<0) THEN
j=j+1
EndIf
WHILE (j<=k) And (lstrcmp(KeyTable[Index[X]],KeyTable[Index[j]])<0)
Index=Index[j]
i=j
j=2*j
IF (j<k) And (lstrcmp(KeyTable[Index[j]],KeyTable[Index[j+1]])<0) THEN
j=j+1
EndIf
WEND
Index=X
'
'3500 '篩い落とし (河川屋さん原本)
' I=L : J=2*L : X=DAT(L)
' IF J<R AND DAT(J)<DAT(J+1) THEN J=J+1
' WHILE J<=R AND X<DAT(J)
' DAT(I)=DAT(J) : I=J : J=2*J
' IF J<R AND DAT(J)<DAT(J+1) THEN J=J+1
' WEND
' DAT(I)=X
' RETURN
End Sub
>河川屋さんのヒープソートが実行できません。
>どなたかご援助をお願いします。
いちおうコメントしておきます。
Sub Sort(S,E)
こうするということは、Sが1以外でも正しく動くことを意味するため、
ヒープソートの場合は特にやめたほうがいいです。
データ開始が0or1以外は意味ないヤヤコシサを持ち込むだけだから考えたくないです。
まず、ヒープとは。
メモリー管理の際のヒープは関係ありません。
ヒープとは、2分木の特殊な形式で、以下の構造をしています。
1.親と子の関係:親をiとすると、子は、2iおよび2i+1。
(iは1から始まるのを前提として。)
2.親子の大小関係:親と子では、親のほうが大きい数値である。
子の2つ(2i、2i+1)の大小関係は不明。
で、まず、データをヒープになるようにします。
その結果、DAT(1)にはデータの最大値が入ります。
これで最大値が確定したので、DAT(1)とDAT(N)を入れ替える。
次に小さい値は、DAT(2)とDAT(3)のいずれか。
ですが、そうするかわりに、ヒープを再構築する。
といっても、そんなに手間はかからない。
DAT(2)とDAT(3)のうち大きいほうとDAT(1)を入れ替える。
DAT(2)のほうとして、
DAT(4)とDAT(5)のうち大きいほうとDAT(2)を入れ替える。
DAT(4)のほうとして、
DAT(8)とDAT(9)のうち大きいほうとDAT(2)を入れ替える。
以下略。途中で入れ替え不要となれば打ち止め。最悪でも、高々logN回のオーダー。
これでヒープが復活したので、2番目に小さい値が確定。
DAT(1)とDAT(N-1)を入れ替える。
ヒープを再構築する。高々logN回のオーダー。
以下繰り返せばソート終わり。
あ、ヒープを作る話が残っていました。
データの後ろ半分(N\2+1) だけを考えると、子を持たないため、ヒープである。
ここから、データを1つづつ遡り、ヒープを構築する。(親をLとし、ヒープが成り立つよう
下に向かって調整する。このルーチンはヒープ再構築と同じである。)
これを繰り返した結果、i=1まで戻ればヒープ完成。
以上。
' ヒープソート N88における最も普通の組み方。
L=(N\2)+1 : R=N
WHILE L>1
L=L-1 : GOSUB 3500'SHIFT
WEND
WHILE R>1
SWAP DAT(1),DAT(R)
R=R-1 : GOSUB 3500'SHIFT
WEND
RETURN
3500 '篩い落とし
I=L : J=2*L : X=DAT(L)
IF J<R AND DAT(J)<DAT(J+1) THEN J=J+1
WHILE J<=R AND X<DAT(J)
DAT(I)=DAT(J) : I=J : J=2*J
IF J<R AND DAT(J)<DAT(J+1) THEN J=J+1
WEND
DAT(I)=X
RETURN
>どなたかご援助をお願いします。
いちおうコメントしておきます。
Sub Sort(S,E)
こうするということは、Sが1以外でも正しく動くことを意味するため、
ヒープソートの場合は特にやめたほうがいいです。
データ開始が0or1以外は意味ないヤヤコシサを持ち込むだけだから考えたくないです。
まず、ヒープとは。
メモリー管理の際のヒープは関係ありません。
ヒープとは、2分木の特殊な形式で、以下の構造をしています。
1.親と子の関係:親をiとすると、子は、2iおよび2i+1。
(iは1から始まるのを前提として。)
2.親子の大小関係:親と子では、親のほうが大きい数値である。
子の2つ(2i、2i+1)の大小関係は不明。
で、まず、データをヒープになるようにします。
その結果、DAT(1)にはデータの最大値が入ります。
これで最大値が確定したので、DAT(1)とDAT(N)を入れ替える。
次に小さい値は、DAT(2)とDAT(3)のいずれか。
ですが、そうするかわりに、ヒープを再構築する。
といっても、そんなに手間はかからない。
DAT(2)とDAT(3)のうち大きいほうとDAT(1)を入れ替える。
DAT(2)のほうとして、
DAT(4)とDAT(5)のうち大きいほうとDAT(2)を入れ替える。
DAT(4)のほうとして、
DAT(8)とDAT(9)のうち大きいほうとDAT(2)を入れ替える。
以下略。途中で入れ替え不要となれば打ち止め。最悪でも、高々logN回のオーダー。
これでヒープが復活したので、2番目に小さい値が確定。
DAT(1)とDAT(N-1)を入れ替える。
ヒープを再構築する。高々logN回のオーダー。
以下繰り返せばソート終わり。
あ、ヒープを作る話が残っていました。
データの後ろ半分(N\2+1) だけを考えると、子を持たないため、ヒープである。
ここから、データを1つづつ遡り、ヒープを構築する。(親をLとし、ヒープが成り立つよう
下に向かって調整する。このルーチンはヒープ再構築と同じである。)
これを繰り返した結果、i=1まで戻ればヒープ完成。
以上。
' ヒープソート N88における最も普通の組み方。
L=(N\2)+1 : R=N
WHILE L>1
L=L-1 : GOSUB 3500'SHIFT
WEND
WHILE R>1
SWAP DAT(1),DAT(R)
R=R-1 : GOSUB 3500'SHIFT
WEND
RETURN
3500 '篩い落とし
I=L : J=2*L : X=DAT(L)
IF J<R AND DAT(J)<DAT(J+1) THEN J=J+1
WHILE J<=R AND X<DAT(J)
DAT(I)=DAT(J) : I=J : J=2*J
IF J<R AND DAT(J)<DAT(J+1) THEN J=J+1
WEND
DAT(I)=X
RETURN
ヒープソートについて
お世話になります。
河川屋さんのご意見に感謝しております。
ヒープソートはやはり非常に難しいロジックだと思います。
なかなか動きません。
マティさんのホームページのヒープロジックもトライをしておりますが、
やはり難しいです。
ネットで探し回りCやVBからのコンバートもしておりますが、
やはり動きません。
勉強と努力が足りんと自分に言い聞かせております。
どなたかソートロジック実行速度比較環境にしていただける方はおられませんでしょうか?(質問版)
追伸:ネットで検索すると「ソートロジック大会」も検索されます。
皆様の貴重なロジックを公開したいと思いますので、検索キーとして記述します。
ベーシック、アクティブベーシック
バブルソート、単純挿入ソート、単純選択ソート、シェーカーソート、
シェルソート、コムソート、コームソート
ヒープソート、トーナメントソート、ラディックスソート
マージソート、クイックソート
河川屋さんのご意見に感謝しております。
ヒープソートはやはり非常に難しいロジックだと思います。
なかなか動きません。
マティさんのホームページのヒープロジックもトライをしておりますが、
やはり難しいです。
ネットで探し回りCやVBからのコンバートもしておりますが、
やはり動きません。
勉強と努力が足りんと自分に言い聞かせております。
どなたかソートロジック実行速度比較環境にしていただける方はおられませんでしょうか?(質問版)
追伸:ネットで検索すると「ソートロジック大会」も検索されます。
皆様の貴重なロジックを公開したいと思いますので、検索キーとして記述します。
ベーシック、アクティブベーシック
バブルソート、単純挿入ソート、単純選択ソート、シェーカーソート、
シェルソート、コムソート、コームソート
ヒープソート、トーナメントソート、ラディックスソート
マージソート、クイックソート
oomasuさんご苦労様です。ヒープソートですが、以下のソースで実行可能でしょうか?
(配列のベースが分からなかったので2種類準備しました。)
動作確認を行っていないので、何かあればご連絡下さい。
PS.最近検索を行うと、ここが出る事が多くなってきましたね!
(配列のベースが分からなかったので2種類準備しました。)
動作確認を行っていないので、何かあればご連絡下さい。
ヒープソート(0ベース) [ここをクリックすると内容が表示されます]
コード: 全て選択
'-----------------------------------------------------------
' ヒープソート(0ベース)
'-----------------------------------------------------------
Sub HeapSort( S As Long, E As Long)
Dim i As Long
Dim j As Long
Dim w As xCd
If(S<>0)Then MessageBox(0,"処理できません","",BM_OK):End Sub
'ヒープ作成(最初の処理)
For i = (E \ 2) To 0 Step -1 '0基準
MakeHeap(i, E)
Next
'並べ替え
For i = E To 2 Step -1
Swap(Index[0],Index)
MakeHeap(0, i-1)
Next
Swap(Index[0],Index[1])
End Sub
'実際に、ヒープを編集する処理です。
Sub MakeHeap(s As Long, n As Long)
Dim i As Long
i = s * 2 + 1 '0基準
Do
If (i < n) Then If (lstrcmp(KeyTable[Index],KeyTable[i+1])<0) Then i=i+1 '子の大を選択
If (lstrcmp(KeyTable[Index[s]],KeyTable)>0)) Then Exit Do '親が大ならHeap完成
'親と子を交換後、処理を繰り返す
Swap(Index[s],Index)
s = i
i = i * 2 + 1 '0基準
Loop Until(i > n)
End Sub
ヒープソート(1ベース) [ここをクリックすると内容が表示されます]
コード: 全て選択
'-----------------------------------------------------------
' ヒープソート(1ベース)
'-----------------------------------------------------------
Sub HeapSort( S As Long, E As Long)
Dim i As Long
Dim j As Long
Dim w As xCd
If(S<>1)Then MessageBox(0,"処理できません","",BM_OK):End Sub
'ヒープ作成(最初の処理)
For i = (E \ 2 + 1) To 1 Step -1 '1基準
MakeHeap(i, E)
Next
'並べ替え
For i = E To 3 Step -1
Swap(Index[1],Index)
MakeHeap(1, i-1)
Next
Swap(Index[1],Index[2])
End Sub
'実際に、ヒープを編集する処理です。
Sub MakeHeap(s As Long, n As Long)
Dim i As Long
i = s * 2 '1基準
Do
If (i < n) Then If (lstrcmp(KeyTable[Index],KeyTable[i+1])<0) Then i=i+1 '子の大を選択
If (lstrcmp(KeyTable[Index[s]],KeyTable)>0)) Then Exit Do '親が大ならHeap完成
'親と子を交換後、処理を繰り返す
Swap(Index[s],Index)
s = i
i = i * 2 '1基準
Loop Until(i > n)
End Sub
PS.最近検索を行うと、ここが出る事が多くなってきましたね!
ヒープソート実行管理委員会の能力不足についてⅡ
お世話になります。
マティさんの「スループット」の早さ、
「ターンアラウンドタイム」にはいつも恐れ入ります。
実行してみましたが、エラーが発生、実行可能にまでは修正できましたが、ソートされません。
現在、解析中です。
どうも、中間変数のタイプのちがいが災いをしているようです。
以下に実行速度比較環境の再提示をいたします。
もちろんイグトランスさんの母体です。
マティさんの「スループット」の早さ、
「ターンアラウンドタイム」にはいつも恐れ入ります。
実行してみましたが、エラーが発生、実行可能にまでは修正できましたが、ソートされません。
現在、解析中です。
どうも、中間変数のタイプのちがいが災いをしているようです。
以下に実行速度比較環境の再提示をいたします。
もちろんイグトランスさんの母体です。
実行速度環境プログラムの再提示 マージ(非再帰)版 [ここをクリックすると内容が表示されます]
H17.12.17致命的なバグがあります。次の投稿をご利用ください。コード: 全て選択
'********************************************************************************
'* CSVファイル ソートプログラム
'********************************************************************************
'
#strict ' コンパイルの際に型チェックが厳密に行われるようになります。
#prompt ' #include <basic\prompt.sbp> , #N88BASIC でも可
'
Declare Function timeGetTime Lib "winmm.dll" () As DWord
Declare Function CharNext Lib "User32" Alias "CharNextA" (psz As BytePtr) As BytePtr
'
Const SubWndTitle$="ソート" ' メッセージタイトル
Const infile$="infile1000.csv" ' 入力ファイル名定義(フルパス指定、省略時はカレント)
Const outfile$="outfile.csv" ' 入力ファイル名定義(フルパス指定、省略時はカレント)
Const TableSize=110000 ' データ最大件数定義
'
' グローバル領域変数定義
'
Dim hHeap As HANDLE
Dim KeyTable[TableSize] As BytePtr,DataTable[TableSize] As BytePtr,Index[TableSize] As Long,DataSize As Long
Dim Work[TableSize] As Long
Dim StartTime1 As DWord,EndTime1 As DWord,StartTime2 As DWord,EndTime2 As DWord
Dim hInputFile As HANDLE
Dim FileSize As DWord,dwReadSize As DWord
Dim pInputBuffer As BytePtr
Dim strCurrentLine As String
Dim i As Long,j As Long,k As Long,l As Long
'
'********************************************************************************
'* プログラム開始
'********************************************************************************
'
Function OwnerWnd() As HWND
OwnerWnd=_PromptSys_hWnd
End Function
StartTime1=timeGetTime()
Print "ソートファイル名:",infile$
Print
If MessageBox(OwnerWnd(),"ソート処理を実行します。よろしいですか?",SubWndTitle$,MB_YESNO or MB_ICONINFORMATION)=IDNO Then
Goto *ProgramEnd
End If
hHeap=HeapCreate(HEAP_NO_SERIALIZE,131072,0)
If hHeap=0 Then
End
End If
Print "program start",StartTime1-StartTime1
Print
'
'********************************************************************************
'* ファイルリード
'********************************************************************************
'
StartTime2=timeGetTime()
Print "read start",StartTime2-StartTime1
'
' ファイルリード(プロシージャ)
'
Function FileRead(FileName As BytePtr) As BytePtr
hInputFile=CreateFile(FileName,GENERIC_READ,FILE_SHARE_READ,ByVal 0,OPEN_EXISTING,FILE_FLAG_SEQUENTIAL_SCAN,0) As HANDLE
If hInputFile=INVALID_HANDLE_VALUE Then
Exit Function
End If
FileSize=GetFileSize(hInputFile,0)
FileRead=malloc(FileSize+1)
FileRead[FileSize]=0
ReadFile(hInputFile,FileRead,FileSize,VarPtr(dwReadSize),ByVal 0)
CloseHandle(hInputFile)
End Function
'
' ファイルリード
'
pInputBuffer=FileRead(infile$)
If pInputBuffer=0 Then
Goto *ProgramEnd
End If
'
' ファイルリード終了
'
EndTime2=timeGetTime()
Print "read end",EndTime2-StartTime1,"ファイルリード時間:",(EndTime2-StartTime2)/1000;"秒"
Print
'
'********************************************************************************
'* データストック
'********************************************************************************
'
StartTime2=timeGetTime()
Print "stock start",StartTime2-StartTime1
'
' 行単位に分解抽出(プロシージャ)
'
Function GetLine(ByRef rpsz As BytePtr) As BytePtr
GetLine=rpsz
While GetWord(rpsz)<>&h0a0d ' GetWord(Ex"\r\n")
If GetByte(rpsz)=0 Then
rpsz=0
Exit Function
End If
rpsz=CharNext(rpsz)
Wend
SetByte(rpsz,0)
rpsz=rpsz+2
End Function
'
' メモリーブロックコピー(プロシージャ)
'
Function StrDupS(str As String) As BytePtr
Dim Size As DWord
Size=Len(str)+1
StrDupS=malloc(Size)
memcpy(StrDupS,StrPtr(str),Size)
End Function
'
' キー部抽出(プロシージャ)
'
Function GetKeyPart$(ByVal str As String) As String
Dim PartA As Long,PartB As Long
PartA=InStr(1,str,",")
If PartA>0 Then
PartB=InStr(PartA+1,str,",")
End If
GetKeyPart$=str
End Function
'
' 行単位に分解・キーテーブルストック・データテーブルストック
'
For i=0 To TableSize
strCurrentLine=GetLine(pInputBuffer)
KeyTable=StrDupS(GetKeyPart$(strCurrentLine)) ' KeyTableにキーストック
DataTable=StrDupS(Str$(i+1)+","+strCurrentLine) ' DataTableにデータストック
Index=i
If pInputBuffer=0 Then
Exit For
End If
Next
free(pInputBuffer)
DataSize=i-1
'
' データストック終了
'
EndTime2=timeGetTime()
Print "stock end",EndTime2-StartTime1,"データストック時間:",(EndTime2-StartTime2)/1000;"秒"
Print
'
'********************************************************************************
'* ソート
'********************************************************************************
'
StartTime2=timeGetTime()
Print "sort start",StartTime2-StartTime1
'
' ソート
'
Sort(0,DataSize)
'
EndTime2=timeGetTime()
Print "sort end",EndTime2-StartTime1," ソート時間:",(EndTime2-StartTime2)/1000;"秒"
Print
'
' ソートプロシージャ
'
Sub Sort(ByVal S As Long,ByVal E As Long)
Dim Bunkatu As Long
Bunkatu=1
While Bunkatu<E
Bunkatu=Bunkatu*2
For i=S To E Step Bunkatu
For j=i To i+(Bunkatu\2)-1
Work[j-i]=Index[j]
Next j
k=0
l=i
While (k<Bunkatu\2) And (j<=i+Bunkatu-1) And (j<=E)
If lstrcmp(KeyTable[Work[k]],KeyTable[Index[j]])>0 Then
Index[l]=Index[j]
j=j+1
Else
Index[l]=Work[k]
k=k+1
End If
l=l+1
Wend
For j=k To Bunkatu\2-1
Index[l+(j-k)]=Work[j]
Next j
Next i
Wend
End Sub
' スワッププロシージャ
'
Sub Swap(ByRef x As Long,ByRef y As Long)
Dim temp As Long
temp=x
x=y
y=temp
End Sub
'
'********************************************************************************
'* ソートしたテーブルをファイルに出力
'********************************************************************************
'
StartTime2=timeGetTime()
Print "file out start",StartTime2-StartTime1
'
Open outfile$ For Output As #2
For i=0 To DataSize
Print #2,MakeStr(DataTable(Index))
Next i
Close
'
EndTime2=timeGetTime()
Print "file out end",EndTime2-StartTime1,"ファイルアウト時間:",(EndTime2-StartTime2)/1000;"秒"
Print
'
'********************************************************************************
'* プログラム終了確認
'********************************************************************************
'
EndTime1=timeGetTime()
Print "program end",EndTime1-StartTime1,"プログラム実行時間:",(EndTime1-StartTime1)/1000;"秒"
Print
HeapDestroy(hHeap)
'
*ProgramEnd
MessageBox(OwnerWnd(),"ソート処理が終了しました。",SubWndTitle$,MB_OK or MB_ICONINFORMATION)
End
最後に編集したユーザー omasu [ 2005年12月17日(土) 16:11 ], 累計 1 回
配列はゼロベースのようなので、以下の処理でソートできると思います。
確認事項
①.Outputファイルの先頭項目は元データの行番号になっていますよね!
②.キーの作成方法がおかしいと思うのですが・・・
(KeyTableに行データの全体が格納されているように思えます。)
途中から仕様を変更していませんか?
ヒープソート(0ベース) [ここをクリックすると内容が表示されます]
コード: 全て選択
'-----------------------------------------------------------
' ヒープソート(0ベース)
'-----------------------------------------------------------
Sub Sort( S As Long, E As Long)
Dim i As Long
Dim j As Long
If(S<>0)Then If(MessageBox(0,"処理できません","",MB_OK)=MB_OK)Then Exit Sub
'ヒープ作成(最初の処理)
For i = (E \ 2) To 0 Step -1 '0基準
MakeHeap(i, E)
Next
'並べ替え
For i = E To 2 Step -1
Swap(Index[0],Index)
MakeHeap(0, i-1)
Next
Swap(Index[0],Index[1])
End Sub
'実際に、ヒープを編集する処理です。
Sub MakeHeap(s As Long, n As Long)
Dim i As Long
i = s * 2 + 1 '0基準
Do
If (i < n) Then If (lstrcmp(KeyTable[Index],KeyTable[Index[i+1]])<0) Then i=i+1 '子の大を選択
If (lstrcmp(KeyTable[Index[s]],KeyTable[Index])>0) Then Exit Do '親が大ならHeap完成
'親と子を交換後、処理を繰り返す
Swap(Index[s],Index)
s = i
i = s * 2 + 1 '0基準
Loop Until(i > n)
End Sub
確認事項
①.Outputファイルの先頭項目は元データの行番号になっていますよね!
②.キーの作成方法がおかしいと思うのですが・・・
(KeyTableに行データの全体が格納されているように思えます。)
途中から仕様を変更していませんか?
キーデータの確認方法 [ここをクリックすると内容が表示されます]
コード: 全て選択
Sub MakeHeap(s As Long, n As Long)
Dim A$,B$
Dim i As Long
i = s * 2 + 1 '0基準
Do
If (i < n) Then If (lstrcmp(KeyTable[Index],KeyTable[Index[i+1]])<0) Then i=i+1 '子の大を選択
'キーデータを確認する
A$=KeyTable[Index[s]]
B$=KeyTable[Index]
If (lstrcmp(KeyTable[Index[s]],KeyTable[Index])>0) Then Exit Do '親が大ならHeap完成
'親と子を交換後、処理を繰り返す
Swap(Index[s],Index)
s = i
i = s * 2 + 1 '0基準
Loop Until(i > n)
End Sub
実行比較環境のバグについてのお詫び
お世話になります。
>確認事項
>①.Outputファイルの先頭項目は元データの行番号になっていますよね!
ソートロジック大会発足時から入力データに連番をつけ、出力データの先頭項目に付与しています。
ソート後の確認のためにつけた仕様です。
>②.キーの作成方法がおかしいと思うのですが・・・
>(KeyTableに行データの全体が格納されているように思えます。)
> 途中から仕様を変更していませんか?
マティさんに指摘されるまでとんでもないことを気づかずにいました。
確かにキーの中にデータ全体が格納されています。
いつこのようなバグを作りこんだのかは9月23日以前である事以外、今ではわかりません。
ロジックを確認したところ、バグは「Function GetKeyPart$」の中に存在していました。
修正後の実行速度比較環境のプログラムを再々投稿いたします。
しかし、大問題なのは実行時間です。
このバグにより、実行時間は4倍ほど多くかかっていたもようです。
全てのロジックを再計測いたしますので、もう少し時間をください。
申し訳ありませんでした。m(_w_)m
>確認事項
>①.Outputファイルの先頭項目は元データの行番号になっていますよね!
ソートロジック大会発足時から入力データに連番をつけ、出力データの先頭項目に付与しています。
ソート後の確認のためにつけた仕様です。
>②.キーの作成方法がおかしいと思うのですが・・・
>(KeyTableに行データの全体が格納されているように思えます。)
> 途中から仕様を変更していませんか?
マティさんに指摘されるまでとんでもないことを気づかずにいました。
確かにキーの中にデータ全体が格納されています。
いつこのようなバグを作りこんだのかは9月23日以前である事以外、今ではわかりません。
ロジックを確認したところ、バグは「Function GetKeyPart$」の中に存在していました。
修正後の実行速度比較環境のプログラムを再々投稿いたします。
実行速度環境プログラムの再々提示 マージ(非再帰)版 [ここをクリックすると内容が表示されます]
非表示とはいえ、何度も申し訳ありません。コード: 全て選択
'********************************************************************************
'* CSVファイル ソートプログラム
'********************************************************************************
'
#strict ' コンパイルの際に型チェックが厳密に行われるようになります。
#prompt ' #include <basic\prompt.sbp> , #N88BASIC でも可
'
Declare Function timeGetTime Lib "winmm.dll" () As DWord
Declare Function CharNext Lib "User32" Alias "CharNextA" (psz As BytePtr) As BytePtr
'
Const SubWndTitle$="ソート" ' メッセージタイトル
Const infile$="infile1000.csv" ' 入力ファイル名定義(フルパス指定、省略時はカレント)
Const outfile$="outfile.csv" ' 入力ファイル名定義(フルパス指定、省略時はカレント)
Const TableSize=110000 ' データ最大件数定義
'
' グローバル領域変数定義
'
Dim hHeap As HANDLE
Dim KeyTable[TableSize] As BytePtr,DataTable[TableSize] As BytePtr,Index[TableSize] As Long,DataSize As Long
Dim Work[TableSize] As Long
Dim StartTime1 As DWord,EndTime1 As DWord,StartTime2 As DWord,EndTime2 As DWord
Dim hInputFile As HANDLE
Dim FileSize As DWord,dwReadSize As DWord
Dim pInputBuffer As BytePtr
Dim strCurrentLine As String
Dim i As Long,j As Long,k As Long,l As Long
'
'********************************************************************************
'* プログラム開始
'********************************************************************************
'
Function OwnerWnd() As HWND
OwnerWnd=_PromptSys_hWnd
End Function
StartTime1=timeGetTime()
Print "ソートファイル名:",infile$
Print
If MessageBox(OwnerWnd(),"ソート処理を実行します。よろしいですか?",SubWndTitle$,MB_YESNO or MB_ICONINFORMATION)=IDNO Then
Goto *ProgramEnd
End If
hHeap=HeapCreate(HEAP_NO_SERIALIZE,131072,0)
If hHeap=0 Then
End
End If
Print "program start",StartTime1-StartTime1
Print
'
'********************************************************************************
'* ファイルリード
'********************************************************************************
'
StartTime2=timeGetTime()
Print "read start",StartTime2-StartTime1
'
' ファイルリード(プロシージャ)
'
Function FileRead(FileName As BytePtr) As BytePtr
hInputFile=CreateFile(FileName,GENERIC_READ,FILE_SHARE_READ,ByVal 0,OPEN_EXISTING,FILE_FLAG_SEQUENTIAL_SCAN,0) As HANDLE
If hInputFile=INVALID_HANDLE_VALUE Then
Exit Function
End If
FileSize=GetFileSize(hInputFile,0)
FileRead=malloc(FileSize+1)
FileRead[FileSize]=0
ReadFile(hInputFile,FileRead,FileSize,VarPtr(dwReadSize),ByVal 0)
CloseHandle(hInputFile)
End Function
'
' ファイルリード
'
pInputBuffer=FileRead(infile$)
If pInputBuffer=0 Then
Goto *ProgramEnd
End If
'
' ファイルリード終了
'
EndTime2=timeGetTime()
Print "read end",EndTime2-StartTime1,"ファイルリード時間:",(EndTime2-StartTime2)/1000;"秒"
Print
'
'********************************************************************************
'* データストック
'********************************************************************************
'
StartTime2=timeGetTime()
Print "stock start",StartTime2-StartTime1
'
' 行単位に分解抽出(プロシージャ)
'
Function GetLine(ByRef rpsz As BytePtr) As BytePtr
GetLine=rpsz
While GetWord(rpsz)<>&h0a0d ' GetWord(Ex"\r\n")
If GetByte(rpsz)=0 Then
rpsz=0
Exit Function
End If
rpsz=CharNext(rpsz)
Wend
SetByte(rpsz,0)
rpsz=rpsz+2
End Function
'
' メモリーブロックコピー(プロシージャ)
'
Function StrDupS(str As String) As BytePtr
Dim Size As DWord
Size=Len(str)+1
StrDupS=malloc(Size)
memcpy(StrDupS,StrPtr(str),Size)
End Function
'
' キー部抽出(プロシージャ)
'
Function GetKeyPart$(ByVal str As String) As String
Dim Length As Long,PartA As Long,PartB As Long
PartA=InStr(1,str,",")
If PartA>0 Then
PartB=InStr(PartA+1,str,",")
If PartB>0 Then
GetKeyPart$=Left$(str,PartB-1)
Exit Function
End If
End If
GetKeyPart$ = str
End Function
'
' 行単位に分解・キーテーブルストック・データテーブルストック
'
For i=0 To TableSize
strCurrentLine=GetLine(pInputBuffer)
KeyTable=StrDupS(GetKeyPart$(strCurrentLine)) ' KeyTableにキーストック
DataTable=StrDupS(Str$(i+1)+","+strCurrentLine) ' DataTableにデータストック
Index=i
If pInputBuffer=0 Then
Exit For
End If
Next
free(pInputBuffer)
DataSize=i-1
'
' データストック終了
'
EndTime2=timeGetTime()
Print "stock end",EndTime2-StartTime1,"データストック時間:",(EndTime2-StartTime2)/1000;"秒"
Print
'
'********************************************************************************
'* ソート
'********************************************************************************
'
StartTime2=timeGetTime()
Print "sort start",StartTime2-StartTime1
'
' ソート
'
Sort(0,DataSize)
'
EndTime2=timeGetTime()
Print "sort end",EndTime2-StartTime1," ソート時間:",(EndTime2-StartTime2)/1000;"秒"
Print
'
' ソートプロシージャ
'
Sub Sort(ByVal S As Long,ByVal E As Long)
Dim Bunkatu As Long
Bunkatu=1
While Bunkatu<E
Bunkatu=Bunkatu*2
For i=S To E Step Bunkatu
For j=i To i+(Bunkatu\2)-1
Work[j-i]=Index[j]
Next j
k=0
l=i
While (k<Bunkatu\2) And (j<=i+Bunkatu-1) And (j<=E)
If lstrcmp(KeyTable[Work[k]],KeyTable[Index[j]])>0 Then
Index[l]=Index[j]
j=j+1
Else
Index[l]=Work[k]
k=k+1
End If
l=l+1
Wend
For j=k To Bunkatu\2-1
Index[l+(j-k)]=Work[j]
Next j
Next i
Wend
End Sub
' スワッププロシージャ
'
Sub Swap(ByRef x As Long,ByRef y As Long)
Dim temp As Long
temp=x
x=y
y=temp
End Sub
'
'********************************************************************************
'* ソートしたテーブルをファイルに出力
'********************************************************************************
'
StartTime2=timeGetTime()
Print "file out start",StartTime2-StartTime1
'
Open outfile$ For Output As #2
For i=0 To DataSize
Print #2,MakeStr(DataTable(Index))
Next i
Close
'
EndTime2=timeGetTime()
Print "file out end",EndTime2-StartTime1,"ファイルアウト時間:",(EndTime2-StartTime2)/1000;"秒"
Print
'
'********************************************************************************
'* プログラム終了確認
'********************************************************************************
'
EndTime1=timeGetTime()
Print "program end",EndTime1-StartTime1,"プログラム実行時間:",(EndTime1-StartTime1)/1000;"秒"
Print
HeapDestroy(hHeap)
'
*ProgramEnd
MessageBox(OwnerWnd(),"ソート処理が終了しました。",SubWndTitle$,MB_OK or MB_ICONINFORMATION)
End
しかし、大問題なのは実行時間です。
このバグにより、実行時間は4倍ほど多くかかっていたもようです。
全てのロジックを再計測いたしますので、もう少し時間をください。
申し訳ありませんでした。m(_w_)m
quicksort
だいぶ前に投稿したquicksortをソートロジック大会風にしたものです。といっても、関数名を変えて、基準値の取り方と挿入ソートを投稿物から移しただけというシロモノですが。
実行速度の再計測中とのことなので、せっかくだからやってもらおうかと(^^;
昔の実行速度環境プログラムで50万件までは動作確認しましたので動くと思います。ただ、100万件ではバッファの開放か何かでエラーが出ました(きちんと確認していませんが)。
記念すべき返信100通目は次の人にプレゼント(笑
実行速度の再計測中とのことなので、せっかくだからやってもらおうかと(^^;
昔の実行速度環境プログラムで50万件までは動作確認しましたので動くと思います。ただ、100万件ではバッファの開放か何かでエラーが出ました(きちんと確認していませんが)。
[ここをクリックすると内容が表示されます]
コード: 全て選択
'quicksort ソートロジック大会の実行速度比較環境風
Const THRESHOLD = 10 '挿入ソートに切り替える境界値
Const STACKSIZE = 32 'たかだか Long のビット数程度(>log2Nの数であること)
Sub Sort(S As Long, E As Long)
Dim i As Long, j As Long, k As Long
Dim left As Long, right As Long, middle As Long
Dim leftstack[STACKSIZE] As Long
Dim rightstack[STACKSIZE] As Long
Dim x As Long, tmp As Long
left = S
right = E
While 1
If right - left <= THRESHOLD Then
If k = 0 Then Exit While
k = k - 1
left = leftstack[k]
right = rightstack[k]
End If
'基準値の作成(投稿された中央値のもの)
middle = (left + right) \ 2
If lstrcmp(KeyTable[Index[left]],KeyTable[Index[middle]])>0 Then
Swap(Index[left],Index[middle])
EndIf
If lstrcmp(KeyTable[Index[middle]],KeyTable[Index[right]])>0 Then
Swap(Index[middle],Index[right])
If lstrcmp(KeyTable[Index[left]],KeyTable[Index[middle]])>0 Then
Swap(Index[left],Index[middle])
EndIf
EndIf
x = Index[middle] '比較値の保存
i = left
j = right
While 1
While lstrcmp(KeyTable[Index], KeyTable[x]) < 0
i = i + 1
Wend
While lstrcmp(KeyTable[x], KeyTable[Index[j]]) < 0
j = j - 1
Wend
If i >= j Then Exit While
Swap(Index, Index[j])
i = i + 1
j = j - 1
Wend
If i - left > right - j Then
If i - left > THRESHOLD Then
leftstack[k] = left
rightstack[k] = i - 1
k = k + 1
End If
left = j + 1
Else
If right - j > THRESHOLD Then
leftstack[k] = j + 1
rightstack[k] = right
k = k + 1
End If
right = i - 1
End If
Wend
InsertionSort(S, E)
End Sub
Sub InsertionSort(S As Long, E As Long)
For i = S + 1 To E
j = i
While j >= S + 1 And lstrcmp(KeyTable[Index[j]],KeyTable[Index[j-1]])<0
Swap(Index[j], Index[j - 1])
j = j - 1
Wend
Next i
End Sub
記念すべき返信100通目は次の人にプレゼント(笑
記念すべき返信100通目は
申し訳ありません!m(_w_)m
記念すべき返信100通目を取ってしまいました。!!! (しかし、「おくゆかしい」方々の存在も考慮しました(笑)
マティさんのありがたいご指摘により、ソートロジック大会の信憑性もランクアップしたおもいです!m(_w_)m
マティさんへ
ヒープソート実行できました。
ありがとうございます。
こんな難しいロジックでありながら、速度的には少し疑問が残ります。
arさんへ
クイックソートの大会実行速度比較環境移植について
ありがとうございます。
[どなたか!]に対する、返信と受け止めます。
大会実行速度実行時間比較について再計測をいたしました。
高度すぎるため、速度比較から別格の件数比較へと分類をさせていただきました。申し訳ありません。
追伸:1000件と5000件の比較は、もういらないような気がします。
あまりにも皆様のコードが早すぎて、速度のむらの[はんちゅう]のようです。
追伸:皆様へ、私のほうが速い、進言およびご指摘ををお願い致します。
備考:返信回数と閲覧回数はいったい何件まで表示可能なのでしょうか?、どの件数で##とかになるのか一瞬、期待してしまいました。m(_ _)m
記念すべき返信100通目を取ってしまいました。!!! (しかし、「おくゆかしい」方々の存在も考慮しました(笑)
マティさんのありがたいご指摘により、ソートロジック大会の信憑性もランクアップしたおもいです!m(_w_)m
マティさんへ
ヒープソート実行できました。
ありがとうございます。
こんな難しいロジックでありながら、速度的には少し疑問が残ります。
arさんへ
クイックソートの大会実行速度比較環境移植について
ありがとうございます。
[どなたか!]に対する、返信と受け止めます。
大会実行速度実行時間比較について再計測をいたしました。
ここをクリックすると実行速度比較が表示されます。 [ここをクリックすると内容が表示されます]
実行環境 (ActiveBasic Ver.4.10~4.12.01)
(Cpu Pentium4 周波数2.66GHz メモリ256MByte)
文字列ソート
実行速度比較 5桁のランダム数字も5桁のランダム文字もソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 1,000 5,000 10,000 50,000 100,000 記事
arさん ラディックス 0.010 0.030 0.060 0.250 0.551 ラディックス最速
arさん マージ 0.010 0.060 0.120 0.411 0.892 マージ最速
omasu マージ(arさん版) 0.010 0.030 0.070 0.430 0.931
arさん クイック 0.010 0.050 0.110 0.410 0.952 クイック最速
arさん クイック(大会風) 0.020 0.050 0.080 0.491 1.061
omasu クイック(中級編) 0.010 0.040 0.100 0.471 1.072
omasu マージ(非再帰) 0.010 0.050 0.090 0.521 1.122
イグトランスさん クイック 0.010 0.043 0.093 0.572 1.180
マティさん クイック(初級編) 0.010 0.060 0.100 0.551 1.302
omasu クイック(入門編) 0.010 0.040 0.080 0.561 1.322
omasu シェル4(0.8975+0.45) 0.010 0.050 0.140 0.752 1.622 シェル最速
omasu シェル3(0.8975+¥3) 0.010 0.050 0.120 0.891 1.823
マティさん ヒープ 0.010 0.060 0.130 0.851 1.882 ヒープ最速
omasu シェル2(クヌース大大先生) 0.010 0.070 0.130 0.942 2.253
omasu コーム2(挿入法1.4) 0.010 0.070 0.160 1.071 2.443 コ-ム最速
河川屋さん 改シェル法(クヌース大先生) 0.010 0.060 0.141 1.042 2.523
omasu シェル(ノーマル) 0.010 0.060 0.161 1.162 2.724
河川屋さん コム(挿入法) 0.020 0.080 0.200 1.252 2.924
omasu コーム2(バブル1.4) 0.020 0.090 0.200 1.212 2.964
omasu コーム(ノーマル) 0.020 0.090 0.211 1.442 3.074
omasu マージ(非再帰・非ワーク) 0.030 0.411 1.552 37.564 151.137
omasu 単純挿入法(バイナリサーチ) 0.050 0.701 2.624 64.373 258.011 単純挿入法最速
omasu シェル(ノーマル・再帰) 0.140 3.315 13.990 ――――――― ―――――――
omasu 単純挿入法 0.130 3.445 15.222 ――――――― ―――――――
omasu シェーカー(バブル) 0.200 4.967 21.852 ――――――― ――――――― シェーカー最速
omasu 単純選択法 0.230 6.429 28.340 ――――――― ――――――― 単純選択法最速
omasu バブル 0.250 7.280 31.706 ――――――― ――――――― バブル最速
omasu シェル(選択法) 0.340 8.582 36.873 ――――――― ―――――――
トーナメント法 ただいま勉強中です。
100万件以上の文字列ソート
実行速度比較 5桁のランダム数字も5桁のランダム文字もソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 1,000,000 5,000,000 10,000,000 記事
マティさん クイック改4 284.669 1082.085 2682.166 最大件数ソート可能
数値ソート
実行速度比較 5桁のランダム数字をソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 1,000 5,000 10,000 50,000 100,000 記事
河川屋さん (PJ)クイック(改2) 0.080 0.140 0.271 0.801 1.142 クイック最速
河川屋さん (PJ)クイック(改1) 0.020 0.130 0.170 0.732 1.151 クイック最速
河川屋さん (PJ)クイック(ノーマル版) 0.130 0.160 0.210 0.831 1.192 クイック最速
マティさん (PJ)コーム 0.010 0.060 0.120 0.581 1.643 コーム最速
追伸:マティさんの800万件ソートですが、今回の比較環境のバグに謝罪をいたします。申し訳ありませんでした。
皆様のありがたいロジックの速度を正しく提示できなかったことに、深くお詫び申し上げます。
高度すぎるため、速度比較から別格の件数比較へと分類をさせていただきました。申し訳ありません。
追伸:1000件と5000件の比較は、もういらないような気がします。
あまりにも皆様のコードが早すぎて、速度のむらの[はんちゅう]のようです。
追伸:皆様へ、私のほうが速い、進言およびご指摘ををお願い致します。
備考:返信回数と閲覧回数はいったい何件まで表示可能なのでしょうか?、どの件数で##とかになるのか一瞬、期待してしまいました。m(_ _)m
実行管理委員会の能力向上について
お世話になります。
ついにメモリーを増設しました。
増設1GByte、PCを買い換える前に、メモリ増設を!(シャキシャキです。)
実行速度計測に対し、掲示上、1万件からの計測に変更しました。
計測終了を10秒以上までとした場合の時間全てが計測できました。
あまりにも鈍足なロジック(omasu作)やシェル等重複するロジックを整理しました。
しかし、シェルソートが50万件以上から実行できなくなっているため、悩んでいます。(質問版)
マティさんのクイック改4は、arさんのメモリーソートが5百万件のため、
1千万件からとさせていただきました。
しかし、5千万件以上からエラーとなります、悪戦苦闘です。(質問版)
追伸:AB4.12.02のバージョン情報がAB4.12.01?
ついにメモリーを増設しました。
増設1GByte、PCを買い換える前に、メモリ増設を!(シャキシャキです。)
実行速度計測に対し、掲示上、1万件からの計測に変更しました。
計測終了を10秒以上までとした場合の時間全てが計測できました。
あまりにも鈍足なロジック(omasu作)やシェル等重複するロジックを整理しました。
しかし、シェルソートが50万件以上から実行できなくなっているため、悩んでいます。(質問版)
マティさんのクイック改4は、arさんのメモリーソートが5百万件のため、
1千万件からとさせていただきました。
しかし、5千万件以上からエラーとなります、悪戦苦闘です。(質問版)
ここをクリックすると実行速度比較が表示されます。 [ここをクリックすると内容が表示されます]
実行環境 (ActiveBasic Ver.4.10.01~4.12.02)
(Cpu Pentium4 周波数2.66GHz 純正メモリ256MByte 増設メモリ1GByte)
文字列ソート(1万件~5百万件)
実行速度比較 5桁のランダム数字も5桁のランダム文字もソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 10,000 50,000 100,000 500,000 1,000,000 5,000,000 記事
arさん ラディックス 0.060 0.250 0.551 2.955 5.928 30.464 ラディックス最速
arさん マージ 0.120 0.411 0.892 4.446 9.574 54.959 マージ最速
arさん クイック 0.110 0.410 0.952 5.417 11.706 ――――――――― クイック最速
omasu マージ(arさん版) 0.070 0.430 0.931 5.568 11.968 ―――――――――
omasu マージ(非再帰) 0.090 0.521 1.122 6.399 13.679 ―――――――――
arさん クイック(大会風) 0.080 0.491 1.061 6.409 13.930 ―――――――――
omasu クイック(中級編) 0.100 0.471 1.072 6.439 14.090 ―――――――――
omasu クイック(入門編) 0.080 0.561 1.322 7.130 15.733 ―――――――――
イグトランスさん クイック 0.093 0.572 1.180 7.695 16.116 ――――――――― AB4.11.03
マティさん クイック(初級編) 0.100 0.551 1.302 7.360 16.263 ―――――――――
omasu シェル4(0.8975+0.45) 0.140 0.752 1.622 ??????? ――――――――― ――――――――― シェル最速
マティさん ヒープ 0.130 0.851 1.882 12.037 ――――――――― ――――――――― ヒープ最速
omasu コーム2(挿入法1.4) 0.160 1.071 2.443 16.394 ――――――――― ――――――――― コ-ム最速
河川屋さん 改シェル法(クヌース大先生) 0.141 1.042 2.523 ??????? ――――――――― ―――――――――
omasu シェル(ノーマル) 0.161 1.162 2.724 ??????? ――――――――― ―――――――――
河川屋さん コム(挿入法) 0.200 1.252 2.924 18.948 ――――――――― ―――――――――
omasu コーム2(バブル1.4) 0.200 1.212 2.964 21.240 ――――――――― ―――――――――
omasu コーム(ノーマル) 0.211 1.442 3.074 21.150 ――――――――― ―――――――――
omasu 単純挿入法(バイナリサーチ) 2.624 64.373 ――――――― ――――――― ――――――――― ――――――――― 単純挿入法最速
omasu 単純挿入法 15.222 ―――――― ――――――― ――――――― ――――――――― ―――――――――
omasu シェーカー(バブル) 21.852 ―――――― ――――――― ――――――― ――――――――― ――――――――― シェーカー最速
omasu 単純選択法 28.340 ―――――― ――――――― ――――――― ――――――――― ――――――――― 単純選択法最速
omasu バブル 31.706 ―――――― ――――――― ――――――― ――――――――― ――――――――― バブル最速
トーナメント法 ずっと勉強中ですm(_x_)m。
文字列ソート(1千万件以上)
実行速度比較 5桁のランダム数字も5桁のランダム文字もソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 10,000,000 50,000,000 記事
マティさん クイック改4 2682.166 ?????????? 最大件数ソート可能
数値ソート
実行速度比較 5桁のランダム数字をソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 1,000 5,000 10,000 50,000 100,000 記事
河川屋さん (PJ)クイック(改2) 0.080 0.140 0.271 0.801 1.142 クイック最速
河川屋さん (PJ)クイック(改1) 0.020 0.130 0.170 0.732 1.151 クイック最速
河川屋さん (PJ)クイック(ノーマル版) 0.130 0.160 0.210 0.831 1.192 クイック最速
マティさん (PJ)コーム 0.010 0.060 0.120 0.581 1.643 コーム最速
追伸:AB4.12.02のバージョン情報がAB4.12.01?
omasuさんごめんなさい、ファイルサイズと取得する処理を手抜きしていました。
前回投稿したプログラムでは、ファイルサイズが2GBまでしか処理出来ませんでした。
これで、実行可能になると思います。
PS.テストデータを作成するのに9時間もかかってしまいました。
前回投稿したプログラムでは、ファイルサイズが2GBまでしか処理出来ませんでした。
コード: 全て選択
'宣言の修正
' Dim nSize As Long
Dim nSize As Int64, nSizeLow As DWord '修正&追加
'ロジックの修正
' nSize = GetFileSize( hFileLoad, NULL )
nSizeLow = GetFileSize( hFileLoad, VarPtr(nSize)+4 )
nSize = nSize + nSizeLow
クイックソート改4の改良版も載せておきます [ここをクリックすると内容が表示されます]
コード: 全て選択
Declare Function timeGetTime Lib "winmm.dll" () As Long
'#Strict
'===============================================================================
' 0.01 標準関数のみで処理を作成
' 0.04 関数の展開を行う
' 0.05 ロジックの役割を変える
' 0.06 分割処理の書込み方法を変更
' 0.07 書込みバッファーの採用
'===============================================================================
'Const WriteLine=2048
Const WriteLine=4096
'Const xReSort=10240 '
'Const xReSort=20480 '256MB
'Const xReSort=51200 '
'Const xReSort=102400 '
'Const xReSort=153600 '
'Const xReSort=204800 '512MB
'Const xReSort=256000 '
Const xReSort=307200 '
Const LineLength = 158 '一行のバイト数
Const MarBuffer = xReSort * LineLength '4KB倍数にする事
Const WriteBurrer = WriteLine * LineLength '4KB倍数になる最小値
'Dim Dummy(72) As byte
Dim rBuffer(MarBuffer -1) As Byte 'Read Buffer's
Dim wBuffer(255 * WriteBurrer -1) As Byte 'WriteBuffer's '0.07
'LineLengthが255を超えると追加のワークを作成する必要がある
'Dim wBufferAdd(MarBuffer-(255 * WriteBurrer)) As Byte
Dim wBufAdr(255) As Long '0.07
Dim xFile (255) As Byte '0.06対象の有無
Dim xKeys (xReSort) As Byte '0.06対象キー
Dim MasterKey(LineLength) As Byte
Dim SortIndex(xReSort) As BytePtr
Dim SortKey(100)=[1,2,3,4,5,7,8,9,10,11,-1] As Char '列位置指定(-1で終了)
Dim StartTime As Long
Dim EndTime As Long
Dim xInFile As String
Dim xOutFile As String
Dim xWorkFile As String
'
Dim hFileLoad As HFILE
Dim hFileSave As HFILE
Dim nLoad As Long
Dim nSave As Long
' ---------------------------------------------
' 初期値を設定
' ---------------------------------------------
MkDir "c:\tmp"
xInFile = "c:\infile50000000.csv"
' xInFile = "d:\csv\infile8000000.csv"
' xInFile = "d:\csv\infile1000000.csv"
' xInFile = "d:\csv\infile1000.csv"
' xInFile = "d:\csv\infile100.csv"
' xInFile = "d:\csv\infile10.csv"
xOutFile = "OutPut.csv"
xWorkFile = "c:\tmp\sort"
' ---------------------------------------------
' ソート&ファイル書込み
' ---------------------------------------------
StartTime = timeGetTime()
' hFileSave = CreateFile(xOutFile,GENERIC_WRITE,0,ByVal NULL,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,NULL) 'Write
hFileSave = CreateFile(xOutFile,GENERIC_WRITE,0,ByVal NULL,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL + FILE_FLAG_SEQUENTIAL_SCAN,NULL) 'Write
GigaSort( 0, xInFile )
CloseHandle( hFileSave )
EndTime = timeGetTime()
MsgBox 0, Str$( EndTime - StartTime )&"ms"
End
'===============================================================================
' ファイルを用いたソート方法
'===============================================================================
Function GigaSort(xNo As Integer, xFileName As String)As Integer
Dim i As Long
Dim x As Long
Dim z As Long '分割用アドレス
Dim r As BytePtr 'Read
Dim w As BytePtr 'Write
' Dim p As BytePtr 'pointer
'
Dim Index As Integer
Dim wFile As String 'ワークファイル名
' Dim nSize As Long
Dim nSize As Int64, nSizeLow As DWord
Dim nRead As Long
Dim hFile(255) As HFILE '書込みファイルハンドル
'-------------------------------------------------------
' ファイル処理(読込みファイルの作成作業)
'-------------------------------------------------------
If(xNo)Then wFile = xFileName Else wFile = xWorkFile
'
hFileLoad = CreateFile( xFileName, _
GENERIC_READ , _
0, _
ByVal NULL, _
OPEN_EXISTING, _
FILE_ATTRIBUTE_NORMAL + FILE_FLAG_SEQUENTIAL_SCAN, _
NULL) 'Read
' nSize = GetFileSize( hFileLoad, NULL )
nSizeLow = GetFileSize( hFileLoad, VarPtr(nSize)+4 )
nSize = nSize + nSizeLow
'-------------------------------------------------------
' ソート条件確認
'-------------------------------------------------------
Index=SortKey[xNo]-1
If(Index < 0)Then 'ソート不能、全て書き込む
SortOut( nSize )
If(xNo)Then DeleteFile(xFileName)
Exit Function
End If
If(nSize <= MarBuffer)Then 'メモリー内でソートが出来る場合
QuickSortSetup( xNo, nSize )
If(xNo)Then DeleteFile(xFileName)
Exit Function
End If
'-------------------------------------------------------
' 中間ファイルを用いて分割を行う処理
'-------------------------------------------------------
For i=0 To 255: wBufAdr=0: Next
'----------------------------------------
' 中間ファイル作成!
'----------------------------------------
While( nSize > 0 )
If( nSize > MarBuffer )Then nRead=MarBuffer Else nRead=nSize
ReadFile( hFileLoad, rBuffer As BytePtr, nRead, VarPtr(nLoad), ByVal 0)
'--------------------------------------------------
'インデックス作成
'--------------------------------------------------
r=rBuffer As BytePtr
For i=0 To ( nRead \ LineLength ) - 1
x=r[Index]: xKeys=x: xFile[x]=1: r=r+LineLength
Next
'--------------------------------------------------
'ファイル処理
'--------------------------------------------------
w = wBuffer As BytePtr
For x=0 To 255
If( xFile[x] )Then
If(hFile[x] = 0)Then
hFile[x] = CreateFile( wFile + Chr$(x), _
GENERIC_WRITE, 0, ByVal NULL, CREATE_ALWAYS, _
FILE_ATTRIBUTE_NORMAL + FILE_FLAG_SEQUENTIAL_SCAN, _
NULL) 'Write
End If
'
r=rBuffer As BytePtr
z=wBufAdr[x]
For i=0 To ( nRead \ LineLength ) - 1
If( xKeys = x )Then
memcpy((w+z), r, LineLength) '基準k
z = z + LineLength
If(z >= WriteBurrer)Then
WriteFile(hFile[x], w, z, VarPtr(nSave), ByVal 0)
z=0
End If
End If
r=r+LineLength
Next i
wBufAdr[x]=z
End If
w = w + WriteBurrer
Next
nSize = nSize - nRead
Wend
'----------------------------------------
' 中間ファイルは閉じると完成する!
'----------------------------------------
w = wBuffer As BytePtr
For x=0 To 255
If(hFile[x])Then
z=wBufAdr[x]
If(z>0)Then
WriteFile(hFile[x], w, z, VarPtr(nSave), ByVal 0)
End If
CloseHandle( hFile[x] )
End If
w = w + WriteBurrer
Next
CloseHandle( hFileLoad )
'----------------------------------------
' 再度ソートを行う処理を呼び出す
'----------------------------------------
If(xNo)Then DeleteFile(xFileName)
For i=0 To 255
If(hFile)Then GigaSort(xNo+1, wFile + Chr$(i)) '再帰処理
Next
End Function
'-----------------------------------------------------------
' ソート結果の書込み(最後まで絞り切れない場合に実行)
'-----------------------------------------------------------
Sub SortOut(nSize As DWord)
While( nSize > MarBuffer )
ReadFile( hFileLoad, rBuffer As BytePtr, MarBuffer, VarPtr(nLoad), ByVal 0)
WriteFile(hFileSave, rBuffer As BytePtr, MarBuffer, VarPtr(nSave), ByVal 0)
nSize = nSize - MarBuffer
Wend
ReadFile( hFileLoad, rBuffer As BytePtr, nSize, VarPtr(nLoad), ByVal 0)
WriteFile(hFileSave, rBuffer As BytePtr, nSize, VarPtr(nSave), ByVal 0)
CloseHandle( hFileLoad )
End Sub
'===============================================================================
' メモリーを用いたソート
'===============================================================================
Sub QuickSortSetup( xNo As Integer, nSize As DWord )
Dim i As Long
Dim p As BytePtr
Dim nCount As Long
'
ReadFile( hFileLoad, rBuffer As BytePtr, nSize, VarPtr(nLoad), ByVal 0)
CloseHandle( hFileLoad )
nCount = ( nSize \ LineLength ) - 1
' If(nCount<=0)Then Debug:exit function
' If(nCount>=0)Then
p=rBuffer As BytePtr
For i=0 To nCount
SortIndex = p: p=p+LineLength
Next
'
QuickSort(xNo, 0, nCount ) 'ソート処理
'
p=wBuffer As BytePtr
For i=0 To nCount
memcpy(p, SortIndex, LineLength) '基準k
p=p+LineLength
Next
WriteFile(hFileSave, wBuffer, nSize, VarPtr(nSave), ByVal 0)
' End If
End Sub
'----------------------------------------------------------
' クイックソート
'----------------------------------------------------------
Sub QuickSort( xNo As Integer, Kara As Long, Made As Long)
Dim i As Long
Dim j As Long
Dim w As BytePtr
Dim k As BytePtr
'
memcpy(MasterKey As BytePtr, SortIndex[(Kara+Made)\2], LineLength) '基準k
i=Kara : j=Made: k=MasterKey As BytePtr
Do
While KeyCheck( xNo, SortIndex , k ): i=i+1: Wend
While KeyCheck( xNo, k , SortIndex[j] ): j=j-1: Wend
If (i <= j) Then
w = SortIndex: SortIndex = SortIndex[j]: SortIndex[j] = w
i=i+1 : j=j-1
End If
Loop Until (i > j)
If (Kara < j) Then QuickSort(xNo, Kara, j)
If (i < Made) Then QuickSort(xNo, i, Made)
End Sub
'----------------------------------------------------------
' 比較処理( L<R なら -1 )
'----------------------------------------------------------
Function KeyCheck( xNo As Integer, L As BytePtr, R As BytePtr ) As Long
Dim x As Long
Do
x=SortKey[xNo]-1: If( x<0 )Then Exit Function
If( L[x] < R[x] )Then Exit Do
If( L[x] > R[x] )Then Exit Function
xNo = xNo + 1
Loop
KeyCheck = -1
End Function
'===============================================================================
' コード終了
'===============================================================================
PS.テストデータを作成するのに9時間もかかってしまいました。
クイックソート改4(改0.07)について
お世話になります。
マティさん、ありがとうございます。
クイックソート改4(改0.07)実行してみました。
みごと、5千万件(7.7G)の実行ができました。
ついでに一億件(15.4G)も実行しました。(とても「ついで」でなかったのですが m(_w_)m )
メモリ1.25Gでは[Const xReSort=1024000]まで実行できました。
(一億件実行中、ディスク空き容量2G・・きわどい!)
テストデータの作成時間ですが、本当に時間がかかりますね!
1千万件 約 2時間
5千万件 約11時間
1億件 約21時間
(テストデータ作成大会ではありません、皆さんは真似をしないでください。)
でも、1万件くらいのブロック単位でファイルアウトすれば早くなるかも、どなたか!
追伸:シェルソート全て10万件までは動くのですが、50万件から全て実行不可となっています。
タイプはLongですが、その件数で変わるものではないと思いますが、不思議です。
過去のExit Forバージョンでは動きます。ただいま、ロジックを見直し中です。
マティさん、ありがとうございます。
クイックソート改4(改0.07)実行してみました。
みごと、5千万件(7.7G)の実行ができました。
ついでに一億件(15.4G)も実行しました。(とても「ついで」でなかったのですが m(_w_)m )
メモリ1.25Gでは[Const xReSort=1024000]まで実行できました。
(一億件実行中、ディスク空き容量2G・・きわどい!)
テストデータの作成時間ですが、本当に時間がかかりますね!
1千万件 約 2時間
5千万件 約11時間
1億件 約21時間
(テストデータ作成大会ではありません、皆さんは真似をしないでください。)
でも、1万件くらいのブロック単位でファイルアウトすれば早くなるかも、どなたか!
ここをクリックすると実行速度比較が表示されます。 [ここをクリックすると内容が表示されます]
追伸:クイックソート改4の基本構造をご教授願えれば幸いです。実行環境 (ActiveBasic Ver.4.10.01~4.12.02)
(Cpu Pentium4 周波数2.66GHz 純正メモリ256MByte 増設メモリ1GByte)
文字列ソート(1万件~5百万件)
実行速度比較 5桁のランダム数字も5桁のランダム文字もソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 10,000 50,000 100,000 500,000 1,000,000 5,000,000 記事
arさん ラディックス 0.060 0.250 0.551 2.955 5.928 30.464 ラディックス最速
arさん マージ 0.120 0.411 0.892 4.446 9.574 54.959 マージ最速
arさん クイック 0.110 0.410 0.952 5.417 11.706 ――――――――― クイック最速
omasu マージ(arさん版) 0.070 0.430 0.931 5.568 11.968 ―――――――――
omasu マージ(非再帰) 0.090 0.521 1.122 6.399 13.679 ―――――――――
arさん クイック(大会風) 0.080 0.491 1.061 6.409 13.930 ―――――――――
omasu クイック(中級編) 0.100 0.471 1.072 6.439 14.090 ―――――――――
omasu クイック(入門編) 0.080 0.561 1.322 7.130 15.733 ―――――――――
イグトランスさん クイック 0.093 0.572 1.180 7.695 16.116 ――――――――― AB4.11.03
マティさん クイック(初級編) 0.100 0.551 1.302 7.360 16.263 ―――――――――
omasu シェル4(0.8975+0.45) 0.140 0.752 1.622 ??????? ――――――――― ――――――――― シェル最速
マティさん ヒープ 0.130 0.851 1.882 12.037 ――――――――― ――――――――― ヒープ最速
omasu コーム2(挿入法1.4) 0.160 1.071 2.443 16.394 ――――――――― ――――――――― コ-ム最速
河川屋さん 改シェル法(クヌース大先生) 0.141 1.042 2.523 ??????? ――――――――― ―――――――――
omasu シェル(ノーマル) 0.161 1.162 2.724 ??????? ――――――――― ―――――――――
河川屋さん コム(挿入法) 0.200 1.252 2.924 18.948 ――――――――― ―――――――――
omasu コーム2(バブル1.4) 0.200 1.212 2.964 21.240 ――――――――― ―――――――――
omasu コーム(ノーマル) 0.211 1.442 3.074 21.150 ――――――――― ―――――――――
omasu 単純挿入法(バイナリサーチ) 2.624 64.373 ――――――― ――――――― ――――――――― ――――――――― 単純挿入法最速
omasu 単純挿入法 15.222 ―――――― ――――――― ――――――― ――――――――― ―――――――――
omasu シェーカー(バブル) 21.852 ―――――― ――――――― ――――――― ――――――――― ――――――――― シェーカー最速
omasu 単純選択法 28.340 ―――――― ――――――― ――――――― ――――――――― ――――――――― 単純選択法最速
omasu バブル 31.706 ―――――― ――――――― ――――――― ――――――――― ――――――――― バブル最速
トーナメント法 ただいま勉強中です。
文字列ソート(1千万件以上)
実行速度比較 5桁のランダム数字も5桁のランダム文字もソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 10,000,000 50,000,000 100,000,000 記事
マティさん クイック改4(改0.07) 739.253 4015.514 10025.796 Const xReSort=1024000
マティさん クイック改4 2682.166 ―――――――――― ――――――――――― Const xReSort=20480
数値ソート
実行速度比較 5桁のランダム数字をソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 1,000 5,000 10,000 50,000 100,000 記事
河川屋さん (PJ)クイック(改2) 0.080 0.140 0.271 0.801 1.142 クイック最速
河川屋さん (PJ)クイック(改1) 0.020 0.130 0.170 0.732 1.151 クイック最速
河川屋さん (PJ)クイック(ノーマル版) 0.130 0.160 0.210 0.831 1.192 クイック最速
マティさん (PJ)コーム 0.010 0.060 0.120 0.581 1.643 コーム最速
追伸:シェルソート全て10万件までは動くのですが、50万件から全て実行不可となっています。
タイプはLongですが、その件数で変わるものではないと思いますが、不思議です。
過去のExit Forバージョンでは動きます。ただいま、ロジックを見直し中です。
単純挿入法(改)について
お世話になります。
シェルソート50万件以上実行不可について
よくわからないのですが、50万件の実行には
シェルソートは[Const TableSize=700000]70万件の定義が必要と解りました。
100万件を規定値とすれば全てのシェルロジックは実行可能です。
過去にハッシング手法を使ったソートが失敗に終わりましたが、
単純挿入法のロジックで速度更新がありました。
このコードは(数値ソートが早い)を利用したものです。
今回は亜流のロジック投稿で恐縮しております。
あらかじめキーテーブルストック時に本コードを埋め込めば、
クイック(中級編)100万件で4.106秒です。
ロジック速度測定外ですが、利用価値はあると思われます。
シェルソート50万件以上実行不可について
よくわからないのですが、50万件の実行には
シェルソートは[Const TableSize=700000]70万件の定義が必要と解りました。
100万件を規定値とすれば全てのシェルロジックは実行可能です。
過去にハッシング手法を使ったソートが失敗に終わりましたが、
単純挿入法のロジックで速度更新がありました。
このコードは(数値ソートが早い)を利用したものです。
[ここをクリックすると内容が表示されます]
(H18.1.5コードをファンクション化しました。)Work配列はQWordにしてください。
コード: 全て選択
Sub Sort(ByVal S As Long,ByVal E As Long)
For i=S To E
Work=AscMid(KeyTable)
If i>0 Then
j=i
While (j>=S+1) And _
(Work[Index[j]]<Work[Index[j-1]])
Swap(Index[j],Index[j-1])
j=j-1
Wend
EndIf
Next i
End Sub
'
Function AscMid(buf As String) As QWord
AscMid= buf[00]*1000000000
AscMid=AscMid+buf[01]*100000000
AscMid=AscMid+buf[02]*10000000
AscMid=AscMid+buf[03]*1000000
AscMid=AscMid+buf[04]*100000
AscMid=AscMid+buf[06]*10000
AscMid=AscMid+buf[07]*1000
AscMid=AscMid+buf[08]*100
AscMid=AscMid+buf[09]*10
AscMid=AscMid+buf[10]*1
End Function
今回は亜流のロジック投稿で恐縮しております。
あらかじめキーテーブルストック時に本コードを埋め込めば、
クイック(中級編)100万件で4.106秒です。
ロジック速度測定外ですが、利用価値はあると思われます。
ここをクリックすると実行速度比較が表示されます。 [ここをクリックすると内容が表示されます]
(H18.1.5ファンクション化すると少し早くなりました。)実行環境 (ActiveBasic Ver.4.10.01~4.13.00)
(Cpu Pentium4 周波数2.66GHz 純正メモリ256MByte 増設メモリ1GByte)
文字列ソート(1万件~5百万件)
実行速度比較 5桁のランダム数字も5桁のランダム文字もソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 10,000 50,000 100,000 500,000 1,000,000 5,000,000 記事
arさん ラディックス 0.060 0.250 0.551 2.955 5.928 30.464 ラディックス最速
arさん マージ 0.120 0.411 0.892 4.446 9.574 54.959 マージ最速
arさん クイック 0.110 0.410 0.952 5.417 11.706 ――――――――― クイック最速
omasu マージ(arさん版) 0.070 0.430 0.931 5.568 11.968 ―――――――――
omasu マージ(非再帰) 0.090 0.521 1.122 6.399 13.679 ―――――――――
arさん クイック(大会風) 0.080 0.491 1.061 6.409 13.930 ―――――――――
omasu クイック(中級編) 0.100 0.471 1.072 6.439 14.090 ―――――――――
omasu クイック(入門編) 0.080 0.561 1.322 7.130 15.733 ―――――――――
イグトランスさん クイック 0.093 0.572 1.180 7.695 16.116 ――――――――― AB4.11.03
マティさん クイック(初級編) 0.100 0.551 1.302 7.360 16.263 ―――――――――
omasu シェル4(0.8975+0.45) 0.140 0.752 1.622 10.135 ――――――――― ――――――――― シェル最速
マティさん ヒープ 0.130 0.851 1.882 12.037 ――――――――― ――――――――― ヒープ最速
omasu コーム2(挿入法1.4) 0.160 1.071 2.443 16.394 ――――――――― ――――――――― コ-ム最速
河川屋さん コム(挿入法) 0.200 1.252 2.924 18.948 ――――――――― ―――――――――
河川屋さん 改シェル法(クヌース大先生) 0.141 1.042 2.523 19.578 ――――――――― ―――――――――
omasu シェル(ノーマル) 0.161 1.162 2.724 19.649 ――――――――― ―――――――――
omasu コーム(ノーマル) 0.211 1.442 3.074 21.150 ――――――――― ―――――――――
omasu 単純挿入法(バイナリサーチ) 2.624 64.373 ――――――― ――――――― ――――――――― ――――――――― 単純挿入法最速
omasu 単純挿入法(キー数値化) 4.266 111.681 ――――――― ――――――― ――――――――― ―――――――――
omasu 単純挿入法 15.222 ――――――― ――――――― ――――――― ――――――――― ―――――――――
omasu シェーカー(バブル) 21.852 ――――――― ――――――― ――――――― ――――――――― ――――――――― シェーカー最速
omasu 単純選択法 28.340 ――――――― ――――――― ――――――― ――――――――― ――――――――― 単純選択法最速
omasu バブル 31.706 ――――――― ――――――― ――――――― ――――――――― ――――――――― バブル最速
トーナメント法 ただいま勉強中です。
文字列ソート(1千万件以上)
実行速度比較 5桁のランダム数字も5桁のランダム文字もソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 10,000,000 50,000,000 100,000,000 記事
マティさん クイック改4(改0.07) 739.253 4015.514 10025.796 Const xReSort=1024000
マティさん クイック改4 2682.166 ―――――――――― ――――――――――― Const xReSort=20480
数値ソート
実行速度比較 5桁のランダム数字をソート可能なロジック キー列(1列目と2列目を連結) データ列数(26列)
作成者 ソート名称 1,000 5,000 10,000 50,000 100,000 記事
河川屋さん (PJ)クイック(改2) 0.080 0.140 0.271 0.801 1.142 クイック最速
河川屋さん (PJ)クイック(改1) 0.020 0.130 0.170 0.732 1.151 クイック最速
河川屋さん (PJ)クイック(ノーマル版) 0.130 0.160 0.210 0.831 1.192 クイック最速
マティさん (PJ)コーム 0.010 0.060 0.120 0.581 1.643 コーム最速