文字列の長さを数える関数は、どの言語にもあります。ところが「👍」を渡すと、答えは 1・2・4 の3通りに割れました。10言語中7言語が、1 と答えませんでした。
何をしたか
CODE Polyglot の入門 第4回 は、文字列の文字数とバイト数(UTF-8)を出すプログラムです。この回では、Unicode の文字(コードポイント)の数を「文字数」の正解にしています。
JavaScript ならこう書きます。
console.log(`文字数: ${s.length}`);
各言語のいちばん普通の書き方で、毎朝の検証と同じ Linux の環境で動かした結果です。
| 入力 | 正解 | Python len・Ruby length | Swift count | JavaScript length・Java length()・Kotlin length・C# Length | Go len・PHP strlen・Rust len() |
|---|---|---|---|---|---|
abc | 3 | 3 | 3 | 3 | 3 |
あいう | 3 | 3 | 3 | 3 | 9 |
𠮷野家 | 3 | 3 | 3 | 4 | 10 |
👍 | 1 | 1 | 1 | 2 | 4 |
家族👨👩👧 | 7 | 7 | 3 | 10 | 24 |
6件のうち正解だった数は、Python・Ruby が6件中6件、Swift が6件中5件、JavaScript・Java・Kotlin・C# が6件中3件、Go・PHP・Rust が6件中1件でした。
数えているものが4通りある
- バイト(Go・PHP・Rust): UTF-8 に直したときの長さ。ひらがなは1文字3バイト、絵文字は4バイト。英字だけのテストでは正しく見える
- UTF-16 の単位(JavaScript・Java・Kotlin・C#): ふだん使う文字は1つ。ただし「𠮷」や絵文字は2つと数える。日本語のテストでも、ひらがなと常用漢字だけなら気づけない
- Unicode の文字(Python・Ruby): 「👍」も「𠮷」も1つ。家族の絵文字は、人の絵文字3つと、つなぐ記号2つの合計5つと数える
- 見た目の1文字(Swift): 家族の絵文字も1つ。だから
家族👨👩👧は3になる
Swift の答えは、この回の正解とは違いますが、画面に見える文字の数としては自然です。どれが正しいかは、何のために数えるのかで決まります。データベースの列の長さならバイトか文字、入力欄の「あと何文字」なら見た目の1文字が近いでしょう。
どう直したか
この回の正解(Unicode の文字の数)に合わせるには、次のように書きます。
// Go の len はバイト数を数える。文字(rune)の数は utf8.RuneCountInString で数える
fmt.Printf("文字数: %d\n", utf8.RuneCountInString(s))
// length は UTF-16 の単位を数える(「𠮷」は 2)。[...s] で1文字ずつに分けてから数える
console.log(`文字数: ${[...s].length}`);
// length() は UTF-16 の単位を数えるので「𠮷」や絵文字が 2 になる。codePointCount で Unicode の文字を数える
System.out.println("文字数: " + s.codePointCount(0, s.length()));
// Length は UTF-16 の単位を数えるので「𠮷」や絵文字が 2 になる。EnumerateRunes で Unicode の文字を数える
Console.WriteLine($"文字数: {s.EnumerateRunes().Count()}");
// len() は UTF-8 のバイト数を返す。Unicode の文字の数は chars().count() で数える
println!("文字数: {}", s.chars().count());
// count は見た目の1文字(家族の絵文字は 1)を数える。unicodeScalars.count で Unicode の文字を数える
print("文字数: \(s.unicodeScalars.count)")
直した版は、10言語とも6件中6件が正解になりました。
まとめ
- 「👍」の文字数は、10言語で 1・2・4 に割れた。10言語中7言語が 1 と答えなかった
- 長さの関数が数えるものは、バイト・UTF-16 の単位・Unicode の文字・見た目の1文字の4通り
- 英字とひらがなだけのテストでは、JavaScript・Java・Kotlin・C#・Swift の間違いに気づけない。テストには
𠮷と絵文字を入れる - 「文字数」は、何のために数えるのかを先に決める
- 10言語の全プログラムは 入門 第4回 にあります
連載「その書き方、本当に通る?」(全12回)
- 第1回:「2026-02-30」を渡したら、PHP と JavaScript だけが黙って3月2日にした
- 第2回:JavaScript で「月の最終日」を出したら、日本では毎回1日前になった
- 第3回:C# の Normalize(FormKC) が、Docker の中では何もしなかった
- 第4回:辞書の「取り出す順番」を10言語で20回ずつ試したら、5通りの性格に分かれた
- 第5回:「+5」を整数に直したら、10言語すべてが黙って 5 にした
- 第6回:メールアドレスの正規表現の「$」が、最後の改行を通した
- 第7回:「東京,大阪,」を split したら、Java・Ruby・Swift は最後の空の項目を捨てた
- 第8回:Excel の「CSV UTF-8」を読ませたら、10言語すべてが見出しの行を見失った
- 第9回:2.675 を小数第2位までにしたら、10言語中4言語が 2.67、Swift はそのまま 2.675 と答えた
- 第10回:「👍」の文字数を数えたら、10言語で 1・2・4 の3通りに割れた(この記事)
- 第11回:「こんにちは世界」を5文字で切ったら、Go と PHP は文字化けし、Rust は止まった
- 第12回:「1234567」が郵便番号の確認を通った。\d は Python・C#・Swift で全角の数字に合う
Analyzegear


