なでしこを明後日の方向に

日本語プログラム言語なでしこを応援しています

なでしこ1で文字列処理系の命令を使ってみる例

MTGの「稲妻の」で始まるカードを検索した結果のテキストをサンプルに使います。
検索結果を変数 原文 に入れて文字列処理のスタートです

原文=『 英語名:Chain Lightning
日本語名:稲妻の連鎖(いなずまのれんさ)
 コスト:(赤)
 タイプ:ソーサリー
クリーチャー1体かプレインズウォーカー1体かプレイヤー1人を対象とする。稲妻の連鎖はそれに3点のダメージを与える。その後、そのプレイヤーかそのパーマネントのコントローラーは(赤)(赤)を支払ってもよい。そのプレイヤーがそうした場合、そのプレイヤーはこの呪文をコピーし、そのコピーの新たな対象を選んでもよい。
イラスト:Sandra Everingham
 セット:Legends
 稀少度:コモン2


 英語名:Leyline of Lightning
日本語名:稲妻の力線(いなずまのりきせん)
 コスト:(2)(赤)(赤)
 タイプ:エンチャント
稲妻の力線があなたのゲーム開始時の手札にあるなら、あなたはそれが戦場に出ている状態でゲームを始めてもよい。 
あなたが呪文を唱えるたび、プレイヤー1人かプレインズウォーカー1体を対象とする。あなたは(1)を支払ってもよい。そうしたなら、稲妻の力線はそれに1点のダメージを与える。
イラスト:Paolo Parente
 セット:Guildpact
 稀少度:レア


 英語名:Lightning Angel
日本語名:稲妻の天使(いなずまのてんし)
 コスト:(1)(青)(赤)(白)
 タイプ:クリーチャー --- 天使(Angel)
飛行、警戒、速攻
 P/T:3/4
イラスト:rk post
 セット:Time Spiral "Timeshifted"
 稀少度:タイムシフト』

この原文を反復すると、30行あるので30回のループになります。

見た目がすでに段落分けになっているので、3回の処理にしたいですよね?
この場合は「区切る」をしてから反復しましょう。

原文「{改行}{改行}{改行}」区切る
それ反復
  対象言う

これで3個の段落に分かれ、反復は3回となります。
文字列型を反復した時は1行ごとに繰り返すのですが、
「区切る」で要素数3の配列型になっているので3回になります。

ここから日本語名の「稲妻の連鎖」「稲妻の力線」「稲妻の天使」を取り出す場合を考えます

範囲切り取るを使ってみる

とりあえず「日本語名:」から改行まで範囲切り取るを試してみましょうか?

//なでしこv1
原文「{改行}{改行}{改行}」区切る
それ反復
  対象「日本語名:」から改行まで範囲切り取る
  それ表示

結果

稲妻の連鎖(いなずまのれんさ)  
稲妻の力線(いなずまのりきせん)  
稲妻の天使(いなずまのてんし)

ふりがなも一緒きてしまいましたね。まあいいでしょう。

範囲切り取るを使ったので、対象からその部分が削除されるので注意します。

なお、なでしこ3にはまだ範囲切り取るは実装されていないようです。(v3.4.20時点)

正規表現を使ってみる

正規表現では $ が文末なので使ってみます。

原文「{改行}{改行}{改行}」区切る
それ反復
  対象「日本語名:(.*)$」正規表現マッチ
  それ表示

実行結果

日本語名:稲妻の連鎖(いなずまのれんさ)

日本語名:稲妻の力線(いなずまのりきせん)

日本語名:稲妻の天使(いなずまのてんし)

なんか微妙な改行が挟まりましたね…!
これは改行もマッチした部分として取得しているからです。
トリムで後ろの改行コードを消すとよいでしょう。

今回は「日本語名:」の部分はいらないので抽出文字列を使います。
(.*)の部分が変数抽出文字列に入ります

原文「{改行}{改行}{改行}」区切る
それ反復
  対象「日本語名:(.*)$」正規表現マッチ
  抽出文字列トリムして表示

実行結果

