mots quotidiens.
Daichi Mochihashi (持橋大地) daichi <at> ism.ac.jp by hns, version 2.10-pl1.

先月 2024年05月 来月
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31

2013年09月17日(火) [n年日記]

#1 NL213

 甲府城からの景色。
9/12-13と, 甲府の山梨大学で行われた第213回NL研に行って発表してきました。 (プログラム)。
二日目は発表数が少ないので, 皆来ないのではないかと思っていましたが, 一日目よりむしろ多い聴衆で安心しました。 論文のページに 発表スライド を置いておきます。

発表はどれも面白く, 質疑応答の時間に自分の発表に限らず色々な視点からの意見が 聞けて, 今回も有益でした。今回は松本先生(2日間通して奈良から来られていた)が 学生に発表を促したりしたとのことですが, やはり国際会議でただ発表するだけでなく, こうして直接意見を聞ける場は当たり前ですが, 貴重だと感じます。
一日目の夜は皆さんはフランス料理を食べに行ったりしたらしいですが, 僕はホテルで 準備。それでも最終日はほうとうを食べに行ったりもして, 色々な方と話ができました。

甲府は噂に聞くように, 石の上で釜焼きになっているようなすさまじい暑さでしたが, 丹下健三の代表作の一つである山梨県立文化会館に行ってみたりと, 色々と 楽しめました。
ちなみに甲府駅の北側, 山梨県立文化会館の隣にある, 参加者がかっこいいと言って いたぎざぎざの屋根の建物は山梨県立図書館で, 「新建築」2013年1月号に紹介が 載っているようです (こちら)。 実は2日後の連休にプライベートでまた甲府に行ったので中に入ってみましたが, 建築も中身も本当に素晴らしい図書館でした。 山梨県建築文化賞をとっているとのことで, 流石だなと思います。


2008年09月17日(水) [n年日記]

#1 wchar_t in C++

C++で wstring を使って2バイト文字と1バイト文字を統一的に扱うには, mbstowcs(3) を使って const char * から wchar_t * に変換して, wstring に 格納するのが普通なのだと思う。
さらに iconv(3) で明示的にコード変換をする手もあるが, そこはロケールにお任せ することにして, wstring には EUC がそのまま入っているのだと思っていた。
..ところが, wchar_t「あ」の中身を表示してみると, A4A2ではなく, 42 30という 謎のコードが。泉谷君に相談して二人で調べてみると, どうも wchar_t の中身は いつの間にかUTF-16になっているらしい。(!) 検索してもそんな話は全然ないし, mbstowcs(3) の中にも書いていないのですが, ロケールは入力コードを指定するために使われるのであって, 内部的には変換されて UTF-16で持っていることがわかった。
手元の環境では sizeof(wchar_t) = 4 だが, Unicodeのテーブル を見ると「あ」= 0x3042 で, リトルエンディアンなので「あ」の中身は
42 30 0 0
となっている模様。 正統的には, ロケールに従って元の文字コードに戻して文字クラスを判別するのかも しれないが, そんなの遅くてやっていられないので, 以下のようなコードを地道に 書くことに。
#include <endian.h>

#if __BYTE_ORDER == __LITTLE_ENDIAN
#define ubyte(w) (*((char *)&(w)+1))
#define lbyte(w) (*((char *)&(w)))
#else
#define ubyte(w) (*((char *)&(w)))
#define lbyte(w) (*((char *)&(w)+1))
#endif

wtype_t wtype (wchar_t w)
{
	unsigned char c1 = ubyte(w), c2 = lbyte(w);
	if (0x4E <= c1 && c1 <= 0x9F)
		return ZEN_KANJI;
	..
}
wstring の中身が(普通の方法では)UTF-16というのはあまり聞かない話 なので, (専門の人には知られた話かもしれませんが)ちょっと書いてみました。 というか iswctype(3) が荒っぽすぎるので, 自分で文字クラスの関数を書かないと いけないというのはどうよ, みたいな気が少ししたりして。。
# ちなみに通常の自然言語処理では, 単語を整数に直して後の処理をすることが多い ので, こういうことを心配する場合は普通はあまり多くない, と思います。

#2 -

おまけ。 上のコードをデバッグする時に,
if (t == LATIN_CNTL)
	return "LATIN_CNTL";
if (t == LATIN_SPACE)
	return "LATIN_SPACE";
....
のようなコードを延々と書く必要があって, 何とかならないものかと思っていた。 (今回に限った話ではなく, 前にも同じように思ったことがあった。)
そういえば, cppに関連するマニアックな方法があったような..と思って K&Rの4.11.2節を見てみると, foo(x) をcppで置換する時, #x とするとxがクオート された文字列になって "x" となるらしい。(xは呼び出したときの文字列に置換される。)
ということで, 上のコードは
#define inspect_type(t,type) { if (t == type) return #type; }
inspect_type(t, LATIN_CNTL);
inspect_type(t, LATIN_SPACE);
...
と書いておくと, cppが置換して上と同じコードにしてくれる。(g++ -E で見ると わかる。) ブラボー。初めて使った機能でした。

ちなみに, これは「変数の名前」を"文字列"=データに変換できるということなので, かなり面白い。たとえば,

#define varexec(v) ((void(*)(void))#v)()
のようなマクロを定義しておくと, 変数vの名前を文字列にして, それを関数だと 思って実行することができるはず。だから例えば, 原理的には ASCIIで hello world のような感じで
#define varexec(v)      ((void(*)(void))#v)()
int
main (int argc, char *argv[])
{
	int PTXHHHH0Z_18RVX75ow = -1;	/* 中身は何でもよい */
	varexec(PTXHHHH0Z_18RVX75ow);
	/* = ((void(*)(void))"PTXHHHH0Z_18RVX75ow")(); が実行される */
}
とできるということ(!)。 *1
通常, プログラミング言語では変数は値だけが問題で, 名前は実行には完全に無関係 というナイーブすぎるソシュール主義があるわけですが(注: 前に書いた文章 ), それがここでは完全に逆転していて, 「変数は名前だけが問題で, 中身は何でもよい」 ことになっている。イカス! :-) :-)
*1: 問題は, C言語で許される文字だけで(例えばx86の)機械語としても有効な"名前" をつけるのが難しいかも知れない, ということだと思います。
なお, ((void(*)(void))__FILE__)(); とすると, "ファイル名プログラミング" ができます ("PTXHHHH0Z_18RVX75ow" というファイルにこの1行を書いておく)。この場合は文字の 制限はあまりなさそうです。


2 days displayed.
タイトル一覧
カテゴリ分類
 なかのひと
Powered by hns-2.10-pl1, HyperNikkiSystem Project