私は、ポインター演算がプログラミングの主要ツールである言語を設計しました。
下記は用例です。
(print 0 to 8)
=9[>1=9-*-1.>-1-1]
(print 1 to 10 with spaces in between, character literal extension used)
=1[.>1=10-*-1[>1=' '!>-2+1;-2];1]='\n'!
(compute the factorial of 10)
=10>1=*-1-1[>-1**1>1-1]>-1.
(print "hi")
=104!=105!
(print "hi" with extension for arrays)
={104,105,0}[!>1]
(print "Hello, world!" with extension for C-style string literals)
="Hello, world!"[!>1]
言語仕様
言語の定義は非常に簡単です。Cの経験があれば簡単に理解できますが、私はそうは思いません。
PointerLangのすべてのプログラムには、ポインタ、つまりがありますP
。コマンドを使用して制御できる非表示の単一のグローバル変数と考えることができます。P
最初は配列の先頭を指します。配列内のすべての要素には、32ビットの符号付き整数である型があります。int
Cプログラマ向け
int32_t *P = malloc(1000);
PointerLangには、コマンドと引数があります。引数は、int
コマンドの後に来る必要があります。特に指定がない限り、すべてのコマンドは左から右に実行されます。以下はコマンドのリストです。A
引数を表します。なしのコマンドA
は、引数を取りません。のコマンドA
は引数を取る必要があります。括弧内は同等のC式です。
=A
:AをPに割り当てます(*P = A
)+A
:AをPに追加(*P += A
)-A
:PでAを引く(*P -= A
)*A
:PでAを乗算します(*P *= A
)/A
:PでAで除算(*P /= A
)>A
:移動P
によってA
(P += A
).
:Pの整数を出力(printf("%d", *P)
)!
:Pの整数をASCII(printf("%c", (char)*P)
)として出力します[
:Pの値が0の場合、次の]
(while (*P) {
)の後でコマンドに移動します]
:[
一致するペアである前に移動します(}
);A
次の場合A
正である、後のコマンドに行くA
番目は、]
次の来て。A
負の場合は、前のA
th に移動し[
ます。Aが0の場合、何もしません。
整数リテラルは引数です。
次の2つは、引数を取る特別な引数です。
-A
:と同じ絶対値A
との反対符号を持つ引数として評価されA
ます。単項マイナス*A
:移動P
によってA
で値を評価し、P
移動し、P
で-A
(P[A]
)
PointerLang内のすべてのコメントは括弧内にあり(comment)
ます。
プログラム例
1から10まで数えるこのプログラムは、理解を深めるための良い例です。
(print 1 to 10 with spaces in between)
=1[.>1=10-*-1[>1=32!>-2+1;-2];1]=10!
解釈するときは注意してください-*-1
。-
コマンドで*-1
あり、引数です。整数リテラルは、コマンドと引数のペアの終わりを効果的に示します。
次のように1対1対応でCに変換できます。
int main(void) {
int32_t *P = malloc(1000);
*P = 1; // =1
l:
while (*P) { // [
printf("%d", *P); // .
P += 1; // > 1
*P = 10; // =10
*P -= P[-1]; // -*-1
while (*P) { // [
P += 1; // >1
*P = 32; // =32
printf("%c", (char)*P); // !
P += -2; // >-2
*P += 1; // +1
goto l; // ;-2
} // ]
break; // ;1
} // ]
*P = 10; // =10
printf("%c", (char)*P); // !
return 0;
}
文字リテラル、配列、文字列リテラルなどの拡張機能をこの言語に適用できますが、簡単にするためにこれらを実装する必要はありません。
チャレンジ
言語仕様のセクションと以下の注で詳述されているコア機能を実装する必要があります。可能な限り短いプログラムを記述して、お気に入りのプログラミング言語で試してみてください。
注1:配列のサイズは未定義です。しかし、ほとんどの問題を解決するのに十分な大きさでなければなりません。
注2:整数オーバーフローは定義されていません。
注3:仕様では、特定の言語構成体の結果または効果のみを定義しています。たとえば、引数の定義の手順に厳密に従う必要はありません*
。
注4:コマンド、引数、コメント以外の文字は空白は無視されます。例えば=104!=105!
と同じ= 1 0 4! = 1 05 !
です。
注5:コメントはネストされません。((comment))
構文エラーです。
注6:私の言語の穴を修正するために、重大な変更を加えました。~
コマンドは現在使用されず、;
常に引数を取ります。
注7:すべての整数リテラルは10進数です。
=9[>1=9-*-1.>-1-1]
は0から9が印刷されますか?P [0] = 1であるため8を指定した後、ループの最後の直前で1を減算し、P [0] = 0にします。次に、ループを再び開始すると、P [0] = 0であるため終了します。例では0から8だけを出力する必要がありますか、それとも本当に混乱していますか?