KOTET'S PERSONAL BLOG

#dlang Dでつくるbrainfu*kのインタプリタ

Created: , Last modified:
#dlang #brainfuck #qiita #tech

これは1年以上前の記事です

ここに書かれている情報、見解は現在のものとは異なっている場合があります。

この記事はQiitaに投稿されたものの転載です。


brainf*ckの処理系はすでにいろんな人が作っているけど勉強になりそうだったので自分で書いてみた。

import std.stdio;
import std.getopt;
import core.stdc.stdio;
import std.file;
import std.conv;

const BUFFSIZE = 30000;

void main(string[] args)
{
    string filename = args[1];
    string code = readText(filename);
    size_t ptr = 0;
    size_t codeptr = 0;
    ubyte[] memory = new ubyte[BUFFSIZE];
    while(codeptr < code.length)
    {
        switch(code[codeptr])
        {
            case '+':
                memory[ptr]++;
                break;
            case '-':
                memory[ptr]--;
                break;
            case '>':
                ptr++;
                break;
            case '<':
                ptr--;
                break;
            case '.':
                putchar(memory[ptr]);
                break;
            case ',':
                int tmp = getchar();
                if(tmp == EOF) return;
                memory[ptr] = tmp.to!ubyte;
                break;
            case '[':
                if(memory[ptr] == 0)
                {
                    int loopnest = 1;
                    do
                    {
                        codeptr++;
                        if(code[codeptr] == '[') loopnest++;
                        if(code[codeptr] == ']') loopnest--;
                    }while(0 < loopnest);
                }
                break;
            case ']':
                if(memory[ptr] != 0)
                {
                    int loopnest = 1;
                    do
                    {
                        codeptr--;
                        if(code[codeptr] == '[') loopnest--;
                        if(code[codeptr] == ']') loopnest++;
                    }while(0 < loopnest);
                }
                break;
            default:
        }
        codeptr++;
    }
}

getchar/putcharは何で置き換えればいいんだろうか?

マンデルブロー集合を描かせて時間計測。

$ time ./kbfi mandelbrot.b
real	1m25.554s
user	1m25.464s
sys	0m0.044s

real	1m25.144s
user	1m25.104s
sys	0m0.004s

real	1m25.659s
user	1m25.640s
sys	0m0.000s

$ time bf mandelbrot.b
real	0m8.909s
user	0m8.888s
sys	0m0.012s

real	0m9.066s
user	0m9.048s
sys	0m0.004s

real	0m8.966s
user	0m8.952s
sys	0m0.008s

遅いのでこれから速くしていきたい。