LoginSignup
0
1

Unityでのゲーム作り日記#6 ~自作言語を完成させる~

Last updated at Posted at 2024-01-20

前回の記事はこちら

今までに作ってきたターコイズ言語を完成させ、実際に動かしていきます。

インタープリタを作る

インタープリタといっても、ただノードに実装されているEvaluateメソッドを実行するだけです。

こちらがそのプログラムです。とても短いですね!

TurquoiseInterpreter.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class TurquoiseInterpreter
{
   public void execute(string code)
   {
       Lexer lexer = new Lexer(code, "!\0\"\0'\0&\0|\0(\0)\0[\0]\0{\0}\0+\0-\0*\0/\0^\0<\0>\0<=\0>=\0==\0=\0!=\0=\0+=\0-=\0*=\0/=\0:"); //字句解析器に演算子の一覧を渡す。

       TurquoiseParser parser = new TurquoiseParser(lexer); //構文解析器を生成
       parser.program().Evaluate(); //構文解析器によって作られた構文木を実行!
   }
}

インタープリタを動かす

いよいよインタープリタを動かしていきます。

インタープリタを実行するプログラム

 ついでに、ガーネット言語、トパーズ言語のインタープリタも切り替えられるようにしておきます。
 (いつかガーネット言語とトパーズ言語のプログラムも公開したいと思います。)

Execute.cs
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using TMPro;
using TMPro.EditorUtilities;

public class Execute : MonoBehaviour
{
   public GameObject textBox;
   public TMP_InputField code;

   void Start(){
       code = textBox.GetComponent<TMP_InputField>();
   }

   public void OnClick(){
       //GarnetInterpreter garnetInterpreter = new GarnetInterpreter();
       // ↑↓ garnetの場合
       //garnetInterpreter.execute(code.text);

       //TopazInterpreter topazInterpreter = new TopazInterpreter();
       // ↑↓ topazの場合
       //topazInterpreter.execute(code.text);

       TurquoiseInterpreter turquoiseInterpreter = new TurquoiseInterpreter();
       // ↑↓ turquoiseの場合
       turquoiseInterpreter.execute(code.text);
   }
}

このプログラムをボタンのイベントにくっつけてください。
あと、textBoxの部分にプログラムを入力するインプットフィールドのゲームオブジェクトをドラッグしてください。

ただのC#の場合は、普通にインタープリタに文字列(コード)を渡してもらえれば大丈夫です。(ただし、Debug.Logは全部Console.Writeなどに変えてください。)

動かしていく

まずは再帰版フィボナッチから

フィボナッチ1
func fibonacci(n){
    if(n == 0) 0
    else if(n == 1) 1
    else fibonacci(n - 2) + fibonacci(n - 1)
}
print(fibonacci(10)) # result -> 55

while版フィボナッチも

フィボナッチ2
func fibonacci(n){
   var i = 0
   var a = 0
   var b = 1
   while(i < n-1){
       var tmp = a + b
       var a = b
       var b = tmp

       var i = i + 1
   }
   b
}
print(fibonacci(50)) # result -> 12586269025

ちなみに、実行速度はwhile版のほうが再帰版に比べて圧倒的に速いです。

疑似乱数を生成する関数(線形合同法)

疑似乱数
var x = 10
var A = 1103515245
var B = 12345
var M = 2 ^ 32

func rand(){
   var x = (A * x + B) % M
   x
}

print(var x = rand())
print(var x = rand())
print(var x = rand())
print(var x = rand())
print(var x = rand())

次回はゲームのユニットを作っていきたいと思います。
次回の記事はこちら

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