ASCIIじゃないアルファベットを取り扱う(正規表現、upcase/downcase)

http://ecole-beaumarchais.fr/IMG/jpg/accents.jpg
ツールドフランスが終わって「ああ夏が終わった」とぼんやりしている[twitter:@riocampos]です。

ASCII以外のアルファベットの「\w」

ツール向けに参加選手情報をリプする[twitter:@tdfmembers]というアカウントを運用(ただし途中で停止)していました。
そうすると、英語圏以外の選手の表記はアルファベット26文字で済まないことに気付きます。é や â などのダイアクリティカルマークが付くアルファベットを用いて表記していることがあるのです。

となると、困るのが、上記アカウントにリプされた内容から名前表現を切り出すときに、名前を表す正規表現が/[\w\s-]+/で済まない点です。
結論から書くと

/[\p{Latin}\s-]+/

と書くのですよね。
んじゃ\p{Latin}って何だ、と言うことになります。\p{なんたら}という表記でUnicodeのある文字集合を示すらしいです。「なんたら」のリストは

http://www.geocities.jp/kosako3/oniguruma/doc/RE.ja.txt

  • Ruby 2.0以上(Onigumo)

https://raw.githubusercontent.com/k-takata/Onigmo/master/doc/UnicodeProps.txt
に載っています。

さらなる詳細については省きます(いずれ書きたいのですが)。詳しいサイトへのリンクだけ張っておきます。

るりまの正規表現も張っておきます。(なお、リンクはRuby 1.9.3のものです。1.9.3 だとエンジンが Oniguruma なのに、説明が 2.0 以降で使われている Onigumo なのが不満です)。

あと、本家の「なんたら」リスト。
http://www.unicode.org/Public/UNIDATA/PropList.txt

ASCII以外のアルファベットの「String#upcase / String#downcase」

残念ながら upcase/downcase メソッドはアルファベット26文字にしか利きません。

"é".upcase
#=> "é" #"É"を返してほしいのに…

探すと、 Unicode で upcase/downcase などを扱うためのgemがありました。

Unicode Utils - Unicode algorithms for Ruby 1.9

UnicodeUtils implements Unicode algorithms for case conversion, normalization, text segmentation and more in pure Ruby code.

ひとまずややこしいことは置いておきます。いまは upcase/downcase だけ扱うことにします。
試しに上記の é を É に出来るか確認します。

require "unicode_utils/upcase"
UnicodeUtils.upcase("é")
#=> "É"

できましたね^^。

マニュアルの該当部分を引用しておきます。

Method: UnicodeUtils.upcase

Perform a full case-conversion of str to uppercase according to the Unicode standard.
Examples:

require "unicode_utils/upcase"
UnicodeUtils.upcase("weiß") => "WEISS"
UnicodeUtils.upcase("i", :en) => "I"
UnicodeUtils.upcase("i", :tr) => "İ"

Method: UnicodeUtils.downcase

Perform a full case-conversion of str to lowercase according to the Unicode standard.
Examples:

require "unicode_utils/downcase"
UnicodeUtils.downcase("ᾈ") => "ᾀ"
UnicodeUtils.downcase("aBI\u{307}", :tr) => "abi"

このgemがその他にどのようなことが出来るかというと、以下のような感じです。

Module: UnicodeUtils

UnicodeUtils.upcase full conversion to uppercase
UnicodeUtils.downcase full conversion to lowercase
UnicodeUtils.titlecase full conversion to titlecase
UnicodeUtils.casefold case folding (case insensitive string comparison)
UnicodeUtils.nfd Normalization Form D
UnicodeUtils.nfc Normalization Form C
UnicodeUtils.nfkd Normalization Form KD
UnicodeUtils.nfkc Normalization Form KC
UnicodeUtils.each_grapheme grapheme boundaries
UnicodeUtils.each_word word boundaries
UnicodeUtils.char_name character names
UnicodeUtils.grep find code points by character name

細かくはお調べくださいませ(人任せでスミマセン)。