先日キャプチャ数が動的に変化する正規表現の具体例の記事をあげたところ、@scivola様より丁寧にアドバイスいただき、リファクタリングを行いました。
アルファベットとハイフンから構成される文字列を、ハイフンで区切って単語部分についてcapitalizeする
これまでのコード(splitを使用)
rubypractice.rb
def word_capitalize_split(str) # str = "ruby-php-Python-COBOL-JavaScript-javA"
nstr = []
result_split = ""
nstr = str.split(/-/) # ハイフンで分割し配列に格納
nstr.each do |word|
result_split << word.capitalize + "-" # 単語をCapitalizeしハイフンと一緒に文字列に入れる
end
return result_split.chop # "Ruby-Php-Python-Cobol-Javascript-Java"
end
リファクタリング後(@scivola様を参考)
rubypractice.rb
def word_capitalize_split(str) # str = "ruby-php-Python-COBOL-JavaScript-javA"
str.split(/-/).map(&:capitalize).join("-") # "Ruby-Php-Python-Cobol-Javascript-Java"
end
一行で済ませることができました。
やることの考え方はほぼ一緒ですが、mapやjoinを有効活用すると圧縮できました。すごい。
これまでのコード(正規表現を使用)
rubypractice.rb
def word_capitalize_regexp(str) # str = "ruby-php-Python-COBOL-JavaScript-javA"
count = 0
str.each_char do |n| # 単語の中のハイフンの数を数える
if n == "-"
count += 1
end
end
if count > 0
separator = "(.+)"
for i in 1..count
separator << "-(.+)" #ハイフンの数だけセパレーターに追加する
end
Regexp.new(separator) =~ str # ハイフン区切りで単語をキャプチャ
result = $1.capitalize # 一つ目のキャプチャした単語をCapitalize
# ex.1 ハマったところここから
for i in 2..count + 1
result << "-" + eval('$'+i.to_s).capitalize # 二つ目以降のキャプチャした単語をCapitalize
end
# ex.1 ここまで
return result # "Ruby-Php-Python-Cobol-Javascript-Java"
else
return str.capitalize
end
end
リファクタリング後(@scivola様のアドバイスより組み直し)
rubypractice.rb
def word_capitalize_regexp(str) # str = "ruby-php-Python-COBOL-JavaScript-javA"
Regexp.new(Array.new(str.count("-") + 1){"(.+)"}.join("-")) =~ str
return $~.captures.map(&:capitalize).join("-") # "Ruby-Php-Python-Cobol-Javascript-Java"
end
カウントしたり正規表現用の文字列を作ったりするところが全て一行で収まりました。
String#countとかあったんですね・・・勉強になります。
gsubを使ってリファクタリング(@bogo様を参考)
rubypractice.rb
def word_capitalize_gsub(str) # str = "ruby-php-Python-COBOL-JavaScript-javA"
str.gsub(/([A-Za-z]+)/){ $1.capitalize } # "Ruby-Php-Python-Cobol-Javascript-Java"
end
gsubでもできるというコメントをQrunchで@bogo様からいただきました。
gsubってブロック変数も使えるんですね、もっと勉強しときます。
# まとめ
工夫することにより、21行かけて書いたコードも2行に抑えることが可能という知見を得ました。
処理速度がかなり変わるはずなので、今後は徐々にコードの質にも気をつけていこうと思います。
コメントくださった方々本当にありがとうございました!