ちょっと気になって、他言語、と言っても Java と C# におけるサロゲートペアの取扱いを調べてみた。結論は Java も C# も unicode の 1文字を 16bit で実現しており、サロゲートペアのために特別な API を用意するものの、プログラマーにその特別な処理をお願いしている。ちなみに、Google で「Java サロゲートペア」とか「C# サロゲートペア」とググってみてほしい。それなりの記事がいっぱい出てくる。

Java 言語仕様の正式な記述は、「プログラミング言語 Java」(ケン・アーノルド、ジェームズ・ゴスリング、デビッド・ホームズ)ではなかろうか。その第4版 pp.141 とpp.167 以下に unicode に関する記述がある。ちょっと長くなるが、以下に引用してみる。

まずは、pp.141。ここは Java プログラムコードにおけるトークンや文字セットについての記事だ。
プログラム言語 Java は、Unicode の 16 ビットエンコーディングでかかれます。Unicode 標準は、最初は 16 ビット文字セットをサポートしていましたが、最大値が 0x10ffff を持つ 21 ビット文字まで可能なように拡張されました。値が 0x00ffff より大きい文字は、補助(supplementary) 文字と呼ばれます。特定の 21 ビット値は、コードポイント(code point) と呼ばれます。すべての文字を 16 ビット値で表現可能とするために、UTF-16 と呼ばれるエンコーディング形式を Unicode は定義しています。そして、プログラム言語 Java は、UTF-16 でテキストを表現しています。UTF-16 では、0x0000 と 0xffff 間の値は、直接 Unicode 文字に対応します。補助文字は、2個一組の 16 ビット値でエンコードされます。その組の最初の値は上記代理 (high-surrogates) 範囲に割り当てられ、2番めの値は下位代理 (low-surrogates) 範囲に割り当てられます。
つまり、Java コード中にサロゲートペアの文字を書くことができる?ホントかな?

そして、pp.168 ではいかに Java がマルチ言語を意識しているのか、素晴らしい記述が続きます。ところが、char型はあくまでも 16bit なので、サロゲートペアについては特別な処置が必要になる。
補助文字は一組の char 値としてエンコードする必要があるので、char 配列、文字列、CharSequence を実装した型のどれであろうと、文字のシーケンスを取り扱うことは複雑です。
簡単にいえば、文字列があったとして、その i 番目の文字を取り出しても、もちろんそれがサロゲートペアでなければ、何の問題もないが、ひょっとしてそれがサロゲートペアの上位あるいは下位である可能性もあるということなのだ。そして、文字列の長さ=unicode 文字の数 ではないのだ。IBM の詳細なサロゲートペアに関する検討の記事を参照されたい。

このことは、基本的に C# においても同様だ。このページを見てほしい。

さてそこで、sbcl だ。以前紹介した「サロゲートペア - 闘うITエンジニアの覚え書き」にあるサロゲートペアの漢字を集めて、1行にまとめたファイルを作ってみた。このファイルは、Debian 上の cat で見ても more で見ても正しく漢字を見ることができる。(これはXPでは正しく見れません。)
seiji@agent:~$ more SurrogatePairs3
𠀋𡈽𡌛𡑮𡢽𠮟𡚴𡸴𣇄𣗄𣜿𣝣𣳾𤟱𥒎𥔎𥝱𥧄𥶡𦫿𦹀𧃴𧚄𨉷𨏍𪆐𠂉𠂢𠂤𠆢𠈓𠌫𠎁𠍱𠏹𠑊𠔉𠗖𠘨𠝏
𠠇𠠺𠢹𠥼𠦝𠫓𠬝𠵅𠷡𠺕𠹭𠹤𠽟𡈁𡉕𡉻𡉴𡋤𡋗𡋽𡌶𡍄𡏄𡑭𡗗𦰩𡙇𡜆𡝂𡧃𡱖𡴭𡵅𡵸𡵢𡶡𡶜𡶒𡶷𡷠
𡸳𡼞𡽶𡿺𢅻𢌞𢎭𢛳𢡛𢢫𢦏𢪸𢭏𢭐𢭆𢰝𢮦𢰤𢷡𣇃𣇵𣆶𣍲𣏓𣏒𣏐𣏤𣏕𣏚𣏟𣑊𣑑𣑋𣑥𣓤𣕚𣖔𣘹𣙇𣘸
𣘺𣜜𣜌𣝤𣟿𣟧𣠤𣠽𣪘𣱿𣴀𣵀𣷺𣷹𣷓𣽾𤂖𤄃𤇆𤇾𤎼𤘩𤚥𤢖𤩍𤭖𤭯𤰖𤴔𤸎𤸷𤹪𤺋𥁊𥁕𥄢𥆩𥇥𥇍𥈞
𥉌𥐮𥓙𥖧𥞩𥞴𥧔𥫤𥫣𥫱𥮲𥱋𥱤𥸮𥹖𥹥𥹢𥻘𥻂𥻨𥼣𥽜𥿠𥿔𦀌𥿻𦀗𦁠𦃭𦉰𦊆𦍌𣴎𦐂𦙾𦚰𦜝𦣝𦣪𦥑
𦥯𦧝𦨞𦩘𦪌𦪷𦱳𦳝𦹥𦾔𦿸𦿶𦿷𧄍𧄹𧏛𧏚𧏾𧐐𧑉𧘕𧘔𧘱𧚓𧜎𧜣𧝒𧦅𧪄𧮳𧮾𧯇𧲸𧶠𧸐𧾷𨂊𨂻𨊂𨋳
𨐌𨑕𨕫𨗈𨗉𨛗𨛺𨥉𨥆𨥫𨦇𨦈𨦺𨦻𨨞𨨩𨩱𨩃𨪙𨫍𨫤𨫝𨯁𨯯𨴐𨵱𨷻𨸟𨸶𨺉𨻫𨼲𨿸𩊠𩊱𩒐𩗏𩙿𩛰𩜙
𩝐𩣆𩩲𩷛𩸽𩸕𩺊𩹉𩻄𩻩𩻛𩿎𪀯𪀚𪃹𪂂𢈘𪎌𪐷𪗱𪘂𪘚𪚲

これを次のように sbcl で読み込み端末に表示してみた。(これもXPではだめです。)
* (with-open-file (stream "SurrogatePairs3")
    (let ((sp (read-line stream)))
      (format t "~D~%" (length sp))
      (loop for i from 0 to (1- (length sp))
        do (format t "U+~X ~:C ~W~%" (char-code (char sp i)) (char sp i) (char sp i)))))
303
U+2000B 𠀋 #\U0002000B
U+2123D 𡈽 #\U0002123D
U+2131B 𡌛 #\U0002131B
U+2146E 𡑮 #\U0002146E
U+218BD 𡢽 #\U000218BD
U+20B9F 𠮟 #\U00020B9F
U+216B4 𡚴 #\U000216B4
U+21E34 𡸴 #\U00021E34
U+231C4 𣇄 #\U000231C4
U+235C4 𣗄 #\U000235C4
  ・・・

素晴らしいではないか。確かにこのファイルに含まれるサロゲートペアの文字数は 303 だった。この分なら安心して sbcl で日本語処理を考えることができる。ちなみに、Allegro CL ではこうはいかない。