Quantcast
Channel: つねづね思ふこと 〜 ゲームやアニメの紹介を中心 に、あと気がついたときにプログラムネタも書いてます
Viewing all articles
Browse latest Browse all 153

連想配列(ハッシュ)はやはり使える!

$
0
0

この間、退職したスタッフが以前組んだサーバープログラムを改善する事になった。

メインプログラムが生成する百万行クラスのログファイルの中から、特定の文字列を抽出し、その文字列を一意に配列へ格納し(重複)、そこから格納した各配列へ特定の処理を行うシェルスクリプトーなのだが、今や何日たってもこのプログラムが終わらないため見てみることになったのだ。

なるほど...

1. 定期処理(cron)で起動するにもかかわらず、起動直後にプロセスチェックして2重起動防止機構を入れていない。おかげでこのクソ重いプログラムが多重で起動していた。

2. ループ処理にsleep処理を入れていない。おかげで別スレッドで稼動中のメイン処理が必要なCPUリソースを奪っていた。

3. 一意の変数とするための処理にfor〜if文からなる全検索を行うアルゴリズムを使用していた。

どれもあれだが、この中では3番が一番ひどすぎる。
これは連想配列を使えばめっちゃめちゃ高速化しますぜ!

具体的には前のソースだと確かこんなかんじだった。
(言語は細かいところを思い出すのが面倒なので、俺言語です。シェルスクリプトじゃないよ。イメージで捉えてください)

for $i = 0 to count($ログから抜き出した一意候補の配列); do
  $check = 0
  for $j = 0 to count($確定した一意の配列); do
     if $ログから抜き出した一意候補の配列[$i] == $確定した一意の配列[$j] then
      $check = 1
      break
    end if
  done
  if $check == 1 then
    continue
  end if
  $確定した一意の配列[] = $ログから抜き出した一意候補の配列[$i]
done

これでは、ループし過ぎで時間がかかりすぎるため、こんな感じにしたと言うのが今回の話です。

for $i in $ログから抜き出した一意候補の配列; do
  $確定した一意の連想配列[$i] = 1
  usleep 1000
done

直してみたところーusleepを追加しても処理がたった3分程度で完了してワロタ。
やっぱり大量データから検索する場合は、連想配列を忘れちゃいかんね!

入門UNIXシェルプログラミング―シェルの基礎から学ぶUNIXの世界
ブルース ブリン
ソフトバンククリエイティブ
売り上げランキング: 4,023

Viewing all articles
Browse latest Browse all 153

Trending Articles