2016-04-11 4 views
0

大きなファイルセット(約2Gb)があります。私はそれをロードしようとすると (のは、その正確と仮定しましょう):それはwsfullエラーをバック与えkdb +(Q)で大きなバイナリファイルをロードする

ctq_table:flip `QTIM`BID`OFR`QSEQ`BIDSIZE`QFRSIZ`OFRSIZ`MODE`EX`MMID!("ijjiiihcs";4 8 8 4 4 4 2 1 4) 1: `:/q/data/Q200405A.BIN 

。 Kdb +は私が知っている限り、そのようなタスクに使用されることを意図していました。

メモリが足りなくても大きなファイルを処理する方法はありますか(ディスクが遅い場合でもディスクを保持するなど)。

+0

32ビットkdb +を使用していますか? –

+0

はい。それはここで利用可能な唯一のバージョンです:https://kx.com/software-download.php –

+0

この場合、私は恐れています。 32ビットプロセスが自然に制限されているため、4GB以上は処理できません(実際にはWindowsではわずか2GBです)。そのデータセットのサイズはおそらくその制限を超えます。 –

答えて

3

コメントに記載されているように(そして質問のトピックに戻って)、大きなバイナリファイルをチャンクで読み込んで一度に1つずつディスクに書き込むことができます。これにより、追加のディスクI/O操作のためにメモリ使用量が減少しますが、処理速度が低下します。

一般に、チャンクは不完全なメッセージでチャンクを終了させる可能性があるため(チャンクポイントが任意でメッセージが可変幅の場合)、バイトストリームの場合は扱いにくいことがありますが、チャンクエンドポイントの計算が容易になります。

どちらの方法でも、オーバー(/)を使用してループし、最後の既知の(良好な)インデックスを追跡し、次のチャンクを読み取るときにそのインデックスから開始すると便利です。一般的な考え方(テストされていない)は、次のようなものになります

file:`:/q/data/Q200405A.BIN; 
chunkrows:10000; /number of rows to process in each chunk 
columns:`QTIM`BID`OFR`QSEQ`QFRSIZ`OFRSIZ`MODE`EX`MMID; 
types:"ijjiiihcs"; 
widths:4 8 8 4 4 4 2 1 4; 
{ 
    data:flip columns!(types;widths)1:(file;x;chunkrows*sum widths); 
    upsertToDisk[data];  /write a function to upsert to disk (partitioned or splayed) 
    x+chunkrows*sum widths  /return the rolling index of the starting point for the next chunk 
    }/[hcount[file]>;0] 

これは、最後の良好なインデックスがファイルの最後に達するまで続きます。メモリの制約に応じてチャンクローのサイズを調整することができます。

最終的に、無料の32ビット版で大規模データを扱おうとしている場合は、何をするにしても頭痛があります。

関連する問題