文房清玩の最近のブログ記事

The One Ring, Tengwar fonts

|

J. R. R. トールキンの『指輪物語』にテングワールという謎めいた文字が出て来る。架空の言語は謎めいたファンタスティックな世界の完結性をこの上もなく表わしている。あの恐ろしい力を持つ The One Ring にモルドール語で刻印された火文字を,LaTeX tengwarscript パッケージで組んでみた。

20110418-mordor.jpg

One ring to rule them all, one ring to find them,
One ring to bring them all and in the darkness bind them.
一つの指輪は,すべてを統べ,一つの指輪は,すべてを見つけ,
一つの指輪は,すべてを捕えて,くらやみのなかにつなぎとめる。
J. R. R. トールキン『指輪物語1』瀬田貞二・田中明子 訳,評論社,1992年,p. 112.

tengwarscript は CTAN: macros/latex/contrib/tengwarscript/ にある。バージョンは 1.3。フォントは何種類も出回っているが,私は AnnatarFormal だけを組込んで試してみた。上の画像は Annatar Italic である。流麗でなんとも美しい。原稿は以下のとおり。このモルドール語テクストはパッケージ添付 tengtest.tex にサンプルとして掲載されている。これを pdflatex で処理した。

% -*- coding: utf-8; -*-
% Tengwar on The One Ring from "The Load of the Ring" 
\documentclass[12pt]{article}
\usepackage[pdftex]{color}
\usepackage[T1]{fontenc}
\usepackage[all]{tengwarscript}
\definecolor{charc}{cmyk}{0,0.77,0.87,0}%
\begin{document}
\pagestyle{empty}
\color{charc}
\begin{center}
\tengwarannataritalic[2.0]
\tengwa{254}
\Textendedcalma\TTthreedots\Tnuumen\Tessenuquerna\TTthreedots%
\Tungwe\Tando\Toore\TTrightcurl\Tumbar\Ttinco\TTthreedots%
\Tlambealt\TTrightcurl\Tquesse\TTdoublerightcurl
\Tromanperiod\Ts
\Textendedcalma\TTthreedots\Tnuumen\Tessenuquerna\TTthreedots%
\Tungwe\Tungwe\Tumbar\TTnasalizer\TTdot\Ttinco\TTthreedots%
\Tlambe\TTrightcurl
\tengwa{255}\\
\Textendedcalma\TTthreedots\Tnuumen\Tessenuquerna\TTthreedots%
\Tungwe\Tthuule\Troomen\Tquesse\TTthreedots\Ttinco\TTthreedots%
\Tlambealt\TTrightcurl\Tquesse\TTdoublerightcurl
\Tromanperiod\Ts
\Textendedungwe\TTthreedots\Tumbar\Toore\TTrightcurl%
\Tesse\Tkern{-0.2}\Tmalta\TTrightcurl%
\Textendedcalma\TTdot\Ttelco\TTdot\Tquesse\Troomen\Tparma%
\TTnasalizer\TTdot\Ttinco\TTthreedots\Tlambe\TTrightcurl
\end{center}
\end{document}

tengwarscript のインストールは通常の LaTeX パッケージ組込となにも変わらない。ダウンロードした tengwarscript リソースを TDS に準拠して TeX ツリーに格納し,tengwarscript.mapupdmap-sys で登録する。フォントもほぼ同じだけれど,Formal については TrueType フォントファイル名を tengwarscript.map の記載に合わせてリネームする必要がある(もちろん map を訂正してもよい)。テングワール文字の出力命令については,ドキュメント tengwarscript.pdf を参照。
 

※ 4.20 付記

一応,端末上のインストール・オペレーションもメモっておく。端末操作は tcsh シェルである。TeX ツリーはローカル texmf とし,そのトップ・ディレクトリ名称を /usr/local/texlive/texmf-local としている。

まず,作業ディレクトリ(ここでは ~/tmp/tengwar)で tengwarscript パッケージをダウンロード,展開し,dtx, ins ファイルを latex 処理する。dtx はドキュメントでもあり,以下の操作ではリファレンス解決のため 2 回実行している。もとより PDF はすでに添付されているのできちんとした dvi ファイルが不要ならば,1 回の処理でもよい。

% mkdir -p ~/tmp/tengwar
% cd ~/tmp/tengwar
% set WGET="wget -nH -nd"
% set TEXDIR="/usr/local/texlive/texmf-local"
% $WGET http://mirror.ctan.org/macros/latex/contrib/tengwarscript.zip
% unzip tengwarscript.zip
% cd tengwartscript
% latex tengwarscript.dtx
% latex tengwarscript.dtx
% latex tengwarscript.ins

次に,Annatar 及び Formal フォントをダウンロード,解凍する。Formal フォントについては,map の記述に合うようにファイル名を変更する。

% $WGET http://home.student.uu.se/j/jowi4905/fonts/tngan120.zip
% unzip tngan120.zip
% $WGET http://tengwarformal.limes.com.pl/fonts/TengwarFormal-12c-ttf-pc.zip
% unzip TengwarFormal-12c-ttf-pc.zip
% cd TengwarFormal-12c-ttf-pc/fonts/
% mv TengwarFormal12b.ttf TengwarFormal12.ttf
% mv TengwarFormalA12b.ttf TengwarFormalA12.ttf

su -m で特権ユーザとなり,上で展開したリソースを TeX ツリーに格納し,フォントマップ登録を行う。

% cd ~/tmp/tengwar/tengwarscript
% su -m
# mkdir -p $TEXDIR/{doc/latex,tex/latex,fonts/{tfm,vf,type1,truetype,map/dvips,enc/dvips}}/
tengwarscript
# cp -p *.pdf $TEXDIR/doc/latex/tengwarscript/
# cp -p *.cfg *.sty $TEXDIR/tex/latex/tengwarscript/
# cp -p tfm/* #$TEXDIR/fonts/tfm/tengwarscript/
# cp -p vf/* $TEXDIR/fonts/vf/tengwarscript/
# cp -p map/* $TEXDIR/fonts/map/dvips/tengwarscript/
# cp -p enc/* $TEXDIR/fonts/enc/dvips/tengwarscript/
# cp -p *.ttf $TEXDIR/fonts/truetype/tengwarscript/
# cp -p TengwarFormal-12c-ttf-pc/fonts/*.ttf $TEXDIR/fonts/truetype/tengwarscript/
# mktexlsr
# updmap-sys --enable Map=tengwarscript.map

以上。

新常用漢字表

|

「𠮟」という文字がいまあなたのモニタに表示されているだろうか? 私の愛用する Mac OS X Snow Leopard: Safari 5.0.4 あるいは Mac OS X Tiger: Safari 4.1.3 ならしっかり見えるが,Windows ユーザはどうだろうか? Windows 7 なら大丈夫か。XP ユーザは見えないのではないだろうか? なんでこんなことを記すのかというと,昨年,11 月 30 日に告示された改訂常用漢字表にこの文字が追加されたからである。1981 年以来の改訂である。なんとその前は 1946 年。

上の「𠮟」という文字は「しかる」という訓を持つ字である。口偏に「七」と書く「しかる」。「しかる」と入力して仮名漢字変換されて普通に出て来る「叱」なら,おそらく誰のモニタにも表示されるはずである。ところが,いつもパソコンで入力している「叱」という文字のほうは誤字であって,「𠮟」こそがじつは正しい「しかる」なのだ(『字源』には「俗に叱と作るは非」とある)。JIS がはじめのボタンを着け間違えた次第なのである。ここに来て常用漢字表に正しい字体が入れられた。

文字「𠮟」は Unicode CJK Unified Ideograph U+20B9F というコードポイントを持つ。いわゆるサロゲートペアと呼ばれる拡張領域 (Extension B) に配置されている(JIS では JIS X 0213:2000 第三水準区点 4752)。この領域をきちんと読書きできるソフトウェアはまだ多くないのではなかろうか。私はここで「𠮟」の文字を Mac OS の「ことえり」で入力したわけではない。Emacs 24 ucs-insert 関数に 20b9f を指示して得られたものを,コピペしたんである。

そう,そんな特殊なところにある文字(正しい文字なんだけど)が常用漢字表に収録されたんである。このことはいまあんまり騒がれていないが,官庁,地方自治体はもとより,出版や報道業界にも少なからざる影響が出るはずである。その筋のシステム屋は,もうすでに,これら常用漢字表にあるにも拘らずシステムで表示・印字できない文字の取扱いに悩まされているはずである。大騒ぎにならないうちになんとかしなくっちゃと。

官庁・地方自治体のシステムは,つい最近に設計された新しいものは別として,Unicode 対応すら進んでいないのが実情だと思う。文字コードは JIS X 0208:1983, :1990 準拠が基本ではなかろうか。漢字コード草創期の設計を踏襲して大きくなって来た官庁・自治体システムは,人名許容漢字の法令に従わなければならず,貧弱な JIS X 0208 を補うために,JIS 第一水準/第二水準にない文字のために大量の外字を抱えている。そして,文字周りはいろんなところに影響するので,おいそれとは改修できない。(同じようなことを JIS 2004 についても書いたような気がする。)

JIS の独善的標準なら「システム仕様として対応してません」で済むかも知れないが,こと日本国政府ご指定の「常用漢字」に扱えない文字があるとなると深刻である。国民との文書交換を考慮すれば,世の官庁・自治体もこの常用漢字改訂で Unicode 対応システム改修に重い腰を上げることになると思う。また税金が本質的でないことのために消えて行くというわけである。漢字・仮名遣いという悪魔的正書法に立つ日本は,いつまでたっても文字を巡る混乱から解き放たれない宿命にある。「歴史的仮名遣いに戻せ」云々のエセ文化人による戯言よりも,もっと高度で抜差しならない宿命である。
 

* * *

ことのついでに,「𠮟」のようなサロゲートペア文字をどうしても入力できないとき,Perl で出力させるワンライナーを示しておく。Perl 5.8.5 くらいのバージョンが必要だと思う。

端末コマンドラインから次を叩くと,「𠮟」(=U+20B9F) が出力される。(※ 4.27: 少し簡略化した)

% perl -e 'binmode STDOUT, ":utf8"; print pack("U", 0x20b9f);'

あるいは,

% perl -e 'binmode STDOUT, ":utf8"; print "\x{20b9f}";'

20b9f のところに必要な文字の Unicode コードポイント十六進数を指定する。20bb7 を指定すると「𠮷」(吉野家のつちよし)が出力される。この出力をファイルにでもリダイレクトしてコピペして利用すればよい。Mac OS X Tiger 以降のターミナルなら端末上にきちんと文字が表示されるので,それをコピーすればよい。

Unicode コードポイント十六進数は,学研の『漢字源』なら JIS コードとともに掲載されている。なんの役にもたたない『JIS 漢字字典』なんて高価本を買うのはやめて,ぜひこちらを座右に置いていただきたい。私は改訂第四版を愛用しているが,最近第五版が刊行された。

Windows Vista, Windows 7 なら IME パッドから CJK Unified Ideograph Extension B 領域の文字を入力できると思う。Office も 2007 ならきちんと使えるはずである。
 

 

※ 4.26 付記

この記事を書いたあと,ネットを渉猟していたら,京大の安岡孝一先生(文字コードに関する権威でもある。日本語文字コードに関する見識において私が尊敬する学者のひとりである)が,2009 年 12 月の段階で「新常用漢字表が迫るUnicode移行、『シフトJIS』では対応不可能」というコラムを ITpro に掲載し,新常用漢字表の改訂について IT 業界に警鐘を鳴らしていた。さすがである。

上で「いつもパソコンで入力している「叱」という文字のほうは誤字であって」と書いた。この記述そのものを訂正するつもりはないのだけれど,「叱」という字体はすでに一般に浸透しており,もはや「誤り」とするのは時代錯誤というものである。出版の世界でも「しかる」「しっせき」に対して「叱」を表記しても,「無知無教養」でも「恥ずかしい」わけでもない。きちんとした国語辞典,しかもコンピュータの利用が一般化する以前に出版された新潮国語辞典(昭和 40 年初版)でもすでに「叱る,呵る」となっている(ただし,私の手元にある昭和 58 年刊岩波書店『広辞苑』第三版では「𠮟」という正字体のみが掲載されているし,平成 14 年再版・大修館書店『新漢語新辞典』では正字体「𠮟」のみが見出しになっており「叱」字体については「叱(口を開くさま)は別字であるが,俗に混用する」という記事がある)。つまり,JIS 第一・第二水準における「叱」採用は,JIS が「間違った」というよりも,もとよりこうした俗化・混用の「定着」の反映と捉えるべきである。

Babelbib with ptexlive

|

ptexlive で多言語文献参照パッケージ Babelbib を使ってみた。

LaTeX のマルチリンガルインタフェースとして Babel はデファクトスタンダードになっている。文献参照機能 BibTeX の世界でも Babelbib という Babel の言語切替に対応したパッケージが公開されている。Babelbib 2009 年 10 月の版でロシア語もサポートされた。ptexlive には初期導入されていて,すぐ使いはじめることができる。

pLaTeX2e においては BibTeX は jBibTeX を用いるのが主流だったが,ptexlive における日本語対応版は pBibTeX (pbibtex コマンド) という名称になっている。しかしながら,Babelbib を ptexlive で使う場合,pBibTeX ではなく BibTeX (bibtex コマンド) を使う。pBibTeX で文献データベース処理を行うとロシア語などでエラーになるからである。ptexlive ではキリル文字を欧文として扱う場合エスケープ形式 (文字を十六進数で表現した形式。例えば Ю^^d0^^ae で表す) にしなければならないが,pbibtex がこれをうまく処理できない。本家 bibtex ならうまく通るのである。

Babel を用いて ptexlive で日本語と外国語を混植するとき,稲垣さんの japanese.ldf 日本語言語定義を使っている人は多いと思う。Babelbib でも同様に japanese 環境に応じて文献参照の言語を切替えたい場合,Babelbib 用の日本語言語定義ファイル japanese.bdf を準備しなくてはならない。これの作り方はそんな難しいものではなく,すでにある言語定義をコピーして "Volume" などの文献項目表示ラベルを UTF-8 日本語で書直せばよい。私が試験的に準備した japanese.bdf を置いておく。ただし,これ,英語用を複製して japanese で動くようにしただけのしろもので,まったくラベルの書換をしていない。(※ 4.18 付記: nippon.ldf でも動くようにした。)

Babelbib の使い方は,端末から texdoc babelbib と打ち込めば表示される Babelbib PDF ドキュメントを参照していただきたい。ごくごく簡単に記すと,プリアンブルに以下のように書いておく。

\usepackage[utf8x]{inputenc}
\usepackage[T2A,T1]{fontenc}
\usepackage[italian,german,french,russian,english,japanese]{babel}
\usepackage[japanese]{babelbib}% load japanese.bdf

japanese.bdf は Babelbib 標準言語ではないので,パッケージ・オプションに japanese を指定してロードするよう指示しておくことがポイントである。

日本語 BibTeX では \bibliographystyle として jplainjabbrv が用意されているが,Babelbib では babplain などを使う。ただし,私が試した範囲では,ptexlive との組み合わせで,babplain, babplai3, babunsrt スタイル以外は動作しなかった。

サンプルを以下に示す。LaTeX 原稿 (mlbibjp.tex):

% -*- coding: utf-8; -*-
% mlbibjp.tex: BibTeX Babelbib test
% coded by isao yasuda.
\documentclass[b5paper]{jsarticle}
\usepackage[utf8x]{inputenc}
\usepackage[T2A,T1]{fontenc}
\usepackage[italian,german,french,russian,english,japanese]{babel}
\usepackage[japanese]{babelbib}
\setlength{\textwidth}{30zw}
\begin{document}
\begin{center}
  \Large\bf ptexlive Babelbib試験
\end{center}
 
Bib\TeX{}は\texttt{pbibtex}ではなく\texttt{bibtex}で実行した。
 
\vspace{1em}
ロシア語:
\selectlanguage{russian}
Юрий Лотман написал это в лит.\cite[с. 256]{lotman1970}.
 
