データファイルとして以下のものを用意する。
area.dat
鶴岡市 141479 67147 74332 酒田市 116234 55213 61021 三川町 7953 3841 4112 遊佐町 16685 7846 8839 庄内町 24304 11552 12752
左から順に、市町村名、総面積、農用地面積、森林面積である。 これを読み込んで実行すると、以下のようになる
% ./ranking.rb データファイルを指定して下さい。 実行例: % ./ranking.rb datafile.dat 総面積順に出力 % ./ranking.rb -a datafile.dat 農用地面積順に出力 % ./ranking.rb -f datafile.dat 森林面積順に出力 % ./ranking.rb area.dat --地区---------総面積-------農用地-------森林--- 鶴岡市 141479 67147 74332 酒田市 116234 55213 61021 庄内町 24304 11552 12752 遊佐町 16685 7846 8839 三川町 7953 3841 4112 ./ranking.rb -a area.dat --地区---------総面積-------農用地-------森林--- 鶴岡市 141479 67147 74332 酒田市 116234 55213 61021 庄内町 24304 11552 12752 遊佐町 16685 7846 8839 三川町 7953 3841 4112 ./ranking.rb -f area.dat --地区---------総面積-------農用地-------森林--- 鶴岡市 141479 67147 74332 酒田市 116234 55213 61021 庄内町 24304 11552 12752 遊佐町 16685 7846 8839 三川町 7953 3841 4112
地区名と、その面積を読み取る部分では、配列変数
area
を用意して、
area = Array.new area << {"place" => 地区名, "total" => 総面積値, "farm" => 農用地面積値, "forest"=> 森林面積値}
という風に代入を行なうとよい。 並べ替える部分は以下のようになるだろう。
for i in area.sort_by{|x| x[比較したいキー]}.reverse …… end
実行例では -a
や -f
でソート基準を
変更するようになっている。プログラムの引数にハイフンで始まる文字を
指定して動きを変えることはよく利用される。この場合 -a
や
-f
をオプションという。ARGV
配列を
先頭から調べて行き,あらかじめ決めたオプションに一致したら動きを変えるよ
うにする。完成形プログラムの前半は以下のようになる。
if ARGV[0] == nil STDERR.print "データファイルを指定して下さい。 実行例: % ./ranking.rb datafile.dat 総面積順に出力 % ./ranking.rb -a datafile.dat 農用地面積順に出力 % ./ranking.rb -f datafile.dat 森林面積順に出力 " exit 1 end sortby = "total" # デフォルトは総面積でソート while /^-/ =~ ARGV[0] # ハイフンで始まる間繰り返す if ARGV[0] == "-a" (ソート規準を農用地にする) elsif ARGV[0] == "-f" (ソート規準を森林にする) else break end ARGV.shift end area = Array.new : : (以下省略)