フィンローダのあっぱれご意見番

第76回:明日は雨が降る

初出: C MAGAZINE 1998年09月号
Updated: 1998-11-17

[一覧] [ホームページ]


 最近、 東風荘 にハマっている。インターネット上の対戦麻雀なのだが、相手が人間というのがいい。つまり、読みの勝負になるのである。ひっかけてみたり、裏の裏を読んだり、結構壮絶なものだ。私のWeb pageのどこかに試合評を書いたりしているのだが、結構無茶しているので後で読んでも面白いかもしれない。 (※1)


 NIFTY SERVEのFPROGORGでは、昨年から滅茶苦茶なストーリーの連載小説(か?)を書いているのだが (※2) 、この中で、コンピュータと暗号の話題が出てきた。小説というには破綻しすぎているようで読む価値がないが、出てくる暗号にセンテンスコンバージョンという手法を使った。聞いたことのない手法だと思うのだが、これは実は私が勝手に創作した手法ので当然である。しかし発想は平凡なので、実はありきたりな手法でかつ既に実用になっているのかもしれない。アイデアの単純さは今までの暗号化のアルゴリズムに比べると群を抜いて平易である。単語を単語に置換する。ただこれだけなのである。アルファベットからアルファベットへの置換というのはよく知られている。phinlodaという綴のアルファベットを1つ後ろにずらしてqijompebとすると元のイメージが想像できない。復元は1つ前のアルファベットに置き換えるだけだから簡単だ。これを単語単位で実行するのである。そんなことが実際できるだろうか。単語を別の単語に置換するプログラムがあればよいのだ。実際どうだか知らないが、全文検索のWeb pageがあたり前のように存在する昨今、そう難しい技術ではなかろうと想像する。

 例えば「イントラネットは問題が指摘されている」という文を考えてみよう。例えば、fig.1 のような対応付けを考える。キーが-1とか-2という不自然な値だが、これは後に出てくるプログラムに合わせただけで他意はない。この文を暗号化すると「明日は雨が降る」になる。これを-2というキーで解読すると元に戻るのだが、間違って-1を指定すると「給料日は酒場が混雑する」という文章になってしまう。

---- fig.1 文節の対応付け ----
 キーが-2の場合

 明日 <--> イントラネット
 雨   <--> 問題
 降る <--> 指摘されている

 明日は雨が降る <--> イントラネットは問題が指摘されている

 キーが-1の場合

 明日 <--> 給料日
 雨   <--> 酒場
 降る <--> 混雑する

 明日は雨が降る <--> 給料日は酒場が混雑する

 実際にプログラムを作れと言われると、単語のテーブルとか構文解析が実に大変なのだが、とりあえずデタラメなサンプルでよければすぐ出来る。というわけで作ったのが list 1 である。ただし入力したキーの範囲チェックを全然していないから、サンプルに出てくる以外の単語を指定したりすると何がどうなるか分らない。実行する時は注意して欲しい。

---- list 1 (sc.c) ----
/* sentence conversion による暗号化のサンプル
 * 極めてデタラメなので参考の範囲を超えた使用は無茶である。
 * 予期しないキーを入れたりしたら暴走する予定。
 */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int key;

char *array[] = {
    "イントラネット",
    "給料日",
    "明日",
    "問題",
    "酒場",
    "雨",
    "指摘されている",
    "混雑する",
    "降る",
    NULL
};

static void convert(char *s, int len) {
    int i = 0;
    char **p;

    p = array;
    do {
      if (strncmp(p[i], s, len) == 0) {
        p += key; /* 範囲チェックをしていないので注意すること */
        printf("%s", *p);
        return;
      }
      p++;
    } while (*p);
    printf("(?)");
}

int main(int argc, char *argv[]) {
    char *s;
    char *t;
    int len;

    if (argc != 3) {
        fprintf(stderr, "usage: sc key sentence\n");
        fprintf(stderr, "例: sc 2 イントラネットは問題が指摘されている\n");
        exit(1);
    }

    key = atoi(argv[1]);
    s = argv[2]; /* 文章 */
    /* ここで真面目に文章解析するわけだが、今回は超手抜き */

    while (*s != '\0') {
        t = strstr(s, "は");
        if (t != NULL) {
            len = t - s;
            convert(s, t - s);
            printf("は");
            s = t + 2;
            continue;
        }

        t = strstr(s, "が");
        if (t != NULL) {
            len = t - s;
            convert(s, t - s);
            printf("が");
            s = t + 2;
            continue;
        }

        len = strlen(s);
        if (len > 0) {
            convert(s, len);
        }
        break;
    }

    return 0;
}

 実行してみたのが fig.2 である。このように、2で暗号化した文章が-2で復号することで元に戻ることが分る。キーを-1とすると全然違う文章になる。

---- fig.2 実行例 ----
 (キーを2として暗号化する)