\vspace{1em}
\selectlanguage{japanese}
イタリア語:
\selectlanguage{italian}
Nel 1930 venne pubblicato ``\textit{La carne, la morte e 
il diavolo nella letteratura romantica}'' (\cite{mario1930}), 
un testo che tradotto in inglese nel 1933 contribuirà 
ad estendere la sua fama in Gran Bretagna e Stati Uniti, 
e provocherà invece forti reazioni contrarie in Italia, 
fra cui quella di Benedetto Croce.
 
\nocite*
%% Choose one BibTeX style:
\bibliographystyle{babplain}% OK
%\bibliographystyle{bababbrv}% NG
%\bibliographystyle{babalpha}% NG
%\bibliographystyle{babunsrt}% OK
%\bibliographystyle{babamspl}% NG
\bibliography{ml}% see ml.bib
\end{document}

文献データベースファイル例 (ml.bib) は以下のとおり。書誌情報 language に Babel 言語名を指定すると,その言語でのマナーで文献出力がなされる。例にあるとおり,著者名,書名の文字列は UTF-8 で直接入力ができる。ロシア語もキリル文字をそのまま書いてよいし,独・仏語もアクセント付き文字をそのまま入力できる。

% -*- coding: utf-8; -*-
% ml.bib: babelbib test
% coded by isao yasuda.
@book{curtius1961,
  author={Curtius, E. R.},
  title={Europäische Literatur und lateinisches Mittelalter},
  year={1961},
  address={Berlin},
  language={german}
}
@inBook{mario1930,
  author={Praz, M.},
  title={La carne, la morte e il diavolo nella letteratura romantica},
  year={1930},
  address={Milano},
  language={italian}
}
@book{lotman1970,
  author={Лотман, Ю. М.},
  title={Структуры художественного текста},
  year={1970},
  publisher={Искусство},
  address={Москва},
  language={russian}
}
@book{tynyanov1969,
  author={Тынянов, Ю. Н.},
  title={Пушкин и его современники},
  year={1969},
  publisher={Наука},
  address={Москва},
  language={russian}
}
@Book{gracq1938,
  author={Gracq, Julien},
  title={Au château d’Argol},
  publisher={José Corti},
  year={1938},
  address={Paris},
  language={french}
}
@Book{basho1970,
  author={松尾 芭蕉},
  editor={中村俊定},
  title={芭蕉句集},
  publisher={岩波書店},
  year={1970},
  address={東京},
  language={japanese}
}

上記原稿をコンパイルし,PDF を生成するには以下のようにする。

% eplatex mlbibjp.tex
% bibtex mlbibjp.aux
% eplatex mlbibjp.tex
% eplatex mlbibjp.tex
% dvipdfmx mlbibjp.dvi

このとき注意が必要なのは,ロシア語,ギリシア語が原稿,文献データベースに含まれている場合,エスケープ形式にしておかないといけない点である。PTEX_IN_FILTER 環境変数にここであげたフィルタを指定して実行すれば,利用者が意識しなくても ptexlive (UNIX 版) がこの処理を通してくれる。

組版結果は以下のとおり。ここでは文献一覧をイタリア語環境で出力してみた。

20110409-babelbib.png

Unicode msearch 導入メモ

|

私のメインサイトでは namazu 2 でサイト内全文検索ができるようになっている。namazu 2 は UNIX 環境日本語全文検索エンジンの定番になって久しいが,基本的に ISO-2022-JP, Shift_JIS, EUC-JP の日本語文字コードを前提としており,多国語文書には適さない。ロシア語に限って言えば,Unicode ロシア語文書も検索できるのだけど(JIS の智慧のおかげ)。

最近ではサイト内検索エンジンをブログ管理システムに任せるか,Google のドメイン指定の検索窓を設けることで,自らインデックス管理自体をしないですむようになっており,独自に検索エンジンを設置する必要性は薄くなって来ている。ちなみに,Google のドメイン指定で自分のサイト内だけを検索するための検索窓は,以下のようなコードを自サイトのページに埋め込めばよい。

<form method="get" action="http://www.google.com/search">
<input type="text" name="q" size="30" maxlength="255" value="">
<input type="hidden" value="検索対象ドメイン" name="as_sitesearch">
<input type="hidden" name="hl" value="ja">
<input type="hidden" name="ie" value="UTF-8">
<input type="submit" value="Google 検索">
</form>
このサイト内なら—

私は受信したメールを MHonArc でアーカイブし,パスワードで文書セキュリティを保護することで,Web でどこからでも自分のメールを見られるようにしている。このような用途では,Google を使うわけには行かず(非公開なんだから当然),どうしても独自に検索エンジンを設置しなければならない。

Katsushi Matsuda,毛流麦花両氏による msearch は Unicode 文書からインデキシングが可能である。よって多国語文書も本来の文字列で検索が可能である。そこで私も Unicode 版 msearch Ver. 1.52 を導入してみた。これで柔軟な多国語検索とメールアーカイブ検索が両立できるというわけだ。http://yasuda.homeip.net/msearch.html から私のサイト内の検索ができるようにしてみた(メール検索は当然ながら非公開)。検索結果画面は msearch のお仕着せをそのまま使っている。まだ画面右上の namazu 検索は生きている。そのうち整理するつもりである。

msearch は,茶筌で日本語検索対象語を抽出してインデキシングを行う namazu とは異なり,おそらく n-gram で全文インデックスを抽出している。これは検索モレを防ぎかつ高速化を実現するのに有効な方法である。ただし,msearch は多国語文字を取り扱うことができるとはいえ,いわゆる語形変化に追随できるようなインデキシング解析をしているわけではなさそうである。Google なら,нести (「携える」という意味のロシア語不規則変化動詞不定形) を入力すると,несут (三人称複数現在) などの変化形をも検索できる。さすがである。

msearch は PDF, Microsoft Word, Microsoft Excel, Microsoft PowerPoint をインデキシングするためのフィルタを持たないため,そのままでは原則 HTML 文書だけを扱うことになる。私自身は .doc, .xls, .ppt ファイルをプライベートで扱うことはないので,まったく困らないのだが,PDF だけはなんとしても検索できるようにしたい。以下,PDF も取り扱うことができるように msearch 環境を調整するメモをしるしておく。環境は Mac OS X Snow Leopard (インデックス作成) 及び FreeBSD 8.1-RELEASE (公開 Web 環境) である。掲載内容は無保証である。

Unicode 版 msearch インストール

Unicode msearch のダウンロード,インストールは「サイト内全文検索エンジン ― Unicode版msearch」に毛流麦花氏による懇切丁寧な解説があるので,そちらを参照する。アーカイブを解凍し,cgi-bin/msearch にリソースを格納するだけである。Perl 5 が必要である。/~user/ などの Web ユーザディレクトリ下で msearch を運用する場合は,public_html/cgi-bin/msearch のパーミッションが 644 あるいは 755 (他ユーザの書込権限なし) になっていないと,Premature end of script headers のエラーが出て動作しないので注意。

私の場合,PDF 処理その他でサイトのドキュメント・ツリーを書き換えてしまうオペレーションが発生するため,Apache22 の公開エリアとは別に ~/var/webindex ディレクトリ (以下「ワークツリー」) を作成し,そのなかにサイト・ドキュメント・ツリーをコピーするとともに,msearch リソース・ディレクトリをも設置した。ここで検索インデックスをローカル作成(msearch では,Web ブラウザからインデックス作成操作が可能であるが,これを使わず,サーバ・ローカルの端末でコマンド操作によりインデックス作成を行うことを「ローカル作成」と呼んでいる)し,できたものを Apache22 の公開エリア /usr/local/www/apache22/cgi-bin/msearch にコピーするという運用である。

msearch のサイト用独自設定は default.cfg で行う。本稿の試行では,とりあえず set $home= の右辺を私のサイト URL に書き換えただけである。

PDF インデキシング

msearch で PDF ファイルのインデックスを作成するには,いくつか注意事項があり,少し工夫が必要である。そのままで PDF をインデックス作成対象に指定すると,インデックス・ローカル作成プログラム genindex.pl (本稿で「インデクサ」とあるのはこれのこと) は異常終了する。

PDF はテキスト変換した上でインデクサに掛けるのが基本である。UNIX X11 PDF ビュア XPDF のユーティリティ pdftotext で PDF -- テキスト変換を行った上でインデキシング実行すればよい。このときテキスト化されたファイルを元の PDF ファイルと同じ名称にしておかないと,検索結果のリンクで当該ファイルを参照できないので,テキスト変換結果で元 PDF ファイルを上書きしておく必要がある。PDF 以外でも wvWare (Microsoft Word 用),xlHtml (Microsoft Excel 用),pptHtml (Microsoft PowerPoint 用) の各 UNIX ソフトウェアを利用し HTML ないしテキスト形式に変換することで,msearch インデキシングが可能である。

第二の注意点として,HTML / XML 以外のファイルに対して msearch は BOM で Unicode エンコードを判断していることがある。BOM がないと,Web 検索結果画面上の当該ヒットエントリの文字が化けてしまうのである。普通,UTF-8 でテキストファイルを作成するとき,BOM を付けたりしないので,インデクサに掛ける前に UTF-8 BOM (十六進コード "EFBBBF") をワークツリーのテキスト変換後ファイルの先頭に書き込んでおく。これは echo, cat コマンドなどで簡単にできるのだけれども,私は,PDF に混在した不要な制御コード文字を取り除く目的と合わせて,これを行う簡単なプログラム chkucntlchr を書いた。PDF 以外のテキストファイルも同様の処置が必要である。

以上の処理を自動で行うシェルスクリプトのコード例を以下に示す。これを含んで,msearch インデックス作成の全体シェルスクリプト例を最後に掲げてある。

# PDF format conversion
$WRK=ワークツリー
$UCK=chkucntlchr # 制御コード削除・BOM 付加ツール
$STP=タイムスタンプファイル (前回実行時の日付属性をもつ空ファイル)
echo "*  Convert PDF to TEXT by pdftotext (XPDF)."
cd $WRK
for i in `find -L . -newer $STP -name "*.pdf"`
do
    pdftotext -enc UTF-8 -nopgbrk $i $i.txt
    if [ $? -eq 0 ]; then
        echo "**  pdftotext $i OK."
        $UCK < $i.txt > $i
        if [ $? -eq 2 ]; then
            echo "**  $i is empty. Ignore."
            rm -f $i
        fi
    else
        echo "**  pdftotext $i NG. Ignore."
        rm -f $i
    fi
    rm -f $i.txt
done

また,chkucntlchr ツールの Perl コードは以下の通りである。

#!/usr/bin/perl -w
# -*- coding: utf-8; mode: cperl; -*-
# chkucntlchr
# 2011(c) isao yasuda.
# - delete words including control characters (U+0001--U+0020, U+007F--U+00A0)
# - Add UTF-8 BOM (x'efbbbf') for msearch indexer
# - Return code 0: normal; 1: suppressed; 2: imput empty;
use strict;
use utf8;
binmode STDOUT, ":utf8";
my $flg = 0;
my $lc = 0;
my $utf8_bom = "\xEF\xBB\xBF";      # BOM for UTF-8
utf8::decode($utf8_bom);
print $utf8_bom;
while (<STDIN>) {
    chomp($_); $lc++;
    utf8::decode($_);
    my @line = split(/\s/, $_);
    foreach my $wd (@line) {
        if ($wd =~ /[\x{0001}-\x{0020}\x{007F}-\x{00A0}]/) {
            $flg = 1;
        } else {
            print "$wd ";
        }
    }
    print "\n";
}
if (! $lc) {
    print STDERR "*** $0: input empty.\n";
    exit 2;
}
if ($flg) {
    print STDERR "*** $0: suppressed control characters.\n";
} else {
    print STDERR "*** $0: no problem.\n";
}
exit $flg;


segmentation fault 対策

msearch インデクサに PDF を食わせるに際して,もっとも悩んだのはテキスト化した PDF でも,インデクサが segmentation fault エラーで異常終了する場合があることであった。インデクサからコールされる indexing.pl に罠を仕掛けて調査したところ,問題が二つ判明した。

まず第一には,サイトのインデックス対象ファイル数が多いと,UNIX の ulimit のファイルオープン数の制限に引っ掛かり,異常終了してしまう。ulimit -a で制限値を確認し,インデックス対象ファイル数よりも open files の設定値が小さければ,ulimit -n 数値 で値をファイル数よりも大きな値に設定する。

第二には,msearch インデクサは正規表現 s 演算子によって HTML タグの除去処理を行っているが,これをすべてのファイルに適用しており,テキスト変換された PDF ファイル中の文字列如何によっては誤動作してしまう。私のサイトの PDF は,LaTeX 多言語文書を dvipdfmx で処理した生成物が多い。LaTeX フォント・パッケージの enc ファイル(エンコーディング定義ファイル)によってはヘンな文字の羅列になることがあり,これでタグ判定の正規表現がぶっとんでしまったらしい。indexing.pl 791 行目を,HTML / XML でないときは実行しないように,以下の改変を行うと,アボートしないようになった。

