Techioz Blog

文字列から絵文字を削除するにはどうすればよいですか

概要

私の問題は、正規表現を使用して文字列から絵文字を削除するが、文字列から CJK (中国語、日本語、韓国語) 文字を削除することはできません。この正規表現を使用してみました。

REGEX = /[^\u1F600-\u1F6FF\s]/i

この正規表現は、中国語、日本語、韓国語の文字が必要な場合にそれらの文字も検出することを除いて、正常に機能します。この問題を解決する方法はありますか?

解決策

Karol S はすでに解決策を提供していますが、その理由は明らかではないかもしれません。

「F600」は実際には「F60」の後に「0」が続くものです。

"\u1F60"    # => "ὠ"
"\u1F600"   # => "ὠ0"

FFFF より上のコード ポイントには中括弧を使用する必要があります。

"\u{1F600}" #=> "😀"

したがって、文字クラス [F600-F6FF] は [F60 0-F6F F] として解釈されます。 「F60」、範囲「0」..「F6F」および「F」に一致します。

中括弧を使用すると問題が解決されます。

/[\u{1F600}-\u{1F6FF}]/

これは、次の Unicode ブロックの (絵文字) 文字と一致します。

unpack、pack、 between? も使用できます。同様の結果が得られます。これは、正規表現で Unicode をサポートしていない Ruby 1.8.7 でも機能します。

s = 'Hi!😀'
#=> "Hi!\360\237\230\200"

s.unpack('U*').reject{ |e| e.between?(0x1F600, 0x1F6FF) }.pack('U*')
#=> "Hi!" 

Rubular の例について – 絵文字は単一の文字です。

"😀".length  #=> 1
"😀".chars   #=> ["😀"]

一方、顔文字は複数の文字の組み合わせです。

"^_^".length #=> 3
"^_^".chars  #=> ["^", "_", "^"]

これらを一致させることは、まったく異なるタスクです (別の質問で尋ねる必要があります)。