稲妻の連鎖(いなずまのれんさ)
稲妻の力線(いなずまのりきせん)
稲妻の天使(いなずまのてんし)

ワイルドカードを使ってみる

ワイルドカードマッチでも処理できます。
ワイルドカードには文末 $ が使えないので{改行}までを指定。
ワイルドカードでも抽出文字列は使えます。

原文「{改行}{改行}{改行}」区切る
それ反復
  対象「日本語名:(*){改行}」ワイルドカードマッチ
  抽出文字列トリムして表示

実行結果

稲妻の連鎖(いなずまのれんさ)
稲妻の力線(いなずまのりきせん)
稲妻の天使(いなずまのてんし)

正規表現よりも暗号っぽさがないのでいいですね。

なお、なでしこ3にはまだワイルドカードマッチは実装されていないようです。(v3.4.20時点)

実用的なツールにする

さて、カードの日本語名を取り出して何に使うか。 たとえばこういうのはどうでしょう

こんなダイアログをだして、1つ選んだら

1段落を言う。
これをやってみましょう。


まず段落ごとの文章を変数にいれます。
カード名をハッシュのキーにして、1段落分のテキストを値にします

検索キャッシュとはハッシュ //ハッシュ(辞書)型
原文「{改行}{改行}{改行}」区切る
それ反復
  対象「日本語名:(*){改行}」ワイルドカードマッチ
  抽出文字列トリム //カード名
  検索キャッシュそれ対象 //検索キャッシュ@カード名=段落

カード名を選択するダイアログはリスト絞込み選択で出すことができます。
上にある枠に文字を入れると選択肢から絞り込みをかけてくれる、本当に使えるやつです。

先の変数からハッシュキー列挙でカード名を列挙し、選択肢とします。

「抜ける」までループ
 検索キャッシュハッシュキー列挙
 それリスト絞込み選択
 もしそれならば抜ける
 検索キャッシュそれ言う //検索キャッシュ@カード名=段落
おわり

今回のプログラム全文

※ なでしこ1

原文『 英語名:Chain Lightning
日本語名:稲妻の連鎖(いなずまのれんさ)
 コスト:(赤)
 タイプ:ソーサリー
クリーチャー1体かプレインズウォーカー1体かプレイヤー1人を対象とする。稲妻の連鎖はそれに3点のダメージを与える。その後、そのプレイヤーかそのパーマネントのコントローラーは(赤)(赤)を支払ってもよい。そのプレイヤーがそうした場合、そのプレイヤーはこの呪文をコピーし、そのコピーの新たな対象を選んでもよい。
イラスト:Sandra Everingham
 セット:Legends
 稀少度:コモン2


 英語名:Leyline of Lightning
日本語名:稲妻の力線(いなずまのりきせん)
 コスト:(2)(赤)(赤)
 タイプ:エンチャント
稲妻の力線があなたのゲーム開始時の手札にあるなら、あなたはそれが戦場に出ている状態でゲームを始めてもよい。 
あなたが呪文を唱えるたび、プレイヤー1人かプレインズウォーカー1体を対象とする。あなたは(1)を支払ってもよい。そうしたなら、稲妻の力線はそれに1点のダメージを与える。
イラスト:Paolo Parente
 セット:Guildpact
 稀少度:レア


 英語名:Lightning Angel
日本語名:稲妻の天使(いなずまのてんし)
 コスト:(1)(青)(赤)(白)
 タイプ:クリーチャー --- 天使(Angel)
飛行、警戒、速攻
 P/T:3/4
イラスト:rk post
 セット:Time Spiral "Timeshifted"
 稀少度:タイムシフト』

検索キャッシュとはハッシュ
原文「{改行}{改行}{改行}」区切る
それ反復
  対象「日本語名:(*){改行}」ワイルドカードマッチ
  抽出文字列トリム
  検索キャッシュそれ対象

「抜ける」までループ
 検索キャッシュハッシュキー列挙
 それリスト絞込み選択
 もしそれならば抜ける
 検索キャッシュそれ言う
おわり