#title(Visual Studio International Pack: Japanese Kana Conversion Libraryを使う)

#navi(.NETプログラミング研究)

#contents

*Visual Studio International Pack: Japanese Kana Conversion Libraryを使う [#h4d0ffda]

**Visual Studio International Packとは? [#qd83a81b]

Visual Studio International Packはマイクロソフトが配布しているライブラリとコントロールです。日本語等の特有の問題を解決するための機能を提供します。

現在のバージョンである1.0では、以下の7つの機能を提供します。(リリースノートからの抜粋)

-East Asia Numeric Formatting Library(東アジアのための数値フォーマットライブラリ)~
East Asia Numeric Formatting Libraryは数値データを日本語、繁体字中国語、簡体字中国語および韓国語における漢数字の文字列に変換するためのクラスライブラリを提供します。
-Japanese Kana Conversion Library(日本語かな変換ライブラリ)~
かな文字セットを別のかな文字セットに変換するための一連のクラスです。クラスライブラリで使用されている状態機械の設定を変更することにより、テキストストリームの翻字変換方法を指定することができます。ひらがな、カタカナ、半角カタカナの相互変換、およびローマ字の変換ができます。
-Japanese Text Alignment Library(日本語テキスト整列ライブラリ)~
日本固有の均等割付を用いて文字列を描画するためのライブラリを提供します。
-Japanese Yomi Auto-Completion Library(日本語読みがなオートコンプリートライブラリ)~
日本語IME における読みの入力に対応したオートコンプリート機能を提供するライブラリとサンプルのTextBox コントロールを提供します。このライブラリは日本語IMEがインストールされ有効になっている場合にのみ動作します。
-Korean Auto Complete TextBox Control(韓国語オートコンプリート対応TextBoxコントロール)~
韓国語入力に対応したオートコンプリート機能を持つTextBox コントロールを提供します。
-Simplified Chinese Pin-Yin Conversion Library(簡体字中国語Pin-Yin変換ライブラリ)~
簡体字中国語で一般的に用いられるPolyphone、Homophone、Pinyin や画数などの文字のプロパティを取得するためのAPIを提供します。
-Traditional Chinese to Simplified Chinese Conversion Library and Add-In Tool(繁体字中国語と簡体字中国語間の双方向変換ライブラリおよびアドインツール)~
繁体字中国語と簡体字中国語の間の双方向変換を容易にするクラスライブラリを提供します。変換にはOffice 2007で提供される単語の1対1置き換えによる繁体字中国語と簡体字中国語の変換エンジンを利用しています。このコンポーネントには、簡体字中国のリソースファイルを繁体字中国語に変換するための、Visual Studio 統合開発環境用アドインツールが含まれます。

Visual Studio International Pack 1.0のシステム要件は以下の通りです。(リリースノートからの抜粋)

-Microsoft Visual Studio 2005 または Microsoft Visual Studio 2008 
-Microsoft Office 2007~
Traditional to Simplified Chinese Conversion Library and Add-In Toolのために必要になります。他のコンポーネントのみを使用の場合には必要ありません。より良い変換結果を得るためには、Microsoft Office 2007を同じマシンにインストールしてください。 

この内、今回は、Japanese Kana Conversion Library(日本語かな変換ライブラリ)の使い方を紹介します。

**ダウンロードとインストール [#j7703ae1]

Japanese Kana Conversion Libraryをインストールする手順は以下の通りです。

+「[[Microsoft Visual Studio International Pack 1.0 ダウンロード>http://www.microsoft.com/downloads/details.aspx?FamilyID=f9cfc884-1f00-45fa-b2fb-303d9e110bc7&DisplayLang=ja]]」からvsintlpack1.zipをダウンロードする。
+vsintlpack1.zipを展開する。
+7つのmsiファイルが出来るが、"JPNKanaConv.msi"を実行し、インストールする。
+プログラムメニューの「Microsoft Visual Studio International Pack v1.0」にヘルプへのショートカットが作成される。

**参照の追加 [#s794b7fe]

インストールしたライブラリを使用するには、「JpnKanaConversion.dll」と「JpnKanaConvHelper.dll」をプロジェクトの参照に追加する必要があります(ただし、TransliteralConverterクラスだけを使うのであれば、「JpnKanaConversion.dll」だけで十分です)。これらのDLLはインストールしたフォルダにあり、デフォルトでは"C:\Program Files\Microsoft Visual Studio International Pack\Japanese Kana Converter Library"というフォルダです。

DLLを参照に追加する具体的な方法は、「[[「○○○.dllを参照に追加します」>http://dobon.net/vb/dotnet/help/addreference.html]]の意味は?」をご覧ください。
DLLを参照に追加する具体的な方法は、「[[「○○○.dllを参照に追加します」>https://dobon.net/vb/dotnet/help/addreference.html]]の意味は?」をご覧ください。

**Japanese Kana Conversion Libraryの機能 [#v6e6dfdf]

Japanese Kana Conversion Libraryは大きく分けて2つの機能を提供します。1つは、ひらがな、カタカナ、半角カタカナ、ローマ字の変換です。もう一つは、独自の変換ルールに基づく変換です。前者はKanaConverterクラスを使用し、後者はTransliteralConverterクラスを使用します。KanaConverterクラスの使用はとても簡単で、お手軽です。一方TransliteralConverterクラスを使う変換は非常に面倒ですが、KanaConverterクラスで出来ない変換が可能になります。また、TransliteralConverterクラスによる変換は、日本語以外の変換にも使用できます。

**KanaConverterクラス [#e61c370d]

KanaConverterクラスには次の7つの静的メソッドがあります。

|メソッド名|説明|h
|HalfwidthKatakanaToHiragana|半角カタカナからひらがなへ文字を変換します。|
|HalfwidthKatakanaToKatakana|半角カタカナからカタカナへ文字を変換します。|
|HiraganaToHalfwidthKatakana|ひらがなから半角カタカナへ文字を変換します。|
|HiraganaToKatakana|ひらがなからカタカナへ文字を変換します。|
|KatakanaToHalfwidthKatakana|カタカナから半角カタカナへ文字を変換します。|
|KatakanaToHiragana|カタカナからひらがなへ文字を変換します。|
|RomajiToHiragana|ローマ字からひらがなへ文字を変換します。|

ぞれぞれのメソッドを使用した例を以下に示します。

#code(vbnet){{
'半角カタカナをひらがなに変換する 
Dim str1 As String = "アボカド"
Dim ret1 As String = Microsoft.International.Converters.KanaConverter. _
    HalfwidthKatakanaToHiragana(str1)
Console.WriteLine(ret1)
'"あぼかど"と表示される 

'半角カタカナをカタカナに変換する 
Dim str2 As String = "アボカド"
Dim ret2 As String = Microsoft.International.Converters.KanaConverter. _
    HalfwidthKatakanaToKatakana(str2)
Console.WriteLine(ret2)
'"アボカド"と表示される 

'ひらがなを半角カタカナに変換する 
Dim str3 As String = "あぼかど"
Dim ret3 As String = Microsoft.International.Converters.KanaConverter. _
    HiraganaToHalfwidthKatakana(str3)
Console.WriteLine(ret3)
'"アボカド"と表示される 

'ひらがなをカタカナに変換する 
Dim str4 As String = "あぼかど"
Dim ret4 As String = Microsoft.International.Converters.KanaConverter. _
    HiraganaToKatakana(str4)
Console.WriteLine(ret4)
'"アボカド"と表示される 

'カタカナを半角カタカナに変換する 
Dim str5 As String = "アボカド"
Dim ret5 As String = Microsoft.International.Converters.KanaConverter. _
    KatakanaToHalfwidthKatakana(str5)
Console.WriteLine(ret5)
'"アボカド"と表示される 

'カタカナをひらがなに変換する 
Dim str6 As String = "アボカド"
Dim ret6 As String = Microsoft.International.Converters.KanaConverter. _
    KatakanaToHiragana(str6)
Console.WriteLine(ret6)
'"あぼかど"と表示される 

'ローマ字をひらがなに変換する 
Dim str7 As String = "abokado"
Dim ret7 As String = Microsoft.International.Converters.KanaConverter. _
    RomajiToHiragana(str7)
Console.WriteLine(ret7)
'"あぼかど"と表示される 
}}

#code(csharp){{
//半角カタカナをひらがなに変換する
string str1 = "アボカド";
string ret1 = Microsoft.International.Converters.
    KanaConverter.HalfwidthKatakanaToHiragana(str1);
Console.WriteLine(ret1);
//"あぼかど"と表示される

//半角カタカナをカタカナに変換する
string str2 = "アボカド";
string ret2 = Microsoft.International.Converters.
    KanaConverter.HalfwidthKatakanaToKatakana(str2);
Console.WriteLine(ret2);
//"アボカド"と表示される

//ひらがなを半角カタカナに変換する
string str3 = "あぼかど";
string ret3 = Microsoft.International.Converters.
    KanaConverter.HiraganaToHalfwidthKatakana(str3);
Console.WriteLine(ret3);
//"アボカド"と表示される

//ひらがなをカタカナに変換する
string str4 = "あぼかど";
string ret4 = Microsoft.International.Converters.
    KanaConverter.HiraganaToKatakana(str4);
Console.WriteLine(ret4);
//"アボカド"と表示される

//カタカナを半角カタカナに変換する
string str5 = "アボカド";
string ret5 = Microsoft.International.Converters.
    KanaConverter.KatakanaToHalfwidthKatakana(str5);
Console.WriteLine(ret5);
//"アボカド"と表示される

//カタカナをひらがなに変換する
string str6 = "アボカド";
string ret6 = Microsoft.International.Converters.
    KanaConverter.KatakanaToHiragana(str6);
Console.WriteLine(ret6);
//"あぼかど"と表示される

//ローマ字をひらがなに変換する
string str7 = "abokado";
string ret7 = Microsoft.International.Converters.
    KanaConverter.RomajiToHiragana(str7);
Console.WriteLine(ret7);
//"あぼかど"と表示される
}}

***RomajiToHiraganaメソッド [#aff702b0]

RomajiToHiraganaメソッドで変換されるローマ字の規則は、IMEのローマ字かな変換で使われる変換に近く、一般的なローマ字の規則の幾つかは無視されます。例えば、文化庁のサイトにある「[[ローマ字のつづり方 そえがき>http://www.bunka.go.jp/kokugo/main.asp?fl=show&id=1000001798&clc=1000000068&cmc=1000003935&cli=1000005416&cmi=1000005418]]」の2と4項にあるルール(「はねる音を表わすnと次にくる母音字またはyとを切り離す必要がある場合には、nの次に'を入れる。」と「長音は母音字の上に^をつけて表わす。なお、大文字の場合は、母音字を並べてもよい。」)は無視されます。また、ヘボン式の規則である、b、m、pの前では「ん」をmで表記したり、cの前では「っ」をtで表記するといった規則を使ったローマ字は正しく変換できませんでした。また、"ゐ"に変換するには"wyi"、"ゑ"に変換するには"wye"とします。"wi"は"うぃ"に、"we"は"うぇ"になります。

なお、RomajiToHiraganaメソッドが用いる変換表は、ヘルプのRomajiToHiraganaメソッドのページにあります。

***VB.NETのStrConv関数との違い [#jf6c2975]

VB.NETのStrConv関数でも、全角と半角の変換や、ひらがなとカタカナの変換ができます。KanaConverterクラスはStrConv関数と違い、半角カタカナのみを全角に、あるいは全角カタカナやひらがなのみを半角カタカナに変換することが出来ます。

「[[ディベロッパー製品開発統括部 Blog : KanaConverterの使い方>http://blogs.msdn.com/dd_jpn/archive/2008/01/31/7346681.aspx]]」によると、これ以外にも濁点、半濁点の変換で違いが出るようです。StrConvでは結合文字であるU+3099(COMBINING KATAKANA-HIRAGANA VOICED SOUND MARK)の濁点を正しく変換できませんが、KanaConverterクラスではできます。半濁点の結合文字であるU+309A(COMBINING KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK)についても同様です。

#code(vbnet){{
Dim str1 As String = "か" & [Char].ConvertFromUtf32(&H3099)

'StrConvでカタカナに変換 
Dim ret1 As String = StrConv(str1, VbStrConv.Katakana, &H411)
Console.WriteLine(ret1)
'"カ?"と表示される 

'KanaConverterでカタカナに変換 
Dim ret2 As String = Microsoft.International.Converters.KanaConverter. _
    HiraganaToKatakana(str1)
Console.WriteLine(ret2)
'"ガ"と表示される 
}}

#code(csharp){{
//注意: 参照設定に"Microsoft.VisualBasic.dll"を追加する必要があります

string str1 = "か" + Char.ConvertFromUtf32(0x3099);

//StrConvでカタカナに変換
string ret1 = Microsoft.VisualBasic.Strings.StrConv(
    str1, Microsoft.VisualBasic.VbStrConv.Katakana, 0x411);
Console.WriteLine(ret1);
//"カ?"と表示される

//KanaConverterでカタカナに変換
string ret2 = Microsoft.International.Converters.
    KanaConverter.HiraganaToKatakana(str1);
Console.WriteLine(ret2);
//"ガ"と表示される
}}

一方単独の全角の濁点である「゛」(U+309B)と半濁点である「゜」(U+309C)を半角に変換しようとすると、StrConvでは変換されますが、KanaConverterクラスでは変換されません。

半角の濁点である「゙」(U+FF9E)と半濁点である「゚」(U+FF9F)を全角に変換しようとすると、濁点(あるいは半濁点)をつけることが出来る文字の後に濁点があるときは、StrConvとKanaConverterのどちらでも変換できます(この時、1文字の濁音の全角となります)。それ以外では、StrConvでは全角に変換されますが、KanaConverterでは変換されません。

また、KanaConverterクラスではカタカナの"ヷヺ"("\U30F7\U30FA")と半角カタカナの"ヷヺ"の相互変換が可能ですが、StrConvでは出来ません。

その他、半角カナである「。「」、・ー」の全角への変換は、StrConvでは行われますが、KanaConverterクラスでは行われません。

**KanaConverterクラスの不具合と回避法 [#z79fee58]

KanaConverterクラスを使った変換は、後述するTransliteralConverterクラスにより行われます。変換ルールはXMLで記述されており、KanaConverterクラスのそれぞれのメソッドに用意されています。このXMLはヘルプに載っており、それぞれのメソッドの説明ページからリンクされています。このXMLを眺めていたところ、幾つか間違いを見つけましたので、問題になりそうな箇所を紹介します(問題がない部分も一応紹介しておきます)。

なお下の説明で、例えば「"ウカキクケコサシスセソタチツテトワヲ"の後に...」と書いているのは、「"ウカキクケコサシスセソタチツテトワヲ"のいずれかの文字の後に...」という意味です。

***HalfwidthKatakanaToHiraganaメソッド [#l4ea6af2]

-"ウカキクケコサシスセソタチツテトワヲ"の後に"゚"が来ると文字が消える。
-"ワヲ"の後に"゙\U3099"が来ると文字が消える。

***HalfwidthKatakanaToKatakanaメソッド [#q76721ad]

-"ウカキクケコサシスセソタチツテトワヲ"の後に"゚"が来ると文字が消える。

***HiraganaToHalfwidthKatakanaメソッド [#pfd3a063]

-"うかきくけこさしすせそたちつてとわを"の後に"はひふへほ"が来ると、その後に"\U3099\U309A"が来ても濁点、半濁点に変換されない。
-"はひふへほ"の後に"うかきくけこさしすせそたちつてとわを"が来ると、その後に"\U3099"が来ても濁点に変換されない。
-"ヴ"を半角に変換してしまう。(私が知らないだけで、ひらがなの"ヴ"があるのだろうか?)
-不具合は生じないが、"ゐゑゝゞ\U3095\U3096"(\U3095と\U3096「か」と「け」の小書き)は変換できないのにCharSetに入っている。(CharSetの意味がよく分かっていないので、間違っていないのかもしれないが...。)

***HiraganaToKatakanaメソッド [#n56e49d1]

-"うかきくけこさしすせそたちつてとわゐゑをゝ"の後に"はひふへほ"が来ると"はひふへほ"が変換されない。
-不具合は生じないが、"ヴ"を"ヴ"に変換している。(ひらがなの"ヴ"があるのだろうか?)

***KatakanaToHalfwidthKatakanaメソッド [#d81ac235]

-"ウカキクケコサシスセソタチツテトワヲ"の後に"ハヒフヘホ"が来ると、その後に"\U3099\U309A"が来ても濁点、半濁点に変換されない。
-"ハヒフヘホ"の後に"ウカキクケコサシスセソタチツテトワヲ"が来ると、その後に"\U3099"が来ても濁点に変換されない。

***KatakanaToHiraganaメソッド [#nd4837d2]

-"ウカキクケコサシスセソタチツテトヽ"の後に"ハヒフヘホ"が来ると、その後に"\U3099\U309A"が来ても濁点、半濁点が付かない。
-"ハヒフヘホ"の後に"ウカキクケコサシスセソタチツテトヽ"が来ると、その後に"\U3099"が来ても濁点に変換されない。
-不具合ではなく仕様だと思うが、"ヷヺ"を変換しない。

***RomajiToHiraganaメソッド [#i5e1675f]

設定が複雑すぎるため、調べていません。

***修正した構成ファイル [#yba8a063]

上記の不具合を修正したXMLファイルを下に置いておきます(仕様と思われる部分は修正していません)。このファイルを使って変換する方法は、後述するTransliteralConverterクラスの説明をご覧ください。

|メソッド名|ファイル名|h
|HalfwidthKatakanaToHiragana|&ref(HalfwidthKatakanaToHiragana.xml);|
|HalfwidthKatakanaToKatakana|&ref(HalfwidthKatakanaToKatakana.xml);|
|HiraganaToHalfwidthKatakana|&ref(HiraganaToHalfwidthKatakana.xml);|
|HiraganaToKatakana|&ref(HiraganaToKatakana.xml);|
|KatakanaToHalfwidthKatakana|&ref(KatakanaToHalfwidthKatakana.xml);|
|KatakanaToHiragana|&ref(KatakanaToHiragana.xml);|

**TransliteralConverterクラス [#x18c1335]

注意:TransliteralConverterクラスの使い方については、情報がほとんどありません。ヘルプにも説明がほとんどないため、正直使い方が良く分かりません。よってここに書く説明のほとんどは私の想像であり、正しいかどうか分かりません(ある程度は検証していますが)。面倒なので断定口調で書いていますが、正しいという保障は出来ません。間違いを発見された方は、このページの下にあるコメント欄でご報告ください。

TransliteralConverterクラスでは、XMLで記述された設定に従って文字列の変換を行います。そのため、KanaConverterクラスと違い、独自の設定による変換が出来ます。

TransliteralConverterクラスで使用するXMLのスキーマは以下の通りです。(ヘルプからの抜粋)

#pre{{
<AutoConverterConfig>
  <StateMachineConfig>
    <State>
      <StateTransition>
        <InputValidatiors>
          <Regex>
        <Actions>
          <Action>
  <ConversionTable>
    <Conversion>
}}

各要素の意味は、次の通りです。(ヘルプを基に、一部改変、加筆しています。)何を言っているのか分からないという部分がほとんどだと思いますが、今は読み流して、サンプルをご覧いただいた後でもう一度ご覧ください。

#insertblock(StateMachineConfig){{
|属性|説明|h
|EntryState|エントリ状態(スタート状態のID)を指定します。|
|CharSet|変換できる有効な文字をすべて指定します。(スタート状態のときInputValidators要素と一致する全ての文字を指定するのではないかと思われるが、詳細は不明。)|
}}

#insertblock(State){{
|属性|説明|h
|ID|状態の一意のIDを指定します。|
}}

#insertblock(StateTransition){{
|属性|説明|h
|ID|次の状態のIDを指定します。同じIDのStateTransitionが複数存在できます。|
}}

#insertblock(Conversion){{
|属性|説明|h
|Input|変換元の文字列です。大文字と小文字を区別しません。|
|Output|変換後の文字列です。|
}}

#insertblock(Actions){{
|動作|説明|h
|Append(char)|"char"で指定されている文字をバッファの末尾に追加します。例えば、"Append(a)"とすると、バッファに"a"が追加されます。|
|AppendInput|現在の入力文字をバッファの末尾に追加します。|
|ConvertToOutput|バッファの文字をConversionTableを基に変換して出力します。バッファと同じ文字列がConversionTableで見つからなかったときは、何も出力しません。|
|Clear|バッファをクリアします。|
}}

#insertblock(,%){{
|要素|意味|h
|AutoConverterConfig|構成ファイルのルート要素です。|
|StateMachineConfig|状態マシンの構成です。%StateMachineConfig%|
|State|状態マシンの状態です。%State%|
|StateTransition|今の状態から別の状態へ変更します。%StateTransition%|
|InputValidators|入力チェック用の複数の正規表現です。現在の文字がすべての<Regex>要素の正規表現に一致したときに、状態マシンは要素<Actions>で指定した動作を実行します。((ヘルプでは「入力チェック用正規表現はいくつがあります。設定する正規表現のいずれかに一致すれば、状態マシンは要素<Actions>で指定した動作を実行します。」となっており、OR条件のように書かれていますが、実際にはANDのようです。))|
|Regex|入力チェック用正規表現です。|
|Actions|状態マシンが実行する複数の動作です。|
|Actions|状態マシンがバッファに対して実行するひとつの動作です。サポートしている動作は以下の通りです。%Actions%|
|ConversionTable|<Conversion>要素を含んでいます。|
|Conversion|変換元のユニットと変換先の文字セットを表示するペアの文字列です。%Conversion%|

&shiftnote(nohr);
}}

XMLの設定を使ってTransliteralConverterクラスがどのように変換を行うのか、その手順を示します。(この部分はまさに想像です。)これもとりあえずは読み流し、大まかな点をご理解いただければ結構です。

+現在の状態をStateMachineConfig要素のEntryState属性で指定されている値(スタート状態((現在の状態がEntryStateのとき「スタート状態」(または「エントリ状態」)と呼ばれる。現在の状態がどのようにしてEntryStateと同じになったかは関係ない。)))にする。
+入力ストリームから次の1文字を取得し、現在の文字とする。取得できなければ(全て読みきったならば)、バッファを変換、出力((詳細は不明だが、バッファと一致する変換がConversionTableにあれば変換し、なければそのまま出力する。))、終了する。
+現在の状態と同じID属性を持つState要素内にあるStateTransition要素のうち、現在の文字がInputValidatorsで指定されている正規表現と一致するものを探す。見つかれば5.へ。見つからなければ、4.へ。
+この部分で何をしているか、詳細は不明。だが、大体以下のようなことを行っているような感じ。((このあたりでCharSet属性がかかわってくるようだが、どのようにかかわっているかは不明。ただ、例えば"a"を"あ"に、"ka"を"か"に変換するとき、CharSet属性に"k"を指定していないと、"kka"を"kkあ"と変換されてしまう。))
++バッファが空ならば、現在の文字をそのまま出力して1.に戻る。
++バッファが空でなければ、そのはじめの文字をConversionTableに従って変換して出力する。ConversionTableで変換できなければ、そのまま出力する。
++バッファの先頭の文字を削除した文字列を現在の文字の前に挿入して(バッファはクリア)、その先頭の文字を現在の文字(バッファが1文字しかなかったときは、現在の文字がそのまま)として、現在の状態をスタート状態にして、3.に戻る。
+Actions要素で指定されている動作を実行する。Actionsでは、4つの動作を指定できる。AppendInputは、現在の文字をバッファに追加する。ConvertToOutputは、バッファ内の文字列をConversionTable要素で指定された変換に従って変換し、出力する。Clearは、バッファをクリアする。Append(char)は、"char"で指定された文字をバッファに追加する。
+現在の状態を、StateTransition要素のID属性で指定されている値に変更する。
+2.に戻る。

&shiftnote(nohr);

***最も単純な変換の例: 文字を文字列に変換する [#g1ff9ab6]

まずは最も簡単な変換の例を示します。ここでは、「aiueo」を「あいうえお」に変換できるようにします。

まずは次のようなXMLファイル(構成ファイル)を作成します。ファイル名は"TransliteralConverter.xml"とし、実行ファイルと同じフォルダに入れてください(Visual Studioでは、XMLファイルのプロパティの「出力ディレクトリにコピー」を「コピーしない」以外にすると良いでしょう)。

#code(xml){{
<?xml version="1.0" encoding="utf-8" ?>
<AutoConverterConfig>
  <StateMachineConfig EntryState="0" CharSet="[aiueo]">
    <State ID="0">
      <StateTransition ID="0">
        <InputValidators>
          <Regex>[aiueo]</Regex>
        </InputValidators>
        <Actions>
          <Action>AppendInput</Action>
          <Action>ConvertToOutput</Action>
          <Action>Clear</Action>
        </Actions>
      </StateTransition>
    </State>
  </StateMachineConfig>
  <ConversionTable>
    <Conversion Input="a" Output="あ"/>
    <Conversion Input="i" Output="い"/>
    <Conversion Input="u" Output="う"/>
    <Conversion Input="e" Output="え"/>
    <Conversion Input="o" Output="お"/>
  </ConversionTable>
</AutoConverterConfig>
}}

"aiueo"のいずれかの文字が見つかれば、<StateTransition ID="0">の<InputValidators>と一致しますので、<Actions>が実行されます。<Actions>では、AppendInput、ConvertToOutput、Clearが指定されていますが、これはつまり、現在の文字("aiueo"のいずれか)をバッファに追加し、ConversionTableに基づいてバッファ内の文字列を変換し、出力ストリームに出力し、バッファをクリアするという意味です。具体的には、例えば"a"という文字が見つかったときは、バッファに"a"が入り、<Conversion Input="a" Output="あ"/>の設定に基づいて"あ"に変換されて出力され、最後にバッファをクリアします。

この設定を使って変換を実行するには、次のようにします。

#code(vbnet){{
'変換する文字列 
Dim input As String = "abcde"
Dim reader As System.IO.TextReader = New System.IO.StringReader(input)
'出力先 
Dim writer As System.IO.TextWriter = New System.IO.StringWriter()

'TransliteralConverterの作成 
Dim converter As New Microsoft.International.Converters.TransliteralConverter(
    reader, writer)
'全てのデータを変換する 
converter.Run()

'結果を表示する 
Console.WriteLine(writer.ToString())
'"あbcdえ"と表示される

'後始末 
reader.Dispose()
writer.Dispose()
}}

#code(csharp){{
//変換する文字列
string input = "abcde";
System.IO.TextReader reader = new System.IO.StringReader(input);
//出力先
System.IO.TextWriter writer = new System.IO.StringWriter();

//TransliteralConverterの作成
Microsoft.International.Converters.TransliteralConverter converter =
    new Microsoft.International.Converters.TransliteralConverter(reader, writer);
//全てのデータを変換する
converter.Run();

//結果を表示する
Console.WriteLine(writer.ToString());
//"あbcdえ"と表示される

//後始末
reader.Dispose();
writer.Dispose();
}}

ここではXMLファイルの名前を"TransliteralConverter.xml"としたためXMLファイルのパスを指定する必要がありませんでしたが、別のファイル名(別の保存場所)にした場合は、TransliteralConverterコンストラクタの3番目のパラメータにXMLファイルのパスを渡します。XMLファイルのパスではなく、ストリームを指定することも出来ます。

***複数の状態を使用する例: 2つの文字を文字列に変換する [#s05fafb6]

次はもう少し複雑な例です。2つの文字を文字列に変換します。これには、2つの状態を用意する必要があります。

ここでは、「aiueo」を「あいうえお」に変換するのに加え、「kakikukeko」を「かきくけこ」に変換します。

"TransliteralConverter.xml"を次のように書き換えます。

#code(xnl){{
<?xml version="1.0" encoding="utf-8" ?>
<AutoConverterConfig>
  <StateMachineConfig EntryState="0" CharSet="[aiueok]">
    <State ID="0">
      <StateTransition ID="0">
        <InputValidators>
          <Regex>[aiueo]</Regex>
        </InputValidators>
        <Actions>
          <Action>AppendInput</Action>
          <Action>ConvertToOutput</Action>
          <Action>Clear</Action>
        </Actions>
      </StateTransition>
      <StateTransition ID="1">
        <InputValidators>
          <Regex>[k]</Regex>
        </InputValidators>
        <Actions>
          <Action>AppendInput</Action>
        </Actions>
      </StateTransition>
    </State>
    <State ID="1">
      <StateTransition ID="0">
        <InputValidators>
          <Regex>[aiueo]</Regex>
        </InputValidators>
        <Actions>
          <Action>AppendInput</Action>
          <Action>ConvertToOutput</Action>
          <Action>Clear</Action>
        </Actions>
      </StateTransition>
    </State>
  </StateMachineConfig>
  <ConversionTable>
    <Conversion Input="a" Output="あ"/>
    <Conversion Input="i" Output="い"/>
    <Conversion Input="u" Output="う"/>
    <Conversion Input="e" Output="え"/>
    <Conversion Input="o" Output="お"/>
    <Conversion Input="ka" Output="か"/>
    <Conversion Input="ki" Output="き"/>
    <Conversion Input="ku" Output="く"/>
    <Conversion Input="ke" Output="け"/>
    <Conversion Input="ko" Output="こ"/>
  </ConversionTable>
</AutoConverterConfig>
}}