#    $contents =~ s/<(?:[^"'>]|"[^"]*"|'[^']*')*>/ /g;  # オリジナル
    $contents =~ s/<(?:[^"'>]|"[^"]*"|'[^']*')*>/ /g if ($html_xml); # 対策

XPDF 多国語化

XPDF pdftotext の多国語対応について簡単にしるしておく。FreeBSD Ports,Mac OS X MacPorts では XPDF Japanese port が用意されており,これをインストールすれば日本語 PDF については扱うことが出来るようになる。しかし,多国語 PDF はダメ。

XPDF のサイトでは中国語,ギリシア語などいくつかの言語設定追加リソース・パッケージが公開されている。これらを用いて多国語対応設定ファイルを作成する。以下のシェルスクリプトを実行すれば,パッケージをダウンロード・展開した上で,カレントディレクトリに xpdfrc を生成する。これを $HOME/.xpdfrc として格納する。次に,パッケージのリソース xpdf-japanese 等を XPDF 管理ディレクトリ (FreeBSD なら /usr/local/share/xpdf) にコピーする。これで,pdftotext により,日本語のほか簡体中文,繁體中文,韓国語,ロシア語,ギリシア語,アラビア語,ヘブライ語などの Unicode テキストが出力できるようになる。ただし,この実行で生成された xpdfrc には PDF 表示の際に必要となるフォント定義がないので,あくまで pdftotext テキスト変換用途と理解いただきたい。表示も含めた設定は XPDF ドキュメントを参照して displayNamedCIDFontTT 定義に好みの TrueType, OpenType フォントを指定するなりして調整してほしい(私は UNIX 環境での PDF 表示は Adobe Reader を使っているのでこのへんは放置している)。

#!/bin/sh
# Download XPDF language packs
WGET="wget -nH -nd "
XPDFSITE="ftp://ftp.foolabs.com/pub/xpdf"
# XPDFETC は xpdfrc があるディレクトリに変更する
XPDFETC="/usr/local/etc"
$WGET $XPDFSITE/xpdf-arabic.tar.gz
$WGET $XPDFSITE/xpdf-chinese-simplified.tar.gz
$WGET $XPDFSITE/xpdf-chinese-traditional.tar.gz
$WGET $XPDFSITE/xpdf-cyrillic.tar.gz
$WGET $XPDFSITE/xpdf-greek.tar.gz
$WGET $XPDFSITE/xpdf-hebrew.tar.gz
$WGET $XPDFSITE/xpdf-japanese.tar.gz
$WGET $XPDFSITE/xpdf-korean.tar.gz
$WGET $XPDFSITE/xpdf-latin2.tar.gz
$WGET $XPDFSITE/xpdf-thai.tar.gz
$WGET $XPDFSITE/xpdf-turkish.tar.gz
# Expand archives
for i in *.tar.gz; do tar zxvf $i; done
# make xpdfrc
cp $XPDFETC/xpdfrc .
for i in `find . -name "add-to-xpdfrc"`
do cat $i >> xpdfrc; done

インデキシング用シェルスクリプト

最後に私が自サイト用に作成したインデキシング用シェルスクリプトを掲載しておく。Mac OS X Snow Leopard 環境である。HTML ソース Subversion 管理エリアからワークツリーに更新ファイルをコピーし,ワークツリーでインデキシングしたのち,Mac 上の Apache22 cgi-bin 試験環境にインデックスファイル default.idx をコピーする。これでできた Mac 上の default.idx をそのまま FreeBSD サーバの msearch 環境に転送して公開するという運用形態である。

私は自サイトの HTML 等公開コンテンツを Subversion でバージョン管理しており,ソースを commit すると Subversion の commit スクリプトが動作して,自動的に更新コンテンツを Apache22 のドキュメント・ツリーにコピーするようにしている。このスクリプトを変更し,commit のタイミングで msearch インデクス作成スクリプトを呼び出して,検索インデクスを自動的に更新することもできる。crontab に登録して定時自動実行するのもよいと思う。

上記の PDF テキスト変換以外にも,HTML の iso-2022-jp to UTF-8 変換なども実行内容に含まれている。シェル内の各パス設定,サイト設定は私の環境そのままなので,もしこれを活用する方がいらっしゃるのなら,自分の環境に応じて書き換えないといけない。もちろん,中味をよく確認し,私のいい加減なコードにヘンなところがあれば手直しいただいたほうがよい。

#!/bin/sh
# -*- coding: utf-8; -*-
# msearch index generator for ISOLDE
# - coded by isao yasuda, 1 Apr. 2011
#
# DESCRIPTION
# -----------
# 1.前回タイムスタンンプより新しいページをSRCからWRKに格納する。
# 2.JISコードのページをUTF-8に変換して格納する。(nkf, sed)
# 3.PDFをテキスト変換してWRKに格納する。
#     rc OK: .pdf の内容はテキストファイル 
#     rc NG: .pdf, .pdf.txt を削除する
# 5.テキスト変換 OK のものの制御コードを削除する。(chkucntlchr)
# 4.WRKでインデックスを生成する。(genindex.pl
# 5.インデックスをWRKからPUBに格納する。
#
# CAUTION
# -------
# 1.初期作成時はファイル数が多いのでWRKにsite treeをコピーしておく。
#
 
# SRC: ページソースエリア
# WRK: ワークエリア
# PUB: 公開エリア (ここでは触らない)
WWW=/usr/local/www/apache22
SRC=/home/isao/src/noxinsomniae
PUB=$WWW/data
CGI=$WWW/cgi-bin/msearch
WRK=/home/isao/var/webindex/website
MSE=/home/isao/var/webindex/msearch
STP=/home/isao/var/webindex/stamp
TMP=/home/isao/var/webindex/tmp
UCK=$MSE/chkucntlchr
NKF=/usr/local/bin/nkf
PDFTOTEXT=/usr/local/bin/pdftotext
 
echo "********************************************************"
echo "*  msearch Index Generation Start `date '+%Y/%m/%d %H:%M:%S.'`  *"
echo "********************************************************"
# Copy SRC to WRK
echo "*  New Files Archiving."
cd $SRC
find -L . -newer $STP -type f | grep -v '.svn' |\
xargs tar cf - | ( cd $WRK; tar xvf - )
cd $WRK
 
# Convert iso-2022-jp to utf-8
echo "*  Convert ISO-2022-JP pages to UTF-8 pages."
cd $SRC
for i in `find -L . -newer $STP -name "*.html"`
do
    $NKF -w $i |\
    sed -e 's|charset=[Ii][Ss][Oo]-2022-[Jj][Pp]|charset=UTF-8|g' > $WRK/$i
done
 
# PDF format conversion
echo "*  Convert PDF to TEXT by pdftotext (XPDF)."
cd $WRK
for i in `find -L . -newer $STP -name "*.pdf"`
do
    $PDFTOTEXT -enc UTF-8 -nopgbrk $SRC/$i $i.txt
    if [ $? -eq 0 ]; then
        echo "**  $PDFTOTEXT $i OK."
        $UCK < $i.txt > $i
        if [ $? -eq 2 ]; then
            echo "**  $i is empty. Ignore."
            rm -f $i
        fi
    else
        echo "**  $PDFTOTEXT $i NG. Ignore."
        rm -f $i
    fi
    rm -f $i.txt
done
 
# add BOM to text files
echo "*  Add BOM to TEXT files."
cd $WRK
for i in `find -L . -newer $STP -name "*.txt" -or -name "*.tex"`
do
    $UCK < $i > $i.tmp
    if [ $? -eq 2 ]; then
        echo "**  $i is empty. Ignore."
        rm -f $i
    fi
    mv $i.tmp $i
done
 
# rm svn control
cd $WRK
find . -name ".svn" -or -name ".#*" | xargs rm -fr
 
# Indexing
echo "*  Execute Indexing by genindex.pl. PARAM:"
echo "*   1 インデックス名前:        default"
echo "*   2 インデックス対象DIR:     $WRK"
echo "*   3 インデックス対象URL:     http://yasuda.homeip.net/"
echo "*   4 インデックス対象拡張子:   .html,.txt,.pdf,.tex"
echo "*   5 非インデックス対象DIR:   admin,common,css,archives"
echo "*   6 非インデックス対象拡張子: (指定無し)"
echo "*   7 非インデックス対象KWD:   (指定無し)"
echo "*   8 ランキング方法:         最終更新日時降順(1)"
echo "*   9 alt属性の文字:         指定しない(0)"
cd $MSE
./genindex.pl <<EOM
default
/home/isao/var/webindex/website
http://yasuda.homeip.net/
.html,.txt,.pdf,.tex
admin,common,css,archives
 
 
1
0
EOM
 
if [ $? -eq 0 ]; then
    echo "*  Index Generation Succeeded."
    ls -l $MSE/default.idx
    echo "*  Now Copy default.idx to $CGI."
    cp -p $MSE/default.idx $CGI
    # STAMP modify
    SDT=`ls -l $STP`
    echo "*  Previous Update: $SDT"
    touch $STP
    SDT=`ls -l $STP`
    echo "*  Now Updated:     $SDT"
else
    echo "*  Index Generation Something bad."
    ls -l $MSE/default.idx
fi
 
echo "*  Procedure Ended. `date '+%Y/%m/%d %H:%M:%S.'`"
# end of script
        

Year 2038 Problem, UNIX Millenium Bug

|

UNIX 2038 年問題というのがある。西暦 2000 年問題と同じような話である。伝統的な UNIX オペレーティングシステムは日付・時刻を 32 bit 整数値で管理しており,1971 年 1 月 1 日 0 時 0 分 0 秒をはじまりとして 1 秒毎に数値を 1 ずつ増加させる。これを前提としてそのときの時刻を計算している。ところがこの 32 bit データが 2038 年 1 月 19 日 3 時 14 分 07 秒を過ぎると桁溢れし,なんと 1901 年 12 月 13 日 20 時 45 分 52 秒 (UTC) にすっ飛んでしまう。2038 年問題とは,これに伴って UNIX システムでさまざまな不具合が出るであろう事態の総称である。

2038 年なんてまだまだ先だと思う人がいるだろう。でももうこの問題は現実味を帯びはじめている。私は会社で回覧されてくる他サイトの事故事例には必ず目を通すようにしているが,先日,HP-UX (ヒューレットパッカード社の UNIX) の旧版を使っているサイトでユーザ・ログインができなくなる障害報告を読んだ。ユーザ管理項目に有効期限があり,それに 9999 日みたいな大きな数値を指定したら,有効期限日時が 2038 年を飛び越えて 1901 年から折り返してしまい,有効期限はすでに超過しているとシステムが判断したがゆえの障害だった(ヒューレットパッカード社の名誉のために付け加えておくと,HP-UX 最新版では 2038 年問題は訂正されている)。2038 年問題は世間ではあんまり騒がれていないけれども,UNIX サーバに移行したクリティカルなシステムが極めて多いだけに,これ以上にマズイことも起きる可能性がないわけではない。

西暦 2000 年問題は,多くのシステムが西暦を下 2 桁で管理しているがゆえに 2000 年の判断を 1900 年と誤ってしまうことに起因した。その発現は予想が一筋縄ではなく,大陸間弾道弾が誤動作するかも知れないとか,ジェット機が操縦不能に陥るとか,大いに世間を騒がせた。おまけに 2000 年は 100 でも 400 でも割り切れるので超特例的閏年であったという事情が,計算機関係者の恐怖を煽り立てた。閏年を「4 で割り切れ,100 で割り切れない年」とする単純なロジックを使うプログラマが実際にいたのである。ふつう 400 年に一回のことを人生で突き詰めて考える人はまれである。関ヶ原の合戦以来のことが自分の人生で起こるなんて考える人はまれである。

計算機業界のことを知らない人には,2000 年なんてすぐ来るのがわかっているのになんでこんなバカな設計にしたんだろう,まったく呆れる,のようなことをホザく正論吐きがゴマンといた。現象の内在的論理を辿るよりも前に己の感じ方に満足してしまう人,進化の恩恵に無意識に浴する人の典型である。私の尊敬する米原万里も,どの本であったか忘れたが,同じことを書いていて,私は正直悲しくなったことを思い出す。もちろん西暦 1990 年代に設計され,それなりの期間使用される予定のシステムならば,2000 年を考慮していないのはただのバカである。しかし,当時問題になったのはコンピュータ黎明期から少しずつ改修されながら大規模化したシステムだからこそであった。共同体への影響がじつに大きい官庁システムがまさにこれにあたるからだった。私の顧客は,幸いにも,その事情を痛いほど知っており,2000 年対応システム改修にケチケチしなかった。

そもそも,2000 年で問題が出るのがおよそわかっていながら,なんでそういう設計になっていたのか。コンピュータ機器の進化には,3 年で性能が 2 倍になるという「ムーアの法則」と呼ばれる経験則がある。2011 年から逆算して 70 年代あたりに舞い戻ると,かつての計算機が現在と比べていかに貧相なものだったかが想像できるだろう。30 年昔の計算機の性能はいまの 210 分の 1,逆にいうと同じもののお値段はいまの 210 倍。40 年前なら 213 倍くらい。そう,その当時はメモリ 256KB の一月の借料がサラリーマン大卒初任給を越えるくらい高価だった。磁気ディスクも同じ。こういう超高価なリソースを使うとき,とにかくケチろうとするのは当然である。日付・時刻はどんな業務データの属性にも付いて回り,これを仮に short (2 byte) 整数で年,月,日,時,分,秒 12 byte 使えばデータに占めるその割合はバカにならない(まさかと思う前に 12 × 213 がどれほど重いか考えるがよい。いま日付・時刻の格納に一個あたり 12 × 213 byte 使わせてもらいます,なんて顧客に言ったら即刻クビである)。昔,私の担当したシステムでは西暦を下 2 桁だけで管理し,数字 1 桁を 4 bit に入れて 6 byte に切詰めていた。理論的にはもっと切詰められるが計算速度やわかり易さとの兼ね合いでこうしていたわけだ。それくらい記憶域が貴重だったのである。70 年代くらいのシステム設計者は,おそらく皆,計算理論の前に経済学に縛られていたのだと思う。

UNIX 2038 年問題についても,なんでたった 32 bit で管理するなんてケチったんだろうと思う人がいまならウヨウヨいるはずである。4 byte 32 bit というデータ構造は 32 bit 計算機がもっとも高速に取り扱うことのできるものなのだ。でも,それを抜きにしても,1970 年ごろの UNIX 設計者は,2038 年にはボクはもう生きていないと無意識に思ったはずだ。人生 70 古来稀なり。そのころにはボクたちのような貧しい資源制約から解放された,もっと夢のようなオペレーティングシステムが動いているさ,と。つまり計算機の世界でも,老人の感慨同様,人生はあっと言う間に過ぎたわけである。
 

* * *

ところで,西暦 2000 年問題はジョークのネタにもなっている。「2005 年のある日,アルバニア軍のコンピュータ系統が一斉にダウンした。その理由は? — 西暦 2000 年問題」。その国の時代遅れを笑う格好の題材になったんである。でも 2000 年を大きく超過して忘れ去られたころにプチ 2000 年問題が出て恥ずかしい思いをした SE/プログラマは必ずいると私は思う。

携帯機種変更

|

今日,会社携帯電話の機種変更をした。これまで使っていたのは日立製 W22H というモデルで,斜めにスライドする珍しい一品だった。電池交換を一度しただけで,まる 6 年も使ったんである。その間に何回も取り落としたりしてカメラレンズ枠が破損してレンズがむき出しになってしまっていたが,それはそれでスケルトンの味が出て愛用していたんである。古い機種とはいえメールはもちろん Ezweb も利用でき,機能的にはなんの不満もなかったわけだけど,2012 年 7 月の 800 MHz 帯周波数再編に関連して IC カード未対応の CDMA 1X がそろそろ使えなくなるということで,新機種移行ということになったんである。
 

20110306-keitai.jpg

新しい携帯電話もやはり日立製。beskey という名前である。会社が勝手に白色モデルを選定していた(白は経年のヘタレ感がすぐ出てしまうので,私は黒がよかったのだけど,そこは会社携帯,注文をつけても詮ないこと)。私もはじめて二つ折りの流行デザインモデルを携帯することになったわけである。ワンセグが観られるようになった。なんと 8.1 Mega 画素カメラを内臓している。でも,こんなのはどうでもよい。ま,機能的にはなんの新たな期待もなかったのであるが,この際なので,イヤホン,USB ケーブル,microSD カードを自前で調達して音楽でも入れて遊ぼ,ということに。LISMO Port を妻の Windows 7 PC に入れこんで(なんで Mac で使えるようにしてくれないんだ? あ,LISMO は Apple の 宿敵 SONY 製だからか),CD をラッピング,転送してみた。CD ジャケットも表示されてなかなかである。Apple iPod はかさばるので会社にもって行く気がしない。私はサラリーマンのくせに鞄をもたず手ぶらをするたちで,スーツの内ポケットに手帳と財布,外ポケットに通勤定期と文庫本を入れると,もう iPod の余地がない。この携帯ならイヤホンだけポケットに忍ばせておけばよろしい。 息子にも LISMO で携帯に音楽を転送する方法を教えてやったら(「着うたで浪費すんな!」という意味で),えらく感謝されてしまった。
 

20110318-lismo.jpg

Windows 7 マシン

|

妻が使っている PC はもう 10 年くらい昔に買ったオンボロ。JCS Vintage という渋いブランドマシンである。よっていまだに Windows 2000。IE6 は最近の新しいページを表示すると「スクリプトエラー,デバッグしますか」のエラーメッセージが煩くて仕方ない。ディスクも一杯でしょっちゅう不要データを削除しなければならないし,データのフラグメンテーションがハンパでないのにデフラグをする空きすら確保できず,低速運転でガマンしなければならなかった。というわけで,そろそろ買い替えようということになった。Mac にしたらと勧めたが,妻は「また新しいこと覚えんのイヤ」ということでやはり窓族を通すことに。

キューブ型静音設計の PC をネットで購入した。Shuttle 社が製造しているベアボーンである。モニタ,キーボード,マウス,スピーカはこれまでの品物を継続使用する。39,000 円しかしなかったが,それでも intel Core2Duo E7500/2.93 GHz MPU,2 GB DDR-3 メモリ,500 GB HDD,24 倍速スーパマルチドライブ搭載の充分な性能を持つ。妻の機械はわが家で最高性能の PC となった。Windows 7 はネットオークションで Ultimate 32/64 bit 同梱パッケージ正規品を安値で手に入れた。 このモデルは 35 言語から好きな言語を選択できるんである。もちろん日本語を選んだ。

このブログ・システムを稼働させている FreeBSD サーバ(同じ Shuttle 製キューブ。こちらは Core2Duo E7200/2.53 GHz)の上に新 PC を置いた。とりあえず 32bit 版をインストールし,リモートプリンタ,Thunderbird メールクライアント,秀丸エディタ,Adobe Reader 10,Silverlight だけは設置・調整した。いまの Windows は IP ネットワーク設定を自動でやってくれるのに感心した。Office は必要になったら設置するということにした。ところで,Windows 7 って Microsoft Office 2000--2003 は動くんだろうか。Office はアップグレードパッケージでこれまで繋いで来たので,アタマから入れ込むのはチョー面倒である。500 GB もディスクがありゃ昔なら FreeBSD か Linux も別パーティションにインストールして遊んだであろうが,いまはもうそんな元気はない。
 

20110305-shattle.jpg

misima 漢詩分析・詩語検索機能について,簡易版を追加した。旧版は SQL を直接入力する形態だった。これは DB に蓄積しているすべての項目について,柔軟な検索ができるのだけれども,SQL 操作ということもあり,限定公開とした。簡易版はごく限られた条件指定しかできない。それでもこれくらいありゃいいか,ということでこちらは一般の漢詩作成者の方々のお役に立てればと思い,一般公開とする。旧版も expert 版ということで残してある。方式的には expert 版も簡易版も同じで,簡易版は SQL 組立ての JavaScript を追加しただけである。

開発・本番環境は FreeBSD 8.0-RELEASE, Mac OS X Snow Leopard, Tiger, J2SDK-1.5, J2SDK-1.6, Tomcat-5.5, DWR-3-rc1, SQLite-3-5.6, SQLite-JDBC-3.7.2。ブラウザは Safari-5.0.3, Safari-4.1.3, Google Chrome-9.0 にて確認している。Windows ではまったく試験していないのでちょっと不安。

ここで簡易版の使い方を簡単にしるしておく。misima 漢詩分析・詩語検索機能のコンセプト,実現方式については「misimaKansiServlet 漢詩 Chinese Verse 平仄音韻分析」,「DWR with Java: misima 漢詩詩語検索」を参照。

misima 漢詩平仄音韻分析(Servlet版)」ページの「詩語検索」欄にある をクリックすると,別ウィンドウで検索画面が開く。検索はここで実行する。検索条件は図 1. に示す「平仄パターン」,「詩語」,「韻字」,「韻目」 を指定できる。
 

20110220-condition.jpg

図 1. 検索条件

「平仄パターン」(A) は求める詩語の平仄の並びである。プルダウンで平仄を設定する。「」は「平」,「」は「仄」を意味する。初期表示では「○-○-○」,すなわち「平-平-平」の 3 文字詩語の条件になっている。もし 2 文字の詩語を求めたいなら,3 番目のプルダウンで「-」を選択しなければならない。

○,●」いずれの場合も,検索結果に「」記号のものが含まれる。これは両韻を示す記号である。例えば,「思」という文字は意味によって「上平聲四支」と「仄去聲四寘」と平・仄どちらでも使用される可能性をもつ。もちろん詩語においてはどちらかに決まるのであるが,misima 平仄辞書で両韻のものは平・仄いずれの条件でもヒットするようになっている。だから当該詩語でその両韻文字がどちらの平仄で用いられているのか,辞書に当たって意味を確認する必要がある。

「詩語」(B) は指定した一文字を含む条件である。一文字しか指定できない。

「韻字」(C) 指定は詩語の末尾文字の条件である。押韻文字が決まっているときに用いる。

「韻目」(D) は「一東」などの韻目で検索するための指定である。押韻文字が決まっているとき,その韻目を含む詩語を閲覧したい場合などに用いる。韻目指定は面倒なので,ポップアップから選択するようになっている。「韻目」の入力エリアにカーソルが位置づけられると,入力メニューがポップアップされる(図 2.)。その一覧から検索したい韻目をクリックすると,入力エリアに韻目条件が設定され,メニューが消えるようになっている。
 

20110220-inmoku.jpg

図 2. 韻目ポップアップメニュー

条件 (A) は必須である。かつ,(B),(C),(D) から少なくともひとつは条件指定をしなければならない。そして,検索は (A) and ([(B)] or [(C)] or [(D)]) ([ ] 内はひとつ以上必要) という条件で実行される。これは長大な検索結果を防ぐためである。簡易検索はこれ以外の条件指定はできない。

簡易版検索結果例を図 3. に示す。これは「●-○-○」の 3 文字でかつ韻字が「秋」である詩語の検索条件である。
 

20110220-simple-search.jpg

図 3. 簡易版検索結果例

詩語韻目は,「ニモニック:番号:韻目」の様式で出力される。ニモニックの意味は次の通りである。hk: 上平聲; hs: 下平聲; sj: 仄上聲; sk: 仄去聲; sn: 仄入聲。「hk:01:東」は「上平聲一東」を意味する。; (セミコロン) は当該文字が複数の韻目を有することを示している。A;B;C は A, B, C 三つの韻目を持つ文字であることを示す。対応する文字の区切りは - (ハイフン) で判断できる。

簡易版では,(A) and (B) and ((C) or (D)) などのような検索条件指定は不可である。こういう柔軟な条件設定は expert 検索でのみ可能である。expert 版の条件指定は,「実行 SQL」のテキストエリアに where 句の内容を直接コーディングする。検索キーはページにある通り,詩語: sg; 詩語平仄: hs1; 詩語韻目: in1; 押韻字: oj; 押韻字平仄 hs2; 押韻字韻: in2; 詩語字数: ss; 出典: ta が指定できる。expert 版の検索結果を図 4. に示す。
 

20110220-expert-search.jpg

図 4. expert 版検索結果例

 

最後に参考文献を上げておく。
 

Ajax の高度な活用集。詩語検索機能で利用した DWR についても,サンプル付で少し解説されている。しかし,addRows() 関数の仕様など,DB 検索結果表示に適したテクニックの解説までは望むべくもなく,少し自分の課題に応じた詳細事項は,やはり DWR サイトのドキュメントに当たらないと解決不可能である。
 

オライリーのクックブック・シリーズは困ったときに必ず役に立つ。本書で述べられている便利なライブラリもオライリーのサイトからダウンロードできる。
 

これは JavaScript のリファレンス本としてはいちばん優れていると思う。なんといっても,非同期通信オブジェクト,XML DOM オブジェクトについて整理されている。オライリーの「クイックリファレンス」よりも個人的には使いやすい。

漢詩作成支援の一環で今回,詩語検索を追加した。SQLite3 で構築した詩語データベースを Java サーブレットから JDBC でアクセスする。高速化のために Ajax + Java Servlet を基本とした。近年,Ajax も便利なライブラリが出現し,Web 2.0 の世界をより簡単に構築できるようになった。今回はそのひとつ DWR (Dynamic Web Remoting) を使うことにした。

DWR の特徴は大きく二つある。第一に,JavaScript 動作の微妙に異なる数あるブラウザへの対応を吸収してくれること。第二に JavaScript からサーバの Java クラスの呼び出しを可能としたこと。とくに後者は,非同期通信インタフェースとサーバ (Servlet) の存在をプログラマから隠蔽することにより Java Servlet の約束事に精通していない Java プログラマにも (JavaScript が書けないとならないんだけど) Web サーバ・プログラミングを近しいものとする。

以下,misima 漢詩詩語検索を作成したメモを残しておく。

詩語データベースの構築

太刀掛重男著『詩語完備 だれにもできる漢詩の作り方』は,詩語に基づいて漢詩を作成する方法を述べており,合わせて詩語集を掲載している。また,詩語の韻書としては『詩韻含英異同辨』という決定版が存在する。できればこうした詩語集をデータベースに蓄積するのがよいのだが,著作権問題があり公開 DB に入れるのは憚られる(自分だけの個人辞書として構築するならよいのだろうが)。しかも,データ入力に気の遠くなるような時間を要する。私のようなサラリーマンにはとうてい不可能である。

そこで今回の詩語 DB は,どちらかというとコーパス・ビュア風のアイデアに基づくことにした。つまり,インターネットで大量に公開されている漢詩テクストを掻き集め,その詩行を 2 文字 + 3 文字 (五言詩) や 2 文字 + 2 文字 + 3 文字 (七言詩) に分解し,それぞれを「詩語」と見なし,これらに平仄・音韻分析処理を加えて,その結果をリレーショナル・データベースに仕立て上げるわけである。平仄・音韻分析用のデータベースは,「misima 漢詩平仄音韻分析」で構築済みだった。

私はロシア語作文をする際,語結合が妥当かどうか Google で検索してみる。ロシア語は「〜において」というとき,в, на のいずれの前置詞を使うのか悩ましいことが多い。「お茶会で」は на чайной церемонии でよいのか? Google で検索するとこのフレーズを含むきちんとしたページがたくさんヒットするので,不自然ではないとハッキリする。コーパス・ビュア風というのはこういう使い方を指している。漢詩詩語についても過去の偉大な詩人の作品で同じような確認ができるはずである。もちろん,詩語の意味,題詠用の分類(秋思,離別などの詩語と結びついたテーマ論)がないと片手落ちなんであるが,求める平仄,文字,字韻とそれに合致する詩語にどのようなものがあるのかが調査でき,詩語検索機能としてはそれなりのものが得られるはずだと考えた。「平-平-仄のパターンでこの文字を含む詩語」,「脚韻がこの韻目の詩語」,程度でも検索できれば便利ではないか?

『唐詩選』などの漢詩 500 首近くをネットから wget で戴いて来て,Perl HTML::TreeBuilder モジュールでもって詩テクストを解析,抽出して約 4,000 語の詩語テクストを得た。ついでに出典(詩人,題名)情報などの属性をぶら下げた。これに詩語の平仄データ,韻目などを追加して SQLite3 のデータベースが成った。

Java 詩語検索クラスの作成

DWR は様々な Java クラスの呼び出しをサポートしている。今回は JavaBeans で行くことにした。JavaBeans はデータを保持するオブジェクトで,データ項目の出し入れに set〜, get〜 なるメソッドを一式用意しておくというモジュール構造であり,データ部品化の基本になっている。サーバで DB を検索し,その結果を Bean に入れ,JavaScript から DWR インタフェースで取り出す。基本設計はそのようなものである。詩語のための JavaBeans SigoBean.java を以下に示す。本来なら DB に蓄積している項目はいくつもあるが,ここでは詩語,平仄,韻目のみに限定してある。

// -*- coding: utf-8; mode: java; -*-
/**
 *  misimaKansi SigoBean 漢詩詩語
 *  Copyright(c) 2011, isao yasuda, All Rights Reserved.
 */
public class SigoBean
{
    /**
     *  SQLite3 database
     *  詩語 sg, 詩語平仄 hs1, 詩語韻 in1
     */
    private String sg  = null; // 詩語
    private String hs1 = null; // 平仄
    private String in1 = null; // 韻目
 
    /** Constructor */
    public SigoBean(String sg,  // 詩語
                    String hs1, // 平仄
                    String in1, // 韻目
        )
    {
        this.sg  = sg;
        this.hs1 = hs1;
        this.in1 = in1;
    }
 
    /** Getter メソッド */
    public String getSigo()    { return sg;  }
    public String getHyosoku() { return hs1; }
    public String getSigoIn()  { return in1; }
 
    /** Setter メソッド */
    public void setSigo(String sg)     { this.sg  = sg;  }
    public void setHyosoku(String hs1) { this.hs1 = hs1; }
    public void setSigoIn(String in1)  { this.in1 = in1; }
 
    /** テキスト取得用メソッド */
    public String getSigoBean(String sep) {
        return sg + sep + hs1 + sep + in1;
    }
}

さて,実際に詩語データベースを検索し,上記詩語 Bean の配列テーブルとして結果をストアする Java クラスが当然必要である。SigoTable.java コードを以下に示す。ここで,SQLite3 DB アクセスは JDBC インタフェースを使っている。SQLite 用 JDBC ドライバは SQLiteJDBC – Xerial – Trac から sqlite-jdbc-3.7.2.jar (2010.8.27 版) を落として,クラスパスに通しておくとともに,Servlet コンテナ Tomcat の $CATALINA_HOME/common/lib/ にもコピーしておく。

// -*- coding: utf-8; mode: java; -*-
import java.util.ArrayList;
import java.util.List;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
/**
 *  misimaKansi SigoTable 漢詩詩語検索
 *  Copyright(c) 2011, isao yasuda, All Rights Reserved.
 */
public class SigoTable
{
    /** 詩語 DB path */
    private static final String dbpath = "/usr/local/etc/misima/SIGO.db";
    /** SQL */
    private String sqlcond = null;
    /** 詩語テーブル行データ */
    private ArrayList<SigoBean> dbRowList = null;
    /** データ行数 */
    private int gyosu;
   
    /**
     * 詩語 DB を検索し,詩語テーブルを SigoBean 配列として返却する
     * @return 詩語テーブル
     */
    public SigoBean[] getSigoTable(String cond) throws Exception {
        sqlcond = "select * from SIGOTBL where " + cond + ";";
        dbRowList = new ArrayList<SigoBean>();
        /** DB検索 */
        Class.forName("org.sqlite.JDBC");
        Connection conn = null;
        try {
            // create a database connection
            conn = DriverManager.getConnection("jdbc:sqlite:" + dbpath);
            Statement sttmnt = conn.createStatement();
            sttmnt.setQueryTimeout(30); // set timeout to 30 sec.
            ResultSet rset = sttmnt.executeQuery(sqlcond);
            while(rset.next()) {
                // read the result set
                dbRowList.add(new SigoBean(rset.getString("sg"),
                                           rset.getString("hs1"),
                                           rset.getString("in1")));
            }
            rset.close();
        }
        catch(Exception e) {
            System.err.println(e.getMessage());
        }
        finally {
            try {
                if(conn != null)
                    conn.close();
            }
            catch(Exception e) {
                // connection close failed.
                System.err.println(e);
            }
        }
        gyosu = dbRowList.size();
        SigoBean[] dbrows = new SigoBean[gyosu];
        return dbRowList.toArray(dbrows);
    }
   
    /**
     * 詩語 DB 行数を返却する (for debug)
     * @return 行数
     */
    public int size() {
        return gyosu;
    }
}

DWR 環境の作成

DWR のパッケージは DWR ダウンロードページ から dwr.war (Version 3. rc-1) を落として使った。DWR のサーバ側環境設定は大きく 3 点。以下簡単に示す。

  1. ダウンロードした dwr.war を詩語検索 Web アプリの WEB-INF/lib ディレクトリ直下に格納する。
  2. dwr.xml を,以下の内容で WEB-INF/ 下に格納する。これは JavaScript の記述とサーバ側 Java クラスを結びつけるための記述である。create タグで上記 SigoTable クラスが呼び出されるよう,convert タグによってそのデータ構造へのアクセスは JavaBeans SigoBean を介して行われるよう指定している。詳細は Configuring dwr.xml を参照のこと。
  3. <!DOCTYPE dwr PUBLIC
        "-//GetAhead Limited//DTD Direct Web Remoting 3.0//EN"
        "http://directwebremoting.org/schema/dwr30.dtd">
    <!-- -*- coding: UTF-8; -*- 
        misima 漢詩詩語検索用 dwr.xml
        Copyright (c) 2011, isao yasuda, All Rigths Reserved.
        $Id: dwr.xml,v 1.1 2011/02/17 13:55:58 isao Exp $
    -->
    <dwr>
      <allow>
        <create creator="new" javascript="SigoTable">
          <param name="class" value="SigoTable"/>
        </create>
        <convert converter="bean" match="SigoBean"/>
      </allow>
    </dwr>
    

  4. 詩語検索 Servlet 用のデプロイメント・ディスクリプタ web.xmlWEB-INF/ 下に準備する。今回,旧字・旧仮名遣い変換 misimaservlet のサブシステムとして作成したので,すでにある web.xml に DWR 関連用の servlet タグ及び servlet-mapping タグを追加した。DWR 部分は以下とまったく同じでよいと思う。詳細は DWR WEB-INF Reference を参照のこと。
  5. <!DOCTYPE web-app
        PUBLIC  "-//Sun Microsystems, Inc.//DTD Web Application 2.2//EN"
        "http://java.sun.com/j2ee/dtds/web-app_2_2.dtd">
    <!-- -*- coding: UTF-8; -*- 
        misimaServlet web.xml デプロイメントデスクリプタ
        Copyright (c) 2007, isao yasuda, All Rigths Reserved.
    -->
    <web-app>
      <!-- misimaservlet サーブレット -->
      <servlet>
        <servlet-name>misimaServlet</servlet-name>
        <servlet-class>misimaServlet</servlet-class>
    ... (略) ...
      </servlet>
     
      <!-- DWR サーブレット -->
      <servlet>
        <servlet-name>dwr-invoker</servlet-name>
        <servlet-class>org.directwebremoting.servlet.DwrServlet</servlet-class>
        <init-param>
          <param-name>debug</param-name>
          <param-value>true</param-value>
        </init-param>
      </servlet>
     
      <!-- misimaservlet サーブレットのマッピング -->
      <servlet-mapping>
        <servlet-name>misimaServlet</servlet-name>
        <url-pattern>/convert</url-pattern>
      </servlet-mapping>
      
      <!-- DWR サーブレットのマッピング -->
      <servlet-mapping>
        <servlet-name>dwr-invoker</servlet-name>
        <url-pattern>/dwr/*</url-pattern>
      </servlet-mapping>
    </web-app>
    

クライアント・ページ JavaScript の作成

最後に DWR のキモであるクライアント側 JavaScript を作成する。サービス用 HTML から呼び出す JavaScript として DWR ライブラリを次のように指定しておく。

<script type="text/javascript" src="dwr/engine.js"></script>
<script type="text/javascript" src="dwr/util.js"></script>
<script type="text/javascript" src="dwr/interface/SigoTable.js"></script>

はじめの 2 行はおまじないのようなものである。dwr/interface/SigoTable.js は,dwr.xml における javascript="SigoTable" という指定を受けて DWR が自動生成するスクリプトであり,ユーザアプリに応じて名前を変えて指定しなければならない。

さて,DB を検索し,その結果が挿入される HTML は以下の通りである。input タグに SQL 条件を入力し,「検索」ボタンを押下すると,retrieveSigo() 関数(後述)を起動するコードになっている。

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
          "http://www.w3.org/TR/html4/loose.dtd">
<!-- Copyright(c) 2011, isao yasuda, All Rights Reserved. -->
<html>
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
    <title>misima 漢詩詩語検索</title>
  </head>
  <body>
    <dl compact>
      <dt>実行 SQL</dt>
      <dd>select * from SIGOTBL where <br> 
        <input type="text" size="70" id="condition">;
        <input type="button" value="検索" onClick="retrieveSigo()">
      </dd>
    </dl>
    <!-- 詩語検索結果挿入するテーブル -->
    <table border="0">
      <thead>
        <tr style="background-color: #CCCCCC;">
          <th width="80px">詩語</th>
          <th width="120px">詩語平仄</th>
          <th width="400px">詩語韻</th>
        </tr>
      </thead>
      <tbody id="sigotable"></tbody>
    </table>
    <script type="text/javascript" src="dwr/engine.js"></script>
    <script type="text/javascript" src="dwr/util.js"></script>
    <script type="text/javascript" src="dwr/interface/SigoTable.js"></script>
    <script type="text/javascript" src="./sigo.js"></script>
  </body>
</html>

検索ボタンに紐づけられた検索実行制御処理 retrieveSigo() 関数は以下の通り。上記 HTML の sigo.js にこれを定義しておく。ここでサーバとの非同期通信を担っているのは SigoTable.getSigoTable(sql.value, ...); の部分である。サーバ側にある SigoTable クラスの getSigoTable() メソッドをコールしている。これは Java クラスを操作するのと同様の様式であり,DWR の特徴となっている。このコーリング書式は クラス名.メソッド名(メソッド引数, コールバック関数); である。サーバで実行されたメソッドの返値を引数として コールバック関数 が実行される。このなかでブラウザ表示に必要な処理を記述する。

// -*- coding: utf-8; mode: javascript; -*- 
// misima 漢詩詩語検索
function retrieveSigo() {
    var sql = document.getElementById("condition").value;
    var cellFuncs = [
        function(data) { return data.sigo; },    // 詩語
        function(data) { return data.hyosoku; }, // 平仄
        function(data) { return data.sigoIn; }   // 韻目
    ];
    // insert table contents from DB    
    SigoTable.getSigoTable(
        sql,
        function(data){ // callback
            dwr.util.removeAllRows("sigotable");
            dwr.util.addRows("sigotable", data, cellFuncs, {
                // 偶数行の背景色を変更
                rowCreator:function(options) {
                    var row = document.createElement("tr");
                    if (options.rowIndex % 2 != 0) {
                        row.style.background = "#CCCCCC";
                    }
                    return row;
                },
                escapeHtml:false 
            });
        });
}

retrieveSigo() 関数の引数のなかに関数が記述されておりそこでさらに関数が入れ子になっている。わかりにくいのでもう少し説明しておく。ここでサーバからの返値は function(data) 関数 (コールバック関数) に渡され,こちらは DWR util.js のユーティリティ addRows() 関数で HTML のテーブル (上記 HTML の <tbody id="sigotable"> の位置) にデータを展開している。addRows() 関数の書式は以下の通りである。

dwr.util.addRows(id, array, cellfuncs, [options]);
- id: テーブル要素の id。テーブル要素は <tbody id="id"> とするのがよい。
- array: 表にしたいデータ配列
- cellfuncs: 行データの各セルに応じた処理を行う関数の配列
- options: オプション (rowCreator, cellCreator, escapeHtml から複数指定可)

retrieveSigo() ではサーバからの出力 datacellFuncs という名の関数配列で項目を抽出しつつ id="sigotable" のテーブル要素に編集している。この際,rowCreator オブジェクト・オプションを指定し,これに偶数行ごとに背景色を変える関数(= その返値オブジェクト)を対応づけている。また,escapeHtml:false オプションを指定して HTML タグのエスケープをしないようにしている。addRows() 関数は実行のたびに行を追加するだけなので,removeAllRows() 関数で予め行を削除する前処理を行っている。

DWR の JavaScript の書き方,関数仕様詳細は DWR サイト・ドキュメント を参照。悩んだのは cellFuncs 関数配列中の data.sigo 等のオブジェクト指定であった。このうちの sigo の部分は JavaBeans の get〜 メソッドの 〜 を指定しなくちゃならないことに気づくのにえらく時間を要してしまった。それでも MVC デザイン・パターンに従って,しこしこ JSP をコーディングしていたのに比べると,遥かにわかりやすいと思う。DWR なら MVC のうちの C (Controller つまり Servlet) をほぼ意識せずに Web アプリを書くことができるからである。

以上でリソースは整った。Java コードをコンパイルした上で,リソース一式を Tomcat 環境にデプロイしておく。

実行イメージ

misima 漢詩平仄音韻分析」ページに「詩語検索」のボタンを追加した。これをクリックすると,詩語検索のウィンドウがオープンして,詩語の検索ができる。詩語と平仄パターン,韻目が表示される。以下に検索イメージ図を掲げておく。これは平仄パターンが「○-●」(平-仄)もしくは「○-◎」(平-平仄両韻)の 2 字詩語で,かつ「秋」という文字を含む詩語を検索した結果である。ただし,今回作成した版は,直接ユーザが SQL を入力するというイビツにして危険なものであるため,公開は友人限定としている。(2.20 付記:その後,詩語簡易検索機能を一般公開した。その詳細は記事「misimaKansiServlet 漢詩平仄音韻分析・詩語簡易検索」を参照ください。)
 

20110220-expert-search.jpg

検索イメージ

Old Standard Cyrillic Fonts

|

ロシアの LaTeX メーリングリスト CyrTeX-ru投稿 #9606 に Old Standard キリル・フォントを LaTeX で使う話題が上がっていた。興味深かったので,私もインストールして使ってみた。

Old Standard フォントは Шрифтовое семейство Old Standard サイトの説明によれば,古典文献学,聖書学,中世史学等の人文科学研究文献に適した多言語フォントとある。OpenType フォントはキリル文字のほか,古スラヴ文字,アクセント付きラテン文字,複式アクセント付きギリシア文字も含んでいる。つまりロシア語旧正書法の文字をも含んでいることになる。もともと Antiqua, New Standard 系のフォントのようである。

Old Standard フォントを LaTeX で使うには二つの方法がある。[1] autoinst による方法と,[2] CyrTeX-ru #9606 リンクにある OldStandard-source.7z を用いた方法である。ただし,いずれの方法においても,ギリシア文字の取扱いは考慮されていない。

[2] では T2A, T1, TS1 フォントエンコーディングが考慮されている。イタリック書体のとき ; (セミコロン) が出力できない問題がある(生成された Type1 フォントのエンコーディング・バグのようである)。これに対し,[1] の方法は T2A, T1, TS1 のほか,古スラヴ文字 T2D エンコーディングが利用可能だし,[2] のセミコロン問題がない。そういう意味で私は方法 [1] を推奨する。導入の手間は前提ツール次第であって,すでにツールが揃っていればどちらの方法もそれほど面倒ではない。[1] は autoinst 関連ツール(「Хартия, Эвристика フォント: Autoinst によるフォント組込み」にメモを残したので,そちらもご覧ください),[1], [2] ともに LCDF ツールを必要とする。

簡単に [1], [2] の UNIX 系システムでの導入方法をメモしておく。ptexlive-2009 環境である。端末操作は tcsh シェルである。私は Mac OS X Tiger, Snow Leopard で実施したが,Linux, FreeBSD でも同じ操作でよいはずである。

autoinst によるインストール

  1. Загрузка шрифтов (フォント・ダウンロード) サイトから oldstandard-2.0.2.otf.zip をダウンロードし,解凍する。
  2. 解凍したディレクトリで autoinst を実行する。--encoding オプションに T2D を指定するためには,t2d.enc エンコーディング・ファイルが予め TeX ツリーに格納されていなければならない。このファイルは PSCyr-0.4-beta フォント・パッケージなどで入手できる(ここにインストール・メモを記した)。
  3. % autoinst --encoding=T2A,T2D,T1,TS1 *.otf
    

  4. スーパユーザで以下を実行する。autoinst が生成した LaTeX リソースを TeX ツリーに格納しているだけである。これら一連のオペレーションを行うシェルスクリプト autoinst-install.sh を落として使っていただいてもよい。
  5. # setenv TEXDIR /usr/local/texlive/texmf-local
    # mkdir -p $TEXDIR/{fonts/map/dvips,tex/latex}/OldStandard
    # cp -p *.sty *.fd $TEXDIR/tex/latex/OldStandard
    # cp -p *.map $TEXDIR/fonts/map/dvips/OldStandard
    # cd $HOME/.texlive2009/texmf-var
    # find . -name lcdftools -type d | xargs tar cf - | ( cd $TEXDIR; tar xvf - )
    # mktexlsr
    # updmap-sys --enable Map=OldStandard.map
    

  6. 使い方は,通常のロシア語用 LaTeX 原稿のプリアンブルに \usepackage{OldStandard} を追加すればよい。ロシア語旧正書法テクストを直接入力する場合は,以下のように utf8x inputnec 及び T2D エンコーディングの設定が必要である。処理結果イメージをそのあとに掲げておく。原稿及び PDF もリンクしておく。古風な味わいのあるフォントである。
  7. % -*- coding: utf-8; -*-
    % OldStandard Cyrillic Fonts 
    \documentclass[b5paper]{article}
    \usepackage[T2D,T1]{fontenc}% T2D fontenc
    \usepackage[utf8x]{inputenc}% ucs
    \usepackage[russian]{babel}
    \usepackage{OldStandard}
    \pagestyle{empty}
    \setlength{\textwidth}{100mm}
    % 以下 T2D 用設定
    \def\cyrillicencoding{T2D}% russianb.ldf に T2D 指示
    \makeatletter% \cyrii 互換命令
    \def\@td{T2D}% 
    \let\CYRIItmp=\CYRII% upper case
    \let\cyriitmp=\cyrii% lower case
    \def\cyrii{\ifx\cf@encoding\@td\cyrizhe\else\cyriitmp\fi}%
    \def\CYRII{\ifx\cf@encoding\@td\CYRIZHE\else\CYRIItmp\fi}%
    \makeatother%
    \begin{document}
    Вопросъ о разрывѣ Татьяны съ Онѣгинымъ, несмотря на всю
    ясность. Пушкинскаго стиха, выросъ у насъ въ своего рода 
    \glqq гамлетовскую проблему\grqq,
    къ которой постоянно возвращается критическая мысль.
     
    Онъ, по выраженію Достоевскаго, имѣетъ въ нашей литературѣ
    \glqq своего рода исторію весьма характерную\grqq.
      
    Иначе говоря, вокругъ него сталкивались и боролись 
    различныя враждующія теченія соціально-политической мысли.
     
    И совсѣмъ не случайно выразителями двухъ наиболѣе 
    противоположныхъ взглядовъ на этотъ предметъ являются 
    представители враждующихъ міросозерцаній
    "---соціалистъ-радикалъ Бѣлинскій и 
    націоналистъ-славянофилъ Достоевскій.
     
    \vspace{1em}%
    \small%
    \hfill%
    \parbox[t]{.8\textwidth}{%
    \textit{А. И. Ванновский}~~Зерколо судьбы. (Сон Татьяны.)\\
    в кн.: \textit{С. А. Небольсин}~~Пушкин и европейская традиция. 
    Историко-теоретические работы. М. 1999.}%
     
    \end{document}
    

    20110210-oldstandard.jpg


OldStandard-source.7z によるインストール

  1. http://narod.ru/disk/4873172001/OldStandard-source.7z.html から OldStandard-source.7z をダウンロードする。解凍には 7-Zip 圧縮をサポートしたアーカイバが必要である。
  2. Windows MikTeX ユーザなら,添付の fos-FontLab.bat を実行すればよいはずである(私は未確認)。UNIX ユーザは仮想端末から以下を順次実行する。まず,解凍した OldStandard ディレクトリで以下を実行する。これでフォント・リソースが生成される。fos-fontgen.sh としてシェルスクリプトにしたので,これを使ってもよい。
  3. % latex fos-drv.tex
    % latex fos-map.tex
    % foreach i (*.pl)
    foreach? set BS=`basename -s .pl $i`
    foreach? pltotf $BS.pl $BS.tfm
    foreach? end
    % foreach i (*.vpl)
    foreach? set BS=`basename -s .vpl $i`
    foreach? vftovf $BS.vpl $BS.vf $BS.tfm
    foreach? end
    %
    

  4. スーパユーザでリソースを TeX ツリーにコピーし,マップ登録を実行する。fos-install.sh としてシェルスクリプトにしたので,これを使ってもよい。
  5. # setenv TEXDIR /usr/local/texlive/texmf-local
    # mkdir -p $TEXDIR/{fonts/{tfm,vf,afm,type1,map/dvips},tex/latex}/OldStandard
    # cp -p *.tfm $TEXDIR/fonts/tfm/OldStandard
    # cp -p *.vf $TEXDIR/fonts/vf/OldStandard
    # cp -p *.afm $TEXDIR/fonts/afm/OldStandard
    # cp -p *.pfb $TEXDIR/fonts/type1/OldStandard
    # cp -p fos.map $TEXDIR/fonts/map/dvips/OldStandard
    # cp -p *.fd $TEXDIR/tex/latex/OldStandard
    # mktexlsr
    # updmap-sys --enable Map=fos.map
    

  6. 以上でインストールは完了。使い方は通常のロシア語 LaTeX 原稿に \renewcommand{\rmdefault}{fos} を追加すればよい。ただしこの場合,T2D エンコーディングは使えない。また,dvipdfmx で PDF を生成する際,イタリックのセミコロンがエラーになるので注意。

友人の皆様,あけましておめでとうございます。

さて,この正月はまったくどこにも出歩かず,家でずっとプログラム作成,芭蕉研究をしていた。そして,最近,漢詩に興味があり自分でも書いてみたいと思い,漢詩の本に首っ引きであった。俳句・短歌と大きく異なり,漢詩はご存知のとおり,平仄,音韻規則が厳しくてちょっとやそっとじゃ立ち入ることすらできない。俳句なら「春の夜や兄が屁をひり咽せるまで」みたいなのは小学生でも作ってしまう。もちろん俳句・短歌もよい作品を詠むのは生半可のことではないのだけれども,漢詩はまずもって規則に準拠する壁の前に,へたくそな詩すら形をなすこと自体に苦労する。「規則」があるなら計算機の出番。ということで形式分析プログラムを自分のために作ってみた。

misima を作成した際に漢字データベースを作ったこともあり,それに基づくこのサーバも misima シリーズとすることにした。入力した漢字が DB になかったとしてもご愛嬌ということで。この漢字 DB は 6,700 文字程度を蓄積している。覚えたての SQLite3 を使った。漢詩規則は何冊かの本を研究してロジックを考えた。3 年前に作成した misimaServlet, misimaserver を土台に,サーバ化するのは簡単であった。Java Servlet + Ajax + Perl Daemon という方式にした。Javascript が送信した電文を Java Servlet が受け,Perl サーバとソケット接続する。漢詩の分析ロジックは,すべて Perl サーバでこれを実行する。Perl サーバは 3 プロセス分プレフォークして処理依頼を待ち構えていている。ちょっと渡り歩きが多いのだが,Ajax + Java Servlet はページ書き換えが高速で,CGI よりは体感速度は良好のはずである。ただし,本プログラムで使用した Ajax の XMLHttpRequest 関数はクロスサイト・スクリプティング対策実装のため,プロキシを経由する企業 Web 環境からは misimaKansiServlet を利用できないかも知れない。

試行版(まだきちんとデバッグしていない)を「misima 漢詩平仄音韻分析(Servlet版)」にしばらく置いておくので,興味のある方はお試しください。漢詩を作る方のお役に立てればと願っている。まだ出力がベタで汚い。そのうちできるだけ見やすくなるよう工夫したいと思う。

主な仕様は次のとおりである。近体詩五言・七言の絶句,律詩を対象とする。詩格を自動判定する。国字(和製漢字)が含まれていると,デフォルトでは分析を停止する(オプションで無理矢理検査をすることもできる)。詩格に応じて,二四不同,二六対,下三連,弧平(五言詩では二段目,七言詩では四段目だけ)の禁則を検査する。韻字分析では,脚韻の妥当性,冒韻を検査する。拗体,通韻にはいまのところ対応していない。韻目は平水韻に準拠した。同字重出も検査するが,虚字,重言 (畳語) など許容される重複も含めて,重出と見なすようになっている。そのうち詩語データベースを作成して,詩作支援も盛り込みたいと思っている。

実行イメージは次のようなものである。(※ 2.5 付記:画像を最新イメージで入換えた)
 

20110103-kansi.jpg

参考にした文献は以下である。
 

本書は漢詩作りの入門書としては決定的な名著とされている。文字通り「誰にでもできる」と謳っている。掲載された詩語を検索しながら作詩する方法が丁寧に書かれている。漢詩とは言わば高級な着替人形のようなもので,形式と使い古された詩語との芳醇な組み合わせ自体に魅力を感じない人,新規なものにこそ魅力を感じる人には,もはや魂に訴えないだろう。ところがこの作法に慣れるにつれて,菅原道真,嵯峨天皇などの日本の古代の漢詩人たちに対して身近な親しみが芽生えて来るから不思議である。

Amazon で古書が入手できるようなのでリンクを付けておく。新品は,版元に直接注文するか,中国書・漢籍関係を取り扱っている特殊な本屋でないと入手できない。私は東方書店 Web サイトから購入した。
 

これは,細かいことがごちゃごちゃ書いてあるけれども,いまいち整理が足りないという欠点がある。「辞典」と銘打っているのに漢詩作詩法に関する用語の索引がないという,著者・版元の本作りに対する考え方,誠実さを疑いたくなるような書籍である。ただでさえ見た目の立派な函入りの高価な本なのだ。それでもここであげた書籍のなかではいちばん詳しく(雑然とではあるが)作詩法を解説しているので,私のプログラムも多く本書の記述に準拠している。

著者は現代詩を憎悪しているようである。リズムも言辞もぶっとんだレベルの低い文学だとみなしているようである。漢詩が最高の文学表現らしい。ほぼ堂上にある詩語の使用しか認めず同時代の差し迫った表現を排除してしまう漢詩の本性を鑑みるにつけ,こんなことを言って殻に閉じ籠るから漢詩人が絶滅寸前になってしまったんだろう,ということが,ある意味でよくわかる書籍である。芭蕉の言う「不易流行」の「不易」ばかりを追い求め,「流行」の命脈を欠いた姿である。私はこういうのを「権威主義」だと思う。ローマはすでに亡んだのに。そのためか,著者・飯田の詩論は「負け犬の遠吠え」のような印象が拭えない。でも私なんかは,ふむふむ,なかなかいいこと言っていると思わないでもなかった。「負け犬」の言い分も聞くに値することがある,とくに世を支配している趣味が底の浅い時代にあっては。私は本書を読み,漱石,朔太郎,子規の偉大さを改めて思い知った。明治の文学的地殻変動期には,近代日本における「詩とはなにか」が深く追究されたのである。
 

この本はどこでも手に入る。値段も手頃だし,薄くてすぐ読めてしまうし,著者も漢詩研究について日本の学会の権威的存在でもあり,簡にして要を押さえて,いちばんのお勧めかも知れない。『漢詩入門韻引辞典』とは違って著者のただの趣味でしかない詩論を押し付けないところもよい。なにより事項索引がきちんと付いているのがありがたい。さすが大修館書店である。
 

詩韻含英異同弁 (1963年)
浜 隆一郎,石川 梅次郎編校
松雲堂書店

略して「含英」と呼ばれている。求める韻を含む詩語を検索するための本である。江戸時代に書かれた書物で,しかも現代においても韻書の決定版とされている。これの引き方を覚えるのがまずひと苦労である。本書も新品は Amazon などでは入手できない。中古で出ているが,私は Yahoo! ブックスで探しまわってやっと新品を手に入れた(See: 詩韻含英異同弁 - 石川梅次郎/編校 浜久雄/編校 - Yahoo!ブックス)。
 

『字源』は漢詩人御用達の漢字辞典である。そういう点でここにもリンクを設置しておく。misimaKansiServlet では平仄の確認において,原則,学研『漢字源 第四版』に準拠した。『字源』は適宜参照した程度である。

これ,大正 12 年初版というのだから驚く。本辞典は収録漢語の多いのがなによりの美点である。私は普段は大修館書店『漢和辞典』か学研『漢字源 第四版』を愛用しているが(後者は Unicode コードポイントが検索できめっぽう便利なのだ),漢語・字訓を調べるときごくごくたまに『字源』を引く。

本辞典は,大正期以降の漢詩人御用達の権威的辞書であるだけに,漢詩作成サイトの多くが「漢詩作成になくてはならぬ辞書である」かのごとく必要以上に本書を持ち上げている。でも,そんなのはウソに決まっている。『言海』など戦前に纏められた権威ある辞典は旧字・旧仮名遣いにこだわる人たちから大いに賞讃されているのだが,検索しづらいばかりか歴史的仮名遣いに誤りも散見される。『字源』にも「水」の字音を「すゐ」とするなどの誤りがある(正しくは「すい」--- 「すゐ」は一般に流布していた誤りで,最近の辞典では「すい」に正されているのだ。「歴史的仮名遣い」なんてそんなものである)。また『字源』は,説明はすべて歴史的仮名遣い,漢音も字音仮名遣いのみの表示であり,初版増補の昔の活字組版がそのまま用いられていて,画数の多い漢字について活字が潰れて判読できないところすらある。エセ文化人の慕うくだらない「権威」よりも「学問性」と「有用性」に留意するならば,現代の新しい辞書のほうがよいと私は確信している。

私はかつて古書で 4,000 円くらいで本書を手に入れたが,いまやプレミアが付いて 10,000 円以上の価格が付いているようである。経年変色した絵画に美を覚えるようなバカ文化人(歴史的仮名遣いへの回帰を叫ぶような奴ら)でない限り,普通の現代人にとって『字源』よりももっと検索しやすく内容も確かな漢字辞典はいくらでもある。
 

※ 2011.2.18 付記
その後,詩語検索機能を追加した。記事「DWR with Java: misima 漢詩詩語検索」を参照ください。

今日は今上陛下の御誕生日。うちの大学一年になる息子も今日が誕生日。可哀相に,誕生日とクリスマスが近接しているために,お祝いはいつも同時になってしまい,本人は少し損をした気になっているのかも知れない。

とういう訳で今夜は,これからお祝い,プレゼント交換をすることになっている。ところが,肝心の息子はこれからアルバイト。妻,娘と私の三人だけで川崎駅近くで焼き肉を食いに行くことになった。明日か明後日に家族皆でケーキでも食うか。

昨日,仕事の帰りに家族へのプレゼントを仕入れた。いつものように本,レコード。芸がないが,子供たちが自分ではまず買わないだろうものを選んだ。ラッピングは昨年買ったものが残っているはずだと思ったが,今日午,包装しようと探したけどどこにしまったのかまったく思い出せず。探すのをあきらめて,仕入れた Tower Records と丸善の袋を使うという体たらく。自作ロゴを印刷したシールを貼って取り繕った。

妻が来年のカレンダーを買って来てくれた。勤務先出版社のすぐ近くにあるナウカ神保町店で,Русская Икона (『ロシアのイコン』) を見つけて来たんである。Благовещение, XVII в. (『受胎告知』, 17 世紀),Андрей Рублев の描いた Сретение (『ハリストス迎接』, 1399 頃) など,美しいイコンを集めた 2011 カレンダーである。ロシアの祝日やロシア正教の聖日が載っている。

そんな訳で,友人の皆様,クリスマス,来る新年をお喜び申し上げます。イコンにちなんで教会スラヴ語風メッセージをお送りします。LaTeX OldSlav 教会スラヴ語パッケージで組んで,Ghostscript で EPS アウトラインを取ってから Adobe Illustrator CS で jpeg にしました。

% eplatex xmas.tex
% pdvips -Ppdf -E -D 10000 xmas.dvi -o tmp.eps
% gs -dNOPAUSE -dBATCH -sDEVICE=epswrite -r10000 -sOutputFile=xmas.eps tmp.eps
 

2010-xmas.jpg
 

20101223-xmas.jpg

URL encode in LaTeX

|

LaTeX でロシア語テクストを含む URL を出力しなければならないとき,url パッケージの \url 命令だと,キリル文字が出力できない。hyperref パッケージの \href{URL}{text} 命令を使って,text 部にロシア語テクストを記述すれば,これが可能となる。ところが,後者の場合でも,URL 部にロシア語 URL をそのまま指定しても,PDF にした際にそのリンクから当該リソースに飛んでくれない。この URL 部にはエンコード形式,つまり,ロシア文字を 1 オクテットずつ %xx の十六進数とした形式を指定しておかなければならないようである。

URL エンコードを行うツールはあちこちに転がっていて,Web なら http://www.tagindex.com/tool/url.html などの便利なサイトがある。Emacs 用の Elisp も探せばあるかも知れない。でも,LaTeX で,この URL エンコードを埋め込むとなると,% 文字が含まれるため,これをいちいちエスケープする手間が別途発生し,これまた面倒である。そこで,これくらいならツールを探す時間の間に出来てしまうと思い,自前で LaTeX 向け UTF-8 前提 URL エンコード・ツールを作ってみた。Perl である。U+0080 以上の UTF-8 文字を URL エンコードするので,ロシア語以外に日本語,ドイツ語などを含む URL にも適用できるはずである。同じ必要に駆られる方もいらっしゃると思うので,以下にそのコードを掲載しておく。ここにも置いておくので,ダウンロードして使っていただいてよい(無保証)。

#!/usr/bin/perl -w
# -*- coding: utf-8; mode: cperl; -*-
#  URL encoding: convert chars over U+0080 to format %hex.
#  Usage: urlenc [ -l ] < stdin (url text)
use strict;
use utf8;
use Getopt::Std;    # command line processing
use File::Basename; # get file basename
 
# command line
my %opts = ('l' => 0);
Getopt::Std::getopts('l', \%opts) ||
    die "Usage: " . basename($0) .
    " [ -l ] \< (stdin)\n  -l: insert \\ before % for LaTeX\n";
my $sfx = "%"; $sfx = "\\" . $sfx if ($opts{'l'});
 
# hex format
while (<STDIN>) {
    utf8::decode($_);
    my $enc = "";
    foreach my $chr (split(//, $_)) {
        if ($chr ge "\x{0080}") {
            utf8::encode($chr);
            foreach my $bchr (split(//, $chr)) {
                $enc .= $sfx . sprintf("%x", ord($bchr));
            }
        } else {
            $enc .= $chr;
        }
    }
    print $enc;
}

Perl コードはこれだけである。標準入力から読んだ URL 文字列のうち U+0080 以上を %xx 形式に変換して,標準出力に書き出す。オプション -l を指定すると LaTeX 向けに \%xx とエスケープした形で出力する。このプログラムを urlenc と名付けて,パスの通ったところにコピーして利用する。Mac OS X ターミナルでの実行例を以下に示す。

url-term.jpg

Emacs から利用する場合は,以下の内容を .emacs に記述し,関数定義を C-x C-e で Emacs に認識させるか,Emacs を再起動すれば,urlencode 命令が利用可能となる。ウラで上記 urlenc プログラムが動くので先きにこれを組込んでおくこと。urlenc の絶対パスは利用者の環境に応じて変更する必要がある。LaTeX 原稿において変換したいテクストをリージョン設定し,M-x urlencode RTN とすれば,当該リージョンが URL エンコード変換される。Emacs の set-default-coding-systems'utf-8 にセットしておかなければならない。

;;
;; URL encoding for LaTeX
;;
(set-default-coding-systems 'utf-8) ;; すでに設定されていれば不要
;;
(defun urlencode (start end)
  "URL encoding for LaTeX"
  (interactive "r")
  (call-process-region
   start end
   "/usr/local/bin/urlenc" ;; urlenc の絶対パスを指定
   t (list t nil) nil
   "-l") ;; urlenc LaTeX 用オプション
  )

Emacs 上での変換の様子を以下に示す。

url-emacs.jpg

事業仕分けもいい加減・SQLite

|

会社でも政府予算の動向把握は欠かせない。民主党政権の特色のひとつになった事業仕分けの結果も大きな関心を呼ぶ。なにせ時間と労力を掛けて必死こいて担当者が提案していたシステム化が,あの内実も知らない素人仕分け人のつっこみに対して役人がうまく対処できなかったために,一瞬のうちに「廃止,凍結」という話になってしまう。世の官庁関係の仕事をしている人で,これまでの苦労があの数十分の議論のおかげで水泡に帰してしまったような人には,あの仕分け人を後ろからブスリとやりたくなった奴もいるんじゃなかろうか。

ま,国家事業の無駄排除のために侃々諤々議論したうえで,「無駄」と切り捨てること自体は悪いことではない。それで国税を国民生活全体にとってより有益な事業に振り向けることになるのなら,誰だって文句は言えない。もともと事業仕分けは,国税の使途において長かった自民党政権下で既得権益と化した事業,あるいは「天下り」官僚のための有名無実の事業に対する政治による裁断ではなかったか,と私は理解している。しかしいまや,ニュースでも報道されるように,すでに民主党政権となり彼ら自身が予算化したも同然の事業に,尚もつっこみを入れなければ気が済まないのは,この劇場会議,そもそも予算策定の過程に民主党がまったくコミットできていないという恥ずかしい証拠になっているだけじゃなかろうか。

10 月末に行われた事業仕分け第三弾,特別会計の個別 48 事業の仕分け結果の資料を見た。特別会計とは,受益と負担の関係を明確にするために一般会計と区別して経理を行うものである。年金,労働保険など歳入に応じた行政の歳出で成り立っているような事業がこれに相当する。ま,事業はさすがにいろいろあるんだけど,このところ収賄事件で注目していた特許特別会計に私は目がいった。特許庁関係が特別会計になっているのは,ほぼ企業から得られる特許出願料・登録料という歳入だけで審査・審判・公報活動を行う財政構造・予算で成り立っているからである。要するに自分で稼いだカネで仕事をして日本国の産業,ひいては国民に成果を還元している訳である。

特許特別会計の平成 13 年度報告書が,情報公開法に基づき経産省サイトで閲覧できるようになっている。これを見ると,わが国の特許事業は 1,850 億円の歳入に対して歳出がなんと 950 億円であり,次年度繰越金が 900 億円近くもある。普通の会社なら利益率 100% に近い超優良企業である。それなら出願料を下げて出願人企業にもう少し還元したらどうかとも思う。しかしその一方で,なんのために存在しているのかもよくわからない政府外郭団体が無駄に税金を垂れ流す「天下り事業」と比べれば,稼いだ金の範囲で国益を創出している点で,遥かに健全な国家事業であるとも言える。

ところが,事業仕分け第三弾の結論を見ると,特許電子図書館事業は「将来的に廃止」,知的財産権教育事業は「文科省の仕事であり,廃止」,とにべもない。前者は,特許庁の審査用庁内検索システムが将来的に一般にも公開されるという背景を踏まえるとまだ納得できるのだが,後者は,じゃあ文科省にきちんと予算化させるところまでフォローしろよと言いたくなる。技術的,組織的に文科省ができないから経産省・特許庁が音頭取りをしていることをまったく理解していない。なのに,やめろと言うだけでこうしたらどうかという前向きな意見がまるでない。また,「アンタじゃなく文科省がやるべき,アンタはそれを手伝いなさい」などと省庁の縦割り構造を無視した結論を出すのは,現実的な観点において無責任ではなかろうか。

要するに,いまの事業仕分けはアラ探しばかりをする素人の無責任なつっこみにしか見えないのである。国益を考えた建設的意見がまるでない。そう考えるのは私だけではないと思う。だいたい,特別会計のような歳入と歳出の構造が明らかな国家事業にまで素人が首を突っ込むんじゃねぇ。技術立国の根本政策の実行官庁である特許庁の事業を,しかも健全な税金運用をしている特許事業を,井戸端会議的に引っ掻き回すんじゃねぇ。私はアタマに来た。私は当初の事業仕分けに対しては「政治主導」の端的な姿としてかなり好感を抱いていたが,今回の結果を見る限り,初心を忘れた素人つっこみ大会にしか思われなくなってしまった。事業仕分けはいまやただの劇場政治である。仕分ける前にきちんと予算化の段階でコミットすべきである。それはできるはずなんじゃないんでしょうか,政治主導というのだから。
 

* * *

最近,プライベートで漢詩を研究していて,misima の機能に漢詩規則分析を入れたいと思うようになった。平仄の妥当性の検証,孤平や下三連等の禁止事項のチェック,平仄に適合する詩語の検索など,漢詩を作りたいと思う人・漢詩の分析をしたい人のための支援機能である。misima の辞書を作りながら四声データも集めたので,まずはこれをもとにした平仄チェック,禁止事項チェックを行って診断結果を出力するとともに,すでにある機能と連携して \CID 形式の正字体に自動変換し,返り点命令変換を含めて,LaTeX 形式で出力するくらいはできそうである。

漢字・詩語データベースをどうするか悩んで,これまでと同じように DBM にデータを格納し Perl の連想配列で回すのがいちばんラクだと考えたのだけれども,検索機能ものちのち入れるんなら,ちょっと大げさだけど RDB にしようと思った。そこで手軽な SQLite を少し勉強することにした。SQLite は,RBMS サーバなしにライブラリだけで RDB を使う枠組みを特徴とし,ユーザ管理機能も高度なトリガー機能もないけれどもシンプルで軽い,パブリックドメインの RDB ソフトウェアである。Safari や Firefox が SQLite でブックマークなどを管理していることをいまさらながら知った。

会社の帰り,いつも行く虎ノ門の書店「書原」で本を漁った(この本屋,人文社会系の品揃えはなかなかである一方,コンピュータ関係はまったくダメである。またコミック,マンガ雑誌などまったく置いていない。よってコンビニ的風景を免れている。そのポリシーこそが私の贔屓にする所以でもある)が,SQLite の本は見当たらなかった。今日はいつもと違う道で新橋まで行こうか,とぶらぶら霞ヶ関を歩いた。日比谷公園にでも寄るか,ともふと思ったが時間が遅いのでこれはやめ。財務省と文科省の間の小道を抜け,桜田通り(国道 1 号線)を渡って霞ヶ関郵便局の辺りまで来ると,文教堂書店があった。小さい本屋だけど覗いてみたら,技術評論社刊行の『SQLite ポケットリファレンス』があった。このシリーズについてこれまで私は Perl, JavaScript, SQL, LaTeX に関する本を重宝していたので,迷わずこれをゲットした。DML の説明はあらかた普通の SQL 本と変わりがない。DB 運用に関る DDL, 端末コマンド仕様を帰りの電車で読んでイメージを理解した。
 

 

2011.1.5 付記

その後,漢詩平仄音韻分析プログラムをリリースした。SQLite3 を使った Java Servlet である。漢詩に興味のある方は「misima 漢詩平仄音韻分析(Servlet版)」をお試しください。

Khartiya, Heuristica LaTeX packages

|

先日書いた「Хартия, Эвристика フォント: Autoinst によるフォント組込み」で OpenType フォントから autoinst を用いて LaTeX タイプセットに必要な諸々のファイルを生成する方法を探ってみた。でもじつは,こんな面倒なことをしなくても,これらフォントのダウンロード・サイトには LaTeX 用のパッケージ一式が公開されていた。Хартия: http://code.google.com/p/khartiya/downloads/list から khartiya-0.2-tex.tar.xz を, Эвристика: http://code.google.com/p/evristika/downloads/list から heuristica-0.3-tex.tar.xz を取得して,TeX ツリーに展開すればよい。オペレーションは以下のとおり。$TEXDIR にはインストールしたい TEXMF トップディレクトリを指定する。~/Downloads は,アーカイブをダウンロードしたディレクトリを示す。

% mkdir -p ~/tmp/khartiya-heuristica
% xz -dc ~/Downloads/khartiya-0.2-tex.tar.xz | tar xvf - -C ~/tmp/khartiya-heuristica/
% xz -dc ~/Downloads/heuristica-0.3-tex.tar.xz | tar xvf - -C ~/tmp/khartiya-heuristica/
% su -m
# cd ~/tmp/khartiya-heuristica/
# tar cf - ./doc ./dvips ./fonts ./tex | ( cd $TEXDIR; tar xvf - )
# mktexlsr
# updmap-sys --nomkmap --enable Map=khartiya.map
# updmap-sys --enable Map=heuristica.map

フォントを使うには LaTeX 原稿に \usepackagekhartiya.sty, heuristica.sty を指定する。autoinst で自動生成した場合とは異なり,LaTeX パッケージではマクロファイル名の先頭が小文字になっている。

これら LaTeX パッケージは T2A キリルエンコーディングのほか,T1, TS1 用のフォント定義を含んでいる。autoinst によれば autoinst --encoding=T2A,T1,TS1 *.otf で生成した場合と同等になっている。textcomp パッケージと併用すると,\textcelsius などのマクロを Хартия, Эвристика フォントで出力することができる。ただし,これらフォントは textcomp のすべての文字を収録している訳ではない(例えば \textleaf やオールドスタイル数字: \text*oldstyle などは含まれない)ので注意が必要である。私がこの前書いた記事では,autoinst の --encoding オプションに TS1 を指定していないので,その場合,textcomp の出力は標準の TC あるいは Latin Modern フォントが拾われるはずである。どちらがよいかは利用者次第であろう。
 

* * *

今日の朝日新聞夕刊スポーツ面で「鄭大世 賛辞と批判」というコラムを読んだ。北朝鮮代表としてワールドカップに出場した彼は,川崎フロンターレからドイツ二部リーグのボッフムに移籍した。そこでチームの得点頭となる活躍をする一方で,警告で退場するなどの迷惑ぶりでも目立った選手になっている,そういう記事だった。ファイティング・スピリットに溢れる鄭大世らしいこの消息に,うれしくなってしまった。

南アフリカ・ワールドカップののち,海外に移籍する日本人選手がいきなり増えた。香川真司選手などドイツ・ブンデスリーガ・ドルトムントで大活躍している。内田篤人選手のアシストであの元スペイン代表ラウールがゴールした,なんていう話を聞くと,サッカーでもワールドクラスの話題に日本人が食い込んで来る時代が来たんだ,とうれしくなってしまう。70 年代,80 年代,日本がワールドカップ出場とはまったく無縁であった時代,日本人が指をくわえてワールドカップを観ていた時代を知っているだけに,感無量である。

こういうところからも,私たちの世代の日本人よりもいまの若い日本人のほうが優れているということを実感するのだ。そういう点がいちばんうれしい。

昨日,ロシアの LaTeX ユーザ・メーリングリスト CyrTeX-ru に,Хартия (Khartiya) 及び Эвристика (Heuristica) キリルフォントの新しいバージョンがリリースされたとの投稿があった(#9285: "Новые версии шрифтов Хартия и Эвристика" posted by Андрей Панов)。私はこのフォントを使ったことがなかった。ダウンロードして Mac OS X Snow Leopard 上の ptexlive で使用してみた。そのメモをしるしておく。

Хартия, Эвристика フォントの配布アーカイブは OpenType フォントを含むだけで,LaTeX で使うためのリソースを添付してはいない。すなわち,.fd (フォント定義ファイル), .tfm (tfm フォントファイル), .map (マップファイル), .sty (スタイルファイル) などの各種ファイルは,ユーザが自分で準備しなければならない。しかし,LaTeX コミュニティにはそのための便利なツールが用意されている。fontools パッケージがそれである。CTAN: fonts/utilities/fontools/ から入手可能である。autoinst は fontools プログラム群のフロントエンドとして各種 LaTeX リソースを一操作で生成してくれるプログラムである。

fontools は ptexlive ならはじめからインストールされている。もし,自分のシステムに組込まれていなければ,アーカイブを取って来て,bin/ ディレクトリ下にある perl プログラムをパスの通ったところにコピーすればよい(実行権限が付加されているか確認のこと)。fontools は Eddie Kohler 氏による LCDF TypeTools (otftotfm プログラム) を前提とするので,こちらを先にインストールしておく。ptexlive ならばこちらもすでに導入済みのはずである。これらのツールは W32TeX 用のアーカイブも用意されていると思う。

上記ツールの組込みが完了していれば,autoinst を用いたフォントインストールは次のように行う。

まず Хартия, Эвристика フォントパッケージをダウンロードする。それぞれ http://code.google.com/p/khartiya/, http://code.google.com/p/evristika/ から,khartiya-otf-0.2.tar.xz, heuristica-otf-0.3.tar.xz を取得する。その後,xz, tar で解凍する。ここでは $HOME/tmp/{khartiya, heuristica} に展開するものとしている。

% mkdir -p ~/tmp/{khartiya, heuristica}
% xz -dc ~/Downloads/khartiya-otf-0.2.tar.xz | tar xvf - -C ~/tmp/khartiya
% xz -dc ~/Downloads/heuristica-otf-0.3.tar.xz | tar xvf - -C ~/tmp/heuristica

それぞれのディレクトリにおいて autoinst を実行する。キリルフォントなので,T2A エンコーディングを指定する。

% cd ~/tmp/khartiya
% autoinst --encoding=T2A *.otf
% cd ../heuristica 
% autoinst --encoding=T2A *.otf

これが終了すると,それぞれのディレクトリに .sty, .map, .fd ファイルが生成されているはずである。そして同時に $HOME/.texlive2009/texmf-var/fonts/.../lcdftools/ 下に Type1 フォント,tfm フォント,vf フォント,.enc エンコーディングファイルといった LaTeX 用リソースが生成されているはずである。この段階で, autoinst を実行したユーザは .sty, .map, .fd ファイルを参照できるところなら LaTeX でこれらフォントを使ったタイプセットが可能になる。当該ユーザ以外にも LaTeX システム全体で使えるようにするため,次に,これらのリソースを TeX ツリーにコピーし,さらにマップ登録を行う。以下のオペレーション中の $TEXDIR は,インストールしたい TeX ツリーのトップディレクトリ(/usr/local/texlive/texmf-local 等)に読み替えていただきたい。

% cd ~/.texlive2009/texmf-var/
% find . -name lcdftools | xargs tar zcvf ~/tmpfonts.tar.gz
[ 自動生成されたリソース一式を "lcdftools" ディレクトリ名で探索し,抽出 ]
% su -m
# cd $TEXDIR
[ $TEXDIR は /usr/local/texlive/texmf-local 等に読み替えること ]
# tar zxvf ~/tmpfonts.tar.gz
# mkdir -p ./{fonts/map/dvips,tex/latex}/lcdftools/
# cp ~/tmp/khartiya/Khartiya.map ./fonts/map/dvips/lcdftools/
# cp ~/tmp/heuristica/Heuristica.map ./fonts/map/dvips/lcdftools/
# cp ~/tmp/khartiya/*.{fd,sty} ./tex/latex/lcdftools/
# cp ~/tmp/heuristica/*.{fd,sty} ./tex/latex/lcdftools/
# mktexlsr
# updmap-sys --nomkmap --enable Map=Khartiya.map
# updmap-sys --enable Map=Heuristica.map

以上で導入は終わりである。今回のような方法で OpenType フォントを LaTeX で手軽に使うことができると思う。ただし,日本語フォントへの適用は,jvf 等の関係で不可ではないかと思う。

Хартия, Эвристика フォントで LaTeX 文書を組むには,プリアンブルにそれぞれ \usepackage{Khartiya}, \usepackage{Heuristica} を指定する。あとは通常のロシア語のためのパッケージ指定を行えばよい。サンプルを以下に示す。このサンプルでは両方のフォントを使用するため,ファミリ切替え用独自マクロを定義している。

% -*- coding: utf-8; -*-
% Шрифты Хартия, Эвристика 
\documentclass[b5paper]{article}
\usepackage[T2A, T1]{fontenc}
\usepackage[utf8x]{inputenc}
\usepackage[russian]{babel}
\usepackage{Khartiya}%   Хартия fonts
\usepackage{Heuristica}% Эвристика fonts
% macros for change family
\def\famkhartiya{\fontfamily{Khartiya-TLF}\selectfont}%
\def\famheuristica{\fontfamily{Heuristica-TLF}\selectfont}%
\setlength{\textwidth}{240pt}
\begin{document}
\centering{\large Russian autoinst test}
 
\vspace{2em}
\famkhartiya
\noindent Хартия Khartiya
\begin{verse}
Ты проходишь без улыбки,\\
Опустившая ресницы,\\
И во мраке над собором\\
Золотятся купола. 
\end{verse}
\hfill{\it\famkhartiya Александр Блок}
 
\vspace{1.5em}
\famheuristica
\noindent Эвристика Heuristica
\begin{verse}
Ты проходишь без улыбки,\\
Опустившая ресницы,\\
И во мраке над собором\\
Золотятся купола. 
\end{verse}
\hfill{\it Александр Блок}
\end{document}

組版結果は以下のとおり。原稿: autoinst-test.tex, 結果 PDF: autoinst-test.pdf も掲載しておく。両フォントの違いはわかりにくいかも知れない。Хартия は,д と л の形に特徴がある。

autoinst-test.jpg

サーバ機 FreeBSD 8.0-RELEASE にインストールした Emacs 24.0.50 でもロシア語メールを書く必要が発生し,メールエージェント Mew, スペルチェッカ Aspell をセットアップした。前に書いたメモ「Meadow 3.01-dev, GNU Aspell 多言語環境(露・英・仏・独)」に従って Emacs - Aspell 環境を準備したのだが,flyspell-mode (入力の都度スペルチェックが自動で行われるモード) を起動すると,Error: The filter "nroff" does not exists なるエラーが出てスペルチェッカが使えない。

調べたところ,Aspell-0.60.6 では filter-mode がサポートされていて,例えば tex filter を使えば LaTeX の命令のスペルチェックをスキップしてくれるのだが,インストールの仕方によっては nroff などの filter が組込まれないらしい。そのくせ,これを要求しに行って,上記のエラーになったようである。

対策は各種フィルタを付加すること。FreeBSD 8.0-RELEASE で私が Aspell を再導入した場合では,./configure --enable-compile-in-filters で生成した Makefile で組込めば OK になった。

もし同じエラーが出てかつ再インストールが面倒なら,filter 使用設定を外す。すなわち,.emacs の Aspell 起動オプション設定に --mode=none(filter なし)を指定すればよい。以下のように書いておく。

(setq ispell-extra-args '("--sug-mode=ultra" "--encoding=UTF-8" "--mode=none"))

現在の Aspell にどんな filter がインストールされているかは,aspell dump filters とコマンド発行すれば確認できる。私の環境では当初 url filter しか組込まれていなかったが,再インストールで,email, html, sgml, context, url, nroff, tex, texinfo の各種フィルタが認識されるようになった。
 

* * *

Emacs 24.0.50 でメールを書くに際していまひとつ問題があった。fontset-standard で起動してもキリル文字で日本語フォント(要するに全角文字)が拾われて極めてみっともないのだ。なんて Emacs は面倒なんだ!

しようがないので,いちいち set-charset-priority (文字コードの優先順位), set-fontset-font (文字コードに応じたフォント設定) を指示しなければならなかった。フォント名(IPAGothic など)は,fc-list コマンドの出力からユーザの好みのものを指定する。備忘録として .emacs のその部分を掲載しておく。

;;
;; charset priority
;;
(set-charset-priority
 'cyrillic-iso8859-5
 'greek-iso8859-7
 'mule-unicode-0100-24ff
 'japanese-jisx0208
)
;; char width for Mew Summary
;;; iso 8859-5
(map-charset-chars
 (lambda
   (range ignore)
   (set-char-table-range char-width-table range 1))
 'cyrillic-iso8859-5)
;;; iso 8859-7
(map-charset-chars
 (lambda
   (range ignore)
   (set-char-table-range char-width-table range 1))
 'greek-iso8859-7)
 
;;
;; font face
;; - See output of fc-list command for fontname.
;;
(set-face-attribute 'default nil
            :family "DejaVu Sans Mono"
            :height 100)
;; japanese
(set-fontset-font
 (frame-parameter nil 'font)
 'japanese-jisx0208
 '("IPAGothic" . "iso10646-1"))
(set-fontset-font
 (frame-parameter nil 'font)
 'katakana-jisx0201
 '("IPAGothic" . "iso10646-1"))
(set-fontset-font
 (frame-parameter nil 'font)
 'japanese-jisx0212
 '("IPAGothic" . "iso10646-1"))
;; Unicode
(set-fontset-font
 (frame-parameter nil 'font)
 'mule-unicode-0100-24ff
 '("DejaVu Sans Mono" . "iso10646-1"))
;; cyrillic
(set-fontset-font
 (frame-parameter nil 'font)
 'cyrillic-iso8859-5
 '("DejaVu Sans Mono" . "iso10646-1"))
;; greek
(set-fontset-font
 (frame-parameter nil 'font)
 'greek-iso8859-7
 '("DejaVu Sans Mono" . "iso10646-1"))

MusiXTeX in Russian

|

先日,楽譜組版 TeX パッケージ MusiXTeX の Mac OS X Snow Leopard への導入について書いたとき,ロシア語を出力することについて少し触れた。今日はもう少し詳細にその方法についてメモをしるしておく。

MusiXTeX は Plain TeX でコンパイルできるのだが,標準では 8 bit キリル文字の入力も出力も受け付けない。キリル組版用にフォーマットファイルを生成し,これを用いて MusiXTeX の .tex ファイルを処理する必要がある。このためには Cyrillic t2 パッケージ(CTAN:macros/latex/contrib/t2/)及び ec-plain パッケージ(CTAN:macros/ec-plain/)が必要である。前者は ptexlive には初期導入されている。これらを TeX ツリー(plain-TeX から参照できる $TEXMF/tex/generic/ あたり)にインストールしておく。

キリル組版用フォーマットファイル cyrtex.fmt を生成する訳であるが,使用するキリルフォントに応じて cyrtex.cfg を修正しておく。デフォルトだと LH LCY フォントを使用する設定になっているが,LCY はどうも Type1 フォントも見当たらないし,私は LH T2A 用のフォントを使うように変更した。つまり,cyrtex.cfg をカレントディレクトリにコピーして来て,これのはじめのほうにあるフォントエンコーディング選択の指定において,\c lh/lcy/lcydefs/cm/cyrcmfnt をコメントアウトし,かつ \c la/t2a/txxdefs/ex/cyrecfnt を活かすように訂正する。変更したら,cyrtex.fmt を生成する。

% cp `kpsewhich cyrtex.cfg` .  (cyrtex.cfg をカレントにコピー) 
% emacs cyrtex.cfg &  (Emacs で cyrtex.cfg を訂正)
% tex -ini -fmt=cyrtex cyrtex.ini  (フォーマットファイル生成)

MusiXTeX プリプロセス原稿 PMX ファイルには,以下のようなコードを冒頭のマクロ定義のところ(--- で囲んで定義するところ)に書いておく。

---
% font definitions for cyrillic
% 8pt roman, bold, and italic 
\font\eightrm=larm0800 % at 8pt\
\font\eightbf=labx0800 % at 8pt\
\font\eightit=lati0800 % at 8pt\
% 9pt
\font\ninerm=larm0900 % at 9pt\
\font\ninebf=labx0900 % at 9pt\
\font\nineit=lati0900 % at 9pt\
% 10pt
\font\tenrm=larm1000\
\font\tenbf=labx1000\
\font\tenit=lati1000\
% 12pt
\font\twelverm=larm1200 % scaled \magstep 1\
\font\twelvebf=labx1200 % scaled \magstep 1\
\font\twelveit=lati1200 % scaled \magstep 1\
% Large fonts for titles : normal shaped Times-Roman fonts are applied
\font\bigfont=labx1440 % scaled \magstep2, 14pt\
\font\Bigfont=labx1728 % scaled \magstep3, 17pt\
\font\BIgfont=labx2074 % scaled \magstep4, 20pt\
\font\BIGfont=labx2488 % scaled \magstep2, 25pt\
% inputenc
\input plainenc\relax\inputencoding{koi8-r}\
...
---

これは MusiXTeX が要求する文字組版用フォント一式を LH T2A cmr に割り当てる定義である。また,最後の \input 行は,原稿の文字コードを KOI8-R とすることを示す。ロシア語テキストを Windows CP1251 で作成するなら,\inputencoding の引数に cp1251 を指定しなければならない。UTF-8 は処理できない。

さて,以上のような前振りをした上で PMX 原稿の楽曲部分を準備する。今回,ロシア語を含む MusiXTeX 組版例として,ドミトリ・ショスタコーヴィチ作曲『弦楽四重奏曲第 13 番変ロ短調作品 138』第一楽章冒頭を作成してみた。この曲はショスタコーヴィチの弦楽四重奏曲のなかで私がもっとも愛するもの。ヴィオラのモノローグの悲痛な作曲者最晩年の作品である。ウェーベルンの楽譜と比べるとかなりシンプルなので,40 小節近くを結構ラクにコーディングできた。参照した市販のスコアは Dmitri Schostakowitsch STREICHQUARTETTE op. 138 / 142 / 144, Musikverlag Hans Sikorski, Hamburg, 1978 である。この市販スコアでは表題はドイツ語なんだけど,今回の例のために私はロシア語にして組んだ。PMX 原稿 shostako_op138.pmx を掲載しておく。これを次のようにして処理する。cyrtex.fmt がカレントディレクトリにあるものとする。

% ls
cyrtex.fmt              shostako_op138.pmx
% pmxab shostako_op138
% tex -fmt=cyrtex shostako_op138
% musixflx shostako_op138
% tex -fmt=cyrtex shostako_op138
% dvips -Ppdf shostako_op138.dvi -o
% ps2pdf -sPAPERSIZE=a4 shostako_op138.ps shostako_op138.pdf

組版結果の一部は図 1 のとおり。処理結果 PDF: shostako_op138.pdf も掲載しておく。

shostako_op138.jpg

図 1. MusiXTeX 組版結果

ショスタコーヴィチの弦楽四重奏曲第 13 番作品 138 を収録した CD も挙げておく。ロシア現代音楽を得意とするブロツキイ四重奏団による演奏である。
 

MusiXTeX 楽譜の組版

|

世の中には,己の好きなことのためにはどんな困難をも克服してしまう人がいるものである。ミュージック・スコア・タイプセット・パッケージ MusiXTeX をはじめて知ったとき思ったのは,まずこのことだった。TeX でオーケストラの総譜を組もうというのだから。しかも,組版品質がまったく美しいというほかないのだから。TeX の可能性に驚いてしまうのである。

MusiXTeX は大部の英文マニュアルをみてすぐわかるとおり,奇妙キテレツ・面倒な書法を習得しなければならない。少しでも簡単に,効率よく MusiXTeX コードを入力したいという目的で PMX や M-Tx といったプリプロセッサが開発されている。PMX は MIDI データを同時生成できるほか,scor2prt というパート譜生成のユーティリティをも備えている。M-Tx は MusiXTeX プリプロセッサ PMX のさらなるプリプロセッサであり(!),歌詞パートを効率よく記述できる。MusiXTeX, PMX, M-Tx の紹介,インストール方法,関連リンクについては,「TeX wiki 楽譜」が手頃な解説である。しかしながら MusiXTeX のマニュアルをきちんと読んでその仕様を理解していないと,少し特殊なことをやろうとすれば PMX, M-Tx の記法だけではまったく対処できない。

Mac OS X Snow Leopard に MusiXTeX T.114, PMX-2.5.15, M-Tx-0.60 をインストールした。コンパイルしてバイナリを生成する以外は,通常の LaTeX パッケージの設置と変わらない。マクロ関連ファイルは $TEXMF/tex/generic/musixtex/ ディレクトリに集めておくのがよい。バイナリ生成がいちばんやっかいなので少しだけ触れておく。コンパイルで,PMX は Fortran77 (gfortran, g77, f77) を,M-Tx は Free Pascal (fpc) を要求する。私は Mac OS X 用の gfortran を「High Performance Computing for Mac OS X」から,Free Pascal を「Free Pascal - Advanced open source Pascal compiler for Pascal and Object Pascal」から入手して組み込んだ。Fortran, Pascal を使うあたり,かつてコンピュータで音楽をやろうとした人の個性が偲ばれる。PMX は,アーカイブ展開ディレクトリ直下で make FC=gfortran,M-Tx は prepmx ディレクトリ下で make とすればコンパイルが実行される。MusiXTeX 付属のフォーマッタ musixflx は MusiXTeXDistribution/system/musixflx/c-source ディレクトリにおいて,C/C++ コンパイラを用いて cc -g -o musixflx musixflx.c としてバイナリを生成すればよい。こうして生成した実行形式 pmx, pmxab, scor2prt (以上 PMX), prepmx (M-Tx), musixflx (MusiXTeX) をパスの通った場所にコピーしておく。

アントン・ウェーベルンが 1909 年に書いた Der deutsche Expressionismus の傑作『弦楽四重奏のための五つの楽章作品 5』第 1 楽章冒頭を,PMX - MusiXTeX で組んでみた。参照したスコアは,ANTON WEBERN Fünf Sätze für Streichquartett OP.5, Philharmonia Partituren No. 358, Universal Edition, Wien である。"col legno" をどうコーディングするかマニュアルにはなかったので,オクターブ記号出力マクロを少し手直しした。ドイツ語は Latin-1 で直接書いて,Cyrillic t2 パッケージ添付 plainenc.tex を \input して 8 bit 処理した。cyrtex.ini を用いてダンプした plain TeX フォーマットファイル (cyrtex.cfg を適切に編集し,tex -ini -fmt=cyrtex cyrtex.ini で生成した cyrtex.fmt) を使えば,ロシア語入りスコアも作成できる。t2 パッケージは ptexlive に初期導入されている。UTF-8 なら日本語混在でも組めると思うけれども,その方法は調査中である。日本語だけの UTF-8 原稿なら,ptex -kanji=utf8 でコンパイルすればよい。ウェーベルン弦楽四重奏の組版では,フォントはデフォルトのコンピュータモダンを使用したが,\font\ninerm=ptmr7t at 9pt\ のように PMX 原稿のはじめのほうで(--- の間に)宣言しておけば,Times 等別の書体で出力できる(MusiXTeX T.114 マニュアル pp. 61--2 を参照)。以下のようなオペレーションで PMX 原稿 (webern_op5.pmx) から PDF を生成した。dvipdfmx だとスラーで PostScript エラーが出て出力できなかったので,dvips, ghostscript (ps2pdf) を使った。

% pmxab webern_op5
% tex webern_op5
% musixflx webern_op5
% tex webern_op5
% dvips -Ppdf webern_op5.dvi -o
% ps2pdf -sPAPERSIZE=a4 webern_op5.ps webern_op5.pdf

PMX 原稿 webern_op5.pmx 及び組版結果 webern_op5.pdf を掲載しておく。組版結果は図 1 のとおり。図 2 市販スコア(墺 PHILHARMONIA PARTITUREN)と比べると,私の調整がまだまだ足りない訳だけれども,なかなかの出来ではないだろうか。

webern_op5.jpg

図 1. MusiXTeX 組版結果

webern_op5_scan.jpg

図 2. 市販スコア

私は最初の 3 小節でくたびれた。MusiXTeX で総譜を組むのは,よほどの熟練と根気が必要である。Rosegarden などの楽譜専用エディタには MusiXTeX のコードをエクスポートするものもあり,そちらを使うのがよさそうである。トレモロやハーモニクス等の特殊奏法の記述は MusiXTeX マクロを熟知しないと実現できないだろう。一方,MusiXTeX は,現代音楽の凝った記法を含めると,プロフェショナルな業界ではグローバルスタンダードになっているミュージック・エディタ Sibelius には機能的にも劣るだろう。それでも,楽曲の主題を論文に引用するために使う程度なら,MusiXTeX の機能で充分であり,譜表のコーディングも PMX, M-Tx を活用すればそれほど難しくないはずである。

PMX, M-Tx のマニュアルは,それぞれ,pmx250.pdf, mtx060.pdf を参照。また,Cornelius Noack 氏による "Typesetting music with PMX" は,PMX のチュートリアル,テクニックを豊富なサンプルとともに解説した手引書であって,必携のドキュメントである。

kern.maxfiles

|

最近,FreeBSD の security run output に "+kern.maxfiles limit exceeded by uid 80, please see tuning(7)." なるメッセージを出して httpd がアボートした旨の履歴が頻繁に通知されるようになった。このメッセージは,要するにシステムで参照可能なファイルディスクリプタ数を超過したということらしい。サーバは 500GB の HDD を内蔵しており,ここにこのブログの戯言記事やら,Web 公開コンテンツ,受発信電子メールのみならず,エッチ動画やら私の日頃の煩悩の求めるところのゴミデータもが大量に集積されていて,格納ファイルはただならぬ数に昇っているはずである。さもありなん。もしかすると,サーバ攻撃に晒された影響かも知れない。/phpmyadmin/scripts/setup.php 等の脆弱性に依った php アタックが頻発しているのは,apache22 のログからかねてから知っていた。まあ,Web サーバはとくに大きな支障無く動作しているようなので,放置してもよかったのだが気持ち悪いので少し手を加えることにした。

ファイルディスクリプタが足りないということなので,それを増やしてやる。リブートはなかなかする気になれないので,さしあたり root 権限でコマンドラインから kern.maxfiles の数を増やしてやる。sysctl kern.maxfiles とやると,現在の設定値が表示される。FreeBSD 8.0-RELEASE の場合,12288 だったと思う(控えておくのを忘れた)。これを 65536 に拡張した: sysctl kern.maxfiles=65536。次にサーバを再起動した際にもこれが活きるよう,/etc/sysctl.conf にも kern.maxfiles=65536 の一行を書き足しておいた。

昨日上記対策を行って,昨夜の security run output を確認したが,エラーメッセージは出ていなかった。もし,サーバ・アタックの影響だとしたら,もっと別の構造的要因を探る必要があり,上記のような何倍かに設定値を拡張するような小手先の対策では追い付かないかも知れない。しばらく様子を見ることとする。

Moon Calendar

Profile

ISAO。システムエンジニア。昭和 30 年代を懐かしむオヤジ。ロシアに興味があります。
[more], [About our site]

Notice

この文書はフィクションであり,実在する個人,団体等とは一切関係ありません。

文書の記述内容は無保証です。不適切な表現があればコメントにてご指摘ください。

コメント,トラックバックは,管理者承認を経て公開となります。公序良俗に反すると判断されると,断りなく削除される場合があります。

Links

About this archive

All Entries of Category 文房清玩

Previous: 政治・動物園

Next: 日曜大工

Recent Entries in Main Index.
All Entries in Archive Index.

Web Pages

Powered by Movable Type 4.1