言語を自作してみた。(1)


言語を自作してみたよ。

皆さんは言語を自作したことがありますか?え?ある?、、、、、あら、そう。

待って!ブラウザバックしないで!おもしろいですから?この記事!
、、はい。ありがとうございます。改めて、今回は「自作の言語を作ってみた」回の
第一回目であります。まあ書き溜めてたのを記事にしただけなんですけど。
それじゃあ早速行ってみましょう!

何で作るの?

筆者は(当たり前ですが)プログラムを書きます。その時、ふと頭に浮かんだのです。
「PCに言語で命令できるのなら自作の言語でも同じようにできるのでは?」と。
今考えればすぐに忘れるようなことだったのですが、筆者は変わり者なので「ならば作ってしまおう!」
と考えてしまったわけです。

概要

python3.8.5使用
パーサなど:すべて自作(<-ほめて!)

文法

  • 型指定させたい
  • ()の代わりに{}使いたい。個人的に形が好きだから。
  • とりあえず関数定義とかはあと。でも実現させたい。だってまだ1回目だもん。

コードなど

あ、書き忘れてましたがGithubに載せてます。
URL:https://github.com/pythonmaster1027/Omega-version0.0.5
あと筆者はPython初心者です。コードの書き方が下手です。悪しからず。
対話型もあります。
URL:https://github.com/pythonmaster1027/Omega-version0.0.1

コード

read.py
import sys
import os
from main import *

class Fread:
    def __init__(self):
        self.opf = open(str(sys.argv[1]), "r", encoding="utf_8")
    def run(self):
        opf2 = self.opf.readlines()
        for inp in opf2:
            m = Main(inp)
            m.serf()

main.py
import sys
from reanp import *
import os
from collections import defaultdict

global d, x, y

class Main:
    def __init__(self, inp):
        self.inp = inp
        self.dict = {}
        self.d = defaultdict(list)
        self.inp = self.inp.split("//")[0]   # //を取り外す
        self.inp = self.inp.split("#")[0]    # #を取り外す

    def serf(self):
        if self.inp.startswith("def ") or self.inp.startswith("    "):
            self.inp = self.inp.replace("    ", "")
            self.inp = self.inp.replace(";", "")
            print(self.inp)

            self.run()
        else:
            self.run()

    #文字列をprintするときの処理
    def run(self):
        if self.inp.startswith("print{") and "}" in self.inp and '"' in self.inp:
            self.inp = self.inp.replace("print{", "")
            self.inp = self.inp.replace("}", "")
            self.inp = self.inp.replace('"', "")
            print(self.inp)

        #変数定義の場合の処理
        elif "=" in self.inp:
            if self.inp.startswith("int "):
                self.inp = self.inp.replace("int", "")#intを取り外す
                self.inp = self.inp.replace(" ", "")
                self.x = self.inp.split("=")[0]
                self.y = eval(self.inp.split("=")[-1])
                self.dict[self.x] = self.y
                f = open("sys\\var.oms", "a", encoding="utf_8")
                f.write(str(self.dict)+"\n")
                f.close()

            if self.inp.startswith("void "):
                self.inp = self.inp.replace("void", "")
                self.inp = self.inp.replace(" ", "")


        #変数をprintするときの処理
        elif self.inp.startswith("print{") and "}" in self.inp:
            self.inp = self.inp.replace("print{", "")
            self.inp = self.inp.replace("}", "")
            r = Read(self.inp)
            r.run()

        elif self.inp == "\n":
            pass

        elif self.inp == "exit{}":
            sys.exit(0)

        else:
            print("Err:No funcsion Error")

reanp.py
from ast import literal_eval
from pprint import pprint

class Read:
    def __init__(self, inp):
        self.f = open("sys\\var.oms", "r", encoding="utf_8")
        self.r = self.f.readlines()#                             リスト
        self.inp = inp

    def run(self):
        inp = self.inp
        v = Vpri()
        v.run(inp)
        self.f.close()


class Vpri:
    #inp = printを命じられた変数名
    def run(self, inp):
        fil_data = open("sys\\var.oms", encoding="utf_8")
        cov = open("sys\\varconp.oms", "w", encoding="utf_8")
        inp = inp.replace("\n", "")
        for line in fil_data:#一行ずつ読み込まれたデータ
            line = line.replace("{", "").replace("}", "").replace("'", "").replace(" ", "")
            #line = line.rstrip()
            s = line.split(":")[0]#変数名
            i = line.split(":")[-1]#変数にあてられたデータ
            cov.write(s + "," + inp +"\n")
            if inp == s:
                print(i)
                break
            else:
                pass

        fil_data.close()
        cov.close()
Omega.bat
@echo off
read.py %1

簡単な使い方

1.Omega.batのあるフォルダまでたどり着く
2.コマンドプロンプトでOmega 実行するファイル名
3.実行!

まとめ

  • ファイルにしてそれを読み込むから思ったよりコードが長くなっちゃいました。
  • 変数の保存の方法に困りました。
  • 実行速度おそい!!!

以上、dangomushiでした。見ていただきありがとうございました。