前の例と比較して、状態が2つに増えて<State ID="1">が加わったこと注目してください。また、<State ID="0">に<StateTransition ID="1">が追加されたことにも注目してください。(それ以外に、StateMachineConfigのCharSetと、ConversionTableも変更されています。)

例えば"ka"という文字を変換するケースを考えてみましょう。まず"k"という文字が<StateTransition ID="0">の<StateTransition ID="1">の<InputValidators>と一致するため、<Actions>のAppendInputが実行されます。つまりバッファには"k"が入ります。また、次の状態は"1"になります。

次に"a"という文字が<State ID="1">(現在の状態が"1"なので)の<StateTransition ID="0">と一致するため、AppendInput、ConvertToOutput、Clearが実行されます。つまり、バッファに"a"が追加されて"ka"となり、"ka"は"か"に変換されて出力されます。その後、バッファはクリアされます。

この設定を使って実際に変換する例は先ほどのコードと同じですので、省略します。

***おまけの例: 同じ文字が2つ続くか調べる [#i90bc3c1]

最後にもう一つ例を紹介します。ここではさらに、「kkakkikkukkekko」を「っかっきっくっけっこ」に変換できるようにします。

#code(xml){{
<?xml version="1.0" encoding="utf-8" ?>
<AutoConverterConfig>
  <StateMachineConfig EntryState="0" CharSet="[aiueok]">
    <State ID="0">
      <StateTransition ID="0">
        <InputValidators>
          <Regex>[aiueo]</Regex>
        </InputValidators>
        <Actions>
          <Action>AppendInput</Action>
          <Action>ConvertToOutput</Action>
          <Action>Clear</Action>
        </Actions>
      </StateTransition>
      <StateTransition ID="1">
        <InputValidators>
          <Regex>[k]</Regex>
        </InputValidators>
        <Actions>
          <Action>AppendInput</Action>
        </Actions>
      </StateTransition>
    </State>
    <State ID="1">
      <StateTransition ID="0">
        <InputValidators>
          <Regex>[aiueo]</Regex>
        </InputValidators>
        <Actions>
          <Action>AppendInput</Action>
          <Action>ConvertToOutput</Action>
          <Action>Clear</Action>
        </Actions>
      </StateTransition>
      <StateTransition ID="1">
        <InputValidators>
          <Regex>[#History(-1)#]</Regex>
          <Regex>[^#History(-2)#]</Regex>
        </InputValidators>
        <Actions>
          <Action>AppendInput</Action>
        </Actions>
      </StateTransition>
    </State>
  </StateMachineConfig>
  <ConversionTable>
    <Conversion Input="a" Output="あ"/>
    <Conversion Input="i" Output="い"/>
    <Conversion Input="u" Output="う"/>
    <Conversion Input="e" Output="え"/>
    <Conversion Input="o" Output="お"/>
    <Conversion Input="ka" Output="か"/>
    <Conversion Input="ki" Output="き"/>
    <Conversion Input="ku" Output="く"/>
    <Conversion Input="ke" Output="け"/>
    <Conversion Input="ko" Output="こ"/>
    <Conversion Input="kka" Output="っか"/>
    <Conversion Input="kki" Output="っき"/>
    <Conversion Input="kku" Output="っく"/>
    <Conversion Input="kke" Output="っけ"/>
    <Conversion Input="kko" Output="っこ"/>
  </ConversionTable>
</AutoConverterConfig>
}}

ここでは、<State ID="1"><StateTransition ID="1"><InputValidators>で使用している正規表現に注目してください。"#History(-1)#"というキーワードを使用しています。ヘルプには一切説明がありませんが、"#History(-1)#"というのは、バッファの最後の文字という意味のようです。"#History(-2)#"は最後から2番目の文字です。つまり、"[#History(-1)#]"は前にバッファに入れられた文字と同じであることを示し、"[^#History(-2)#]"は前の前の文字とは違うことを示しています。つまり、同じ文字が2つ続き、3つは続かないということです。

この設定で"kkka"という文字を変換すると、"kっか"となります。

**おまけの構成ファイル [#y2a2890d]

***半角カナを全角に変換する [#r1cdb204]

KanaConverter.HalfwidthKatakanaToKatakanaメソッドでは、半角カナの一部の文字を全角に変換しません。そこで半角カナを全角に変換する構成ファイルを作ってみました。具体的には、Halfwidth CJK punctuation(U+FF61〜U+FF64)とHalfwidth Katakana variants(U+FF65〜U+FF9F)を全角に変換します。

#ref(HankakukanaToZenkaku.xml)

**参考 [#pd397479]

-[[ローマ字>Wikipedia:ローマ字]]
-[[ローマ字かな変換>Wikipedia:ローマ字かな変換]]
-[[半角カナ>Wikipedia:半角カナ]]

**コメント [#jb0679f4]
#comment

//これより下は編集しないでください
#pageinfo([[:Category/.NET]] [[:Category/ASP.NET]],2008-11-20 (木) 02:03:24,DOBON!,2008-11-21 (金) 02:48:00,DOBON!)
[ トップ ]   [ 編集 | 差分 | バックアップ | 添付 | 複製 | 名前変更 | リロード ]   [ 新規 | 子ページ作成 | 一覧 | 単語検索 | 最終更新 | ヘルプ ]