D:\CM> sc 2 イントラネットは問題が指摘されている
明日は雨が降る

 (キーを-2として復号すると元に戻る)

D:\CM>sc -2 明日は雨が降る
イントラネットは問題が指摘されている

 (キーを-1にしたらこうなって元の文章が出てこない)

D:\CM>sc -1 明日は雨が降る
給料日は酒場が混雑する


 ポイントは「正しく解読されたかどうかをコンピュータが判定できるか」という所にある。解読成功した時だけ意味のある文になるような暗号化なら、コンピュータに力まかせで解読させて、たまたま意味のある文になった時に成功と判断すればよい。機械的な判断が可能なのである。力技で解ける分野なのだ。与えられた暗号を解析した結果が

lmZplmmZlmzJlm/5mZAJmZM5mZZpmZmZmZzJmZ/…

 のようになったとすると、これは尋常な文章でない、つまり解読に失敗したということが一目瞭然である。実はこれはbase64でエンコードしたテキストの一部なのでそうとも限らないのだが。それはさておき、しかし、「明日は雨が降る」という暗号(?)を復号したら

  給料日は酒場が混雑する

 になったとして、この結果がいったい元の文章なのか失敗した結果なのかをコンピュータに判断できるだろうか? これはAIの範疇に属する問題かもしれない。大昔からプログラマーが最も実現したいと思って努力を続けながら、今なお到達する気配すら見えない領域がある。人と同じように考える機械。それとも、実はもうあるのだろうか。

 とにかく、最近の暗号化アルゴリズムは、機械的な変換を行う方向に走っている。ただし、機械的といっても、力ずくで解くには計算時間が非現実的になっていて、しかもキーがあれば一瞬で復元できる、という都合のよい仕組みだ。

 センテンスコンバージョンを使えば、あまり複雑なキーを使う必要はない。割と単純な置換で構わない。復元するのが困難というのではなく、復元は簡単だが贋物がたくさん出てきてどれが本当の文なのか分らないという状況にするのである。もっとも、これは単なるアイデアで、そのような実用プログラムを完成したという話ではなく、あくまでフィクションの中の話だから、その点は誤解なきようお願いしたい。

 ちなみに、FPROGORGに書いた時には、ホームズ、ポワロ、メイソンの三人がこの暗号を解こうとする設定になっていた。ホームズは理詰めで解釈を試みる。ポワロは暗号を書いた人の性格から推理する。メイソンは書いた本人を捕まえて締め上げようとする。あなたはどのタイプか? ホームズとワトソンにさせた会話を紹介しておこう。残念ながら非保存の会議室における発言なので、現在は該当発言は消滅している。

ワトソン「踊る人形という事件がありましたね」

ホームズ「そうだ、まさにあれがそうだよ、ワトソン君。(略)さて、文字ではなくて、文章と文章、もっと厳密に言えば、意味のある文章から意味のある文章に置き換えるような方法で暗号化したら、どうなるか分るかね?」

「それは、えーと、間違って解読した場合に、文としては正しいが意味としてはどこか間違った文章が出来る、でもそれが間違っていることはどうすれば分るのか、ということですか?」

「その通り。コンピュータは、その文章が文法上正しいかどうかを判断することはできるが、その文章が文法的に正しい場合に、書いた人間の意図の通りの文章であるかどうかを判断することはできないのだよ。これがコンピュータの決定的な弱点なのだ。…


 さて、出てくる文章が皆、意味があるとしたら、どれが正しいかを検証するのが不可能。となると、最後に勝てるのは理詰めではなく行動パターンで相手を読むという方法、つまりここではポワロ型の思考が有利ではないかと思う。相手が人間だと、人間の行動パターンを知っている「人間」ならば先を読むことも可能。東風荘が流行るわけだ。

(フィンローダ ニフティサーブ FPROG SYSOP)


補足

(※1) 本当の裏ページのこと。1998年の6月〜8月頃が熱い。日記ページは最後の方に前月のページに飛べるリンクがあるので、そこからたどるといい。

(※2) 「ROM墓場からの声」という会議室。この会議室は1ヶ月単位で削除してやり直すので過去のログが公式には残っていない。ただし、発言者全員の死亡後50年経過して著作権保護期間が切れた時点で、遺言によりログを発表するという不文律になっている。問題の連載小説だが、仮想世界で借金のため首が回らなくなった主人公がイカサマに失敗して空間移動したらミレニアム2ファルコンという宇宙船にワープしてしまって、しかもさらに遭難。船長の死体の回りで探偵が相談しているというシーンの所。小説は全く小説の形式を踏襲していない。コラムの元になった「 まだらの網 」の前の回である「 煉瓦畑のジオイド 」は意味が分からないということで話題になった。書いた本人も意味は分からない。


(C) 1998 Phinloda, All rights reserved
無断でこのページへのリンクを貼ることを承諾します。問い合わせは不要です。
内容は予告なく変更することがあります。