Help us understand the problem. What is going on with this article?

オフラインリアルタイムどう書く E29 の実装例(BrainF**k)

More than 1 year has passed since last update.

はじめに

こちらは、「オフラインリアルタイムどう書く」のBrinF**kによる実装例です。

コード

githubのレポジトリより。

solve.bf
->+>>+>>,+[
 [
  [->+>[->>>]<[>+++++++>+>]<<<<]
  >>>--[---
   <<-<<+<[-[-[-
      ** 3 **
      <<[-
       ** e==1 **
       >>>->>>[-]+>-[+[-]
        ** not slash **
        <->
       ]
       <[-
        ** slash **
        <<<<+>>>>
       ]
      <<<<<<]
      >>>[-
       ** e==0 **
       >>>>>+<[-[[-]
         ** other **
         >-<<[-]<<<<+>>>[->+<]<++++[->+++++++++++<]>>>
        ]>[-
         ** slash **
         <<<<<<+>>>>>>
        ]
       <]>[-
         ** quote **
         <<[-<<<<<+>>>>>]<[-]<++++[->+++++++++++<]<<++<<+>>>>>>>>
       ]
      <<<<<]
     ]>[-
      ** 2 **
      <<[->+>>>>-<<<<<]>[-<+>]
      >>>>[+++++[-]>+<]+>[[-]
       ** not q **
       <-<<<<++<<[-]>>>>>>>
      ]<[-
       ** q **
       <[-]<<<<[-]>+>>>>
      ]
     <<]
    <]>[-
      ** 1 **
      >>>>>+<[-[[-]
        ** other **
        >-<<[-]<<<<+<<[-]>>>>>>>
       ]>[-
        ** slash **
        <<<[-]<<<+++>>>>>>
       ]
      <]>[-
        ** quote **
        <<[-<<<<<+>>>>>]<[-]<<<++>>>>>>
      ]
    <<<<]
   <]>[-
      ** 0 **
      >>[-]>[-]>[-]
   <<<]
   >[<<<[->+<]<[->+<]<[->+<]>>>>>[-<<<<<+>>>>>]>]
  <,+>>>]
  <[
   ** newline **
   [-]<[-]>
  ]
 <<]
 <<<[-]<[->>+<<]>+>-[+[-]
  ** wrong **
  <++++[-<+++++++++>]<.
 >>]
 <[-
  ** correct **
  <-<+[-<+]->+[-.>+]
 ]
 +[[-]<+]++++++++++.[-]
->+>>+>>,+]

実行例

次のように、問題のパラメータを1行ずつファイルに登録して食わせると、答えを1行ずつ出力するようになっています。

実行例
$ cat input.txt
foo/bar/baz
/foo/bar/baz'/
"
(略)
/"/'//'/"""''//'/"'''
0gK"koYUb""S/p''z/"Et
Foo/Bar/"Hoge'/'Fuga"
$ bff solve.bf < input.txt
foo,bar,baz
-
-
(略)
-
0gKkoYUbS/p''z/Et
Foo,Bar,Hoge'/'Fuga

概要

上のコードは、次のような有限状態機械を想定して作ったものです。

image.png

本当に細かく状態を細分化すると、Start,End,Abort以外に8種類の状態となるのですが、一部を変数とすることでN,Q,Sの3状態に絞り込みました。
コード中では、Abort,N,Q,Sにそれぞれ0~3の数字を割り当てて管理しています。
※Abortを管理する必要があるのは、一旦Abortになったら延々読み捨てる必要があるから

そして変数としたのはe,qで、それぞれ次のような意味を持ちます。

  • e : 最近のスラッシュ以降、エレメントになる文字列が今の所空である ( 0: 空でない、1: 空 )
  • q : クォートの開始文字 ( シングルかダブルか )
    ※実際の処理では、文字は変則divmod8の結果で識別しており、qにはその余り部分を保持します

そのため、コード中では、文字を処理するところの左に e,q,s ( s は状態 ) の3変数を常に持ちまわるようにします。
出力する文字 ( スラッシュのところはカンマに変える ) は、順次左端に送っていって、最後に一括で出力できるようにしています。

おわりに

正規表現で処理できるんだから、BrainF**kでも書けるよね! ということで、実装してみました。

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away