POJ (JVM 上の Pascal) をフォローしていない人のために説明すると、これは サブセット を Pascal から JASM に変換するコンパイラーです ( Java アセンブリ) を使用して、JVM を実行環境として使用できるようにします。
前回の投稿では、Pascal からの read/readln のサポートが実装されました。これは、標準入力 (stdin) からのデータの読み取りを可能にする関数です。この出版物では、標準入力から数値を読み取り、階乗を再帰的に計算するという POJ の目的の 1 つを完了します。
JVM 用にコンパイルしているので、この素晴らしい仮想マシンのさまざまな点の機能を詳しく説明する必要があります。したがって、私はさまざまな機会に、JVM の内部機能とその命令 (オペコード) の一部について詳しく説明します。
プロジェクトの冒頭で述べたように、目標の 1 つは、計算対象の数値を標準入力から読み取り、階乗を再帰的に計算できるようにすることでした。これまでの POJ の実装により、この目的が可能になりました。
今、これまでに開発されたものを検証する時が来ました。とはいえ、以下の Pascal プログラムから:
program fatorial; var numero : integer; function fatorial(n : integer) : integer; begin if n<0 then fatorial := 0 else begin if n<=1 then fatorial := 1 else fatorial := n * fatorial(n-1); end; end; begin write('Introduza numero inteiro: '); readln(numero); writeln; writeln('O fatorial de ', numero, ' e: ', fatorial(numero)); end.
POJ は次の アセンブリ を正しく生成します:
// Code generated by POJ 0.1 public class fatorial { public static numero I static fatorial(I)I { iload 0 sipush 0 if_icmpge L4 iconst 1 goto L5 L4: iconst 0 L5: ifeq L1 sipush 0 istore 100 goto L2 L1: iload 0 sipush 1 if_icmpgt L9 iconst 1 goto L10 L9: iconst 0 L10:ifeq L6 sipush 1 istore 100 goto L7 L6: iload 0 iload 0 sipush 1 isub invokestatic fatorial.fatorial(I)I imul istore 100 L7: L2: iload 100 ireturn } public static main([java/lang/String)V { getstatic java/lang/System.out java/io/PrintStream ldc "Introduza numero inteiro: " invokevirtual java/io/PrintStream.print(java/lang/String)V invokestatic java/lang/System.console()java/io/Console invokevirtual java/io/Console.readLine()java/lang/String invokestatic java/lang/Integer.parseInt(java/lang/String)I putstatic fatorial.numero I getstatic java/lang/System.out java/io/PrintStream invokevirtual java/io/PrintStream.println()V getstatic java/lang/System.out java/io/PrintStream ldc "O fatorial de " invokevirtual java/io/PrintStream.print(java/lang/String)V getstatic java/lang/System.out java/io/PrintStream getstatic fatorial.numero I invokevirtual java/io/PrintStream.print(I)V getstatic java/lang/System.out java/io/PrintStream ldc " e: " invokevirtual java/io/PrintStream.print(java/lang/String)V getstatic java/lang/System.out java/io/PrintStream getstatic fatorial.numero I invokestatic fatorial.fatorial(I)I invokevirtual java/io/PrintStream.print(I)V getstatic java/lang/System.out java/io/PrintStream invokevirtual java/io/PrintStream.println()V return } }
ここで、このプロジェクトの学習の旅は終わります。
このプロジェクトでは、コンパイラーの分野でいくつかの興味深いことを調べることができます (生成されたコードの最適化など)。おそらく近い将来、最適化を行った新しいシリーズを開始することになるでしょう :-)
プロジェクトの完全なコードとドキュメントが含まれるリポジトリはここにあります。
以上が火災テスト: 再帰的階乗の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。