LoginSignup
0
1

More than 3 years have passed since last update.

インタープリタを作る その11

Last updated at Posted at 2021-03-21

概要

インタープリタを作ってみた。
pythonで俺言語インタープリター書いてみた。

俺言語の仕様

 行番号、スペース、ステートメントの順
 代入文しか無い。
 数値は、0から255
 行番号なしで、ダイレクト実行
 行番号は、1から255
 メモリは256バイト
 ラインエディタあり。
 演算子は、+, -, /, *, %の5個
 変数は、a,b,cの三個

コマンド  意味
0 ソース表示
&=0 全行削除
30 行30が消える
a=9 変数aに9を代入
?=$ 乱数表示
#=1 行番号1から実行
?="ok" OK表示
#=120 120行へジャンプ
#=a<10*120 条件分岐、もし a<10 ならば 120行へジャンプ
a=2+3*5 (2+3)*5で25が変数aへ代入。
?=! 改行

九九のソースと実行結果


>0
10  a=1
20  b=1
30  ?=a*b
60  a=a+1
70  #=a<10*30
90  b=b+1
95  ?=!
100  a=1
110  #=b<10*30
120  #=120

>#=1
1 2 3 4 5 6 7 8 9
2 4 6 8 10 12 14 16 18
3 6 9 12 15 18 21 24 27
4 8 12 16 20 24 28 32 36
5 10 15 20 25 30 35 40 45
6 12 18 24 30 36 42 48 54
7 14 21 28 35 42 49 56 63
8 16 24 32 40 48 56 64 72
9 18 27 36 45 54 63 72 81

>

サンプルコード

import random
Ram = []
Rmd = 233
Bnd = 234
PC = 235
Lbf = 237
Ptr = 0
Cur = 0
C = 0
Adr = 0
Adr2 = 0
Val = 0
def WRITEB(adr, data):
    global Ram
    Ram[adr] = data
def READB(adr):
    global Ram
    v = Ram[adr]
    return v
def put(b):
    print(b, end = " ")
def putchar(b):
    c = chr(b)
    print(c, end = "")
def crlf():
    print()
def putl(pt, d):
    while READB(pt) != d:
        putchar(READB(pt))
        pt = pt + 1
    return pt
def putlp(d):
    global Ptr
    while READB(Ptr) != d:
        putchar(READB(Ptr))
        Ptr = Ptr + 1
def term():
    global Ptr, Rmd, Val
    cc = READB(Ptr)
    val2 = Val
    Ptr = Ptr + 1
    factr()
    if cc == ord('*'):
        Val = val2 * Val
    elif cc == ord('+'):
        Val = val2 + Val
    elif cc == ord('-'):
        Val = val2 - Val
    elif cc == ord('/'):
        Val = val2 / Val
    elif cc == ord('%'):
        Val = val2 % Val
    elif cc == ord('='):
        if (val2 == Val):
            Val = 1
        else:
            Val = 0
    elif cc == ord('>'):
        if (val2 >= Val):
            Val = 1
        else:
            Val = 0
    else:
        if (val2 < Val):
            Val = 1
        else:
            Val = 0
def getvr2():
    global Ptr, Adr2, PC, Rmd
    cc = READB(Ptr)
    if cc == ord('a'):
        Adr2 = 230
    elif cc == ord('#'):
        Adr2 = PC
    elif cc == ord('&'):
        Adr2 = Bnd
    elif cc == ord('b'):
        Adr2 = 231
    elif cc == ord('c'):
        Adr2 = 232
    else:
        Adr2 = 230
def factr():
    global Ptr, Val, Adr2
    if READB(Ptr) == ord('\0'):
        Val = 0
        return
    if getnm():
        return
    cc = READB(Ptr)
    if cc == ord('$'):
        r = random.random()
        Val = int(r * 10)
        Ptr = Ptr + 1
    else:
        getvr2()
        Val = READB(Adr2)
        Ptr = Ptr + 1
def expr():
    global Ptr
    factr()
    cc = READB(Ptr)
    while cc != ord('\0'):
        term()
        cc = READB(Ptr)
    Ptr = Ptr + 1
def getvr():
    global Ptr, Adr, PC, Rmd, C
    C = READB(Ptr)
    if C == ord('a'):
        Adr = 230
    elif C == ord('#'):
        Adr = PC
    elif C == ord('&'):
        Adr = Bnd
    elif C == ord('b'):
        Adr = 231
    elif C == ord('c'):
        Adr = 232
    else:
        Adr = 230
def ordr():
    global Ptr, Val, C, Adr
    getvr()
    Ptr = Ptr + 2
    if READB(Ptr) == ord('"'):
        Ptr = Ptr + 1
        putlp(ord('"'))
    elif READB(Ptr) == ord('!'):
        print()
    else:
        expr()
        if C == ord('?'):
            put(Val)
        else:
            WRITEB(Adr, Val)
def nxtln(pt):
    while READB(pt) != ord('\0'):
        pt = pt + 1
    pt = pt + 1
    return pt
def nxline():
    global Bnd, PC, Cur
    Cur = 0
    while Cur != READB(Bnd):
        if READB(Cur) > READB(PC):
            return True
        Cur = nxtln(Cur)
    return False
def fndln():
    global Bnd, PC, Cur
    Cur = 0
    while Cur != READB(Bnd):
        if READB(Cur) == READB(PC):
            return True
        Cur = nxtln(Cur)
    return False
def num():
    global Ptr
    if (48 <= READB(Ptr)) and (READB(Ptr) <= 57):
        return True
    else:
        return False
def getnm():
    global Ptr, Val
    if not(num()):
        return False
    n = 0
    while (num()):
        n *= 10
        ch = READB(Ptr)
        Ptr = Ptr + 1
        n += (ch - 48)
    Val = n
    return True
def run():
    global Bnd, Ptr, Lbf, Cur, PC
    while True:
        #for i in range(10):
        #   print(Ram[i])
        str = input("\n>")
        Ptr = Lbf
        for j in str:
            WRITEB(Ptr, ord(j))
            Ptr = Ptr + 1
        WRITEB(Ptr, ord('\0'))
        ima = 0
        Ptr = Lbf
        if not(getnm()):
            while True:#run
                ima = READB(PC)
                ordr()
                if READB(PC) == 0 and ima == 0:
                    break
                else:
                    if READB(PC) == 0:
                        WRITEB(PC, ima)
                    if READB(PC) == 1:
                        ima = 1
                    if READB(PC) == ima:
                        if nxline():
                            WRITEB(PC, READB(Cur))
                            Ptr = Cur + 2
                        else:
                            break
                    else:
                        if fndln():
                            WRITEB(PC, READB(Cur))
                            Ptr = Cur + 2
                        else:
                            break
        else:
            if Val == 0:#list
                pt = 0
                while pt < READB(Bnd):
                    put(READB(pt))
                    pt = pt + 1
                    pt = putl(pt, ord('\0'))
                    crlf()
                    pt = pt + 1
            else:
                f = 0
                WRITEB(PC, Val)
                if fndln():#del
                    src = nxtln(Cur)
                    dst = Cur
                    while src != READB(Bnd):
                        WRITEB(dst, READB(src))
                        dst = dst + 1
                        src = src + 1
                    WRITEB(Bnd, dst)
                if nxline():
                    f = 1
                src = READB(Bnd)
                m = 2
                h = Ptr
                while READB(h) != ord('\0'):
                    m = m + 1
                    h = h + 1
                if m > 2:
                    WRITEB(Bnd, (src + m))
                    if f == 1:#insert
                        dst = READB(Bnd)
                        while src != Cur:
                            WRITEB(dst, READB(src))
                            dst = dst - 1
                            src = src - 1
                        WRITEB(dst, READB(src))
                        src = Cur
                    WRITEB(src, Val)#append
                    src = src + 1
                    for k in range(m - 1):
                        WRITEB(src, READB(Ptr))
                        Ptr = Ptr + 1
                        src = src + 1

for i in range(256):
    Ram.append(0)
WRITEB(Bnd, 0)
print("ore v0.9")
run()





以上。

0
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
1