-1

CompileAndRun クラスを使用して、HelloWorld クラスをコンパイルして実行できるようになりました。これを使用して、ユーザーの入力が必要なプログラムを実行したいと考えています。これは、コマンド ライン引数または stdin を介して受け取った入力のいずれかです。

import java.io.File;
import java.io.IOException;
import java.io.InputStream;

public class CompileAndRun {

public static void main(String[] args) {
    new CompileAndRun();
}

public CompileAndRun() {
    try {
        int result = compile("compileandrun/HelloWorld.java");
        System.out.println("javac returned " + result);
        result = run("compileandrun.HelloWorld");
    } catch (IOException | InterruptedException ex) {
        ex.printStackTrace();
    }
}

public int run(String clazz) throws IOException, InterruptedException {        
    ProcessBuilder pb = new ProcessBuilder("java", clazz);
    pb.redirectError();
    pb.directory(new File("src"));
    Process p = pb.start();
    InputStreamConsumer consumer = new InputStreamConsumer(p.getInputStream());
    consumer.start();

    int result = p.waitFor();

    consumer.join();

    System.out.println(consumer.getOutput());

    return result;
}

public int compile(String file) throws IOException, InterruptedException {        
    ProcessBuilder pb = new ProcessBuilder("javac", file);
    pb.redirectError();
    pb.directory(new File("src"));
    Process p = pb.start();
    InputStreamConsumer consumer = new InputStreamConsumer(p.getInputStream());
    consumer.start();

    int result = p.waitFor();

    consumer.join();

    System.out.println(consumer.getOutput());

    return result;        
}

public class InputStreamConsumer extends Thread {

    private InputStream is;
    private IOException exp;
    private StringBuilder output;

    public InputStreamConsumer(InputStream is) {
        this.is = is;
    }

    @Override
    public void run() {
        int in = -1;
        output = new StringBuilder(64);
        try {
            while ((in = is.read()) != -1) {
                output.append((char) in);
            }
        } catch (IOException ex) {
            ex.printStackTrace();
            exp = ex;
        }
    }

    public StringBuilder getOutput() {
        return output;
    }

    public IOException getException() {
        return exp;
    }
}
}
4

3 に答える 3

1

私の意見では、より良い解決策はJava 6 Compiler APIを使用することです。javax.tools パッケージのドキュメントも参照してください。

于 2013-07-05T15:39:17.997 に答える
0

ProcessBuilder次のようにコンストラクターに別の文字列を追加することで、コマンドライン引数を追加できますProcessBuilder pb = new ProcessBuilder("java", clazz,"argument");

于 2013-07-05T15:41:08.880 に答える
0

そのためには、Runtime クラスを使用する必要があります。

コード ファイル --x.java を実行する -y.java

ここで、Runtime クラスの「exec」関数を使用する必要があります。

このような

プロセス p=Runtime.getRuntime().exec("cmd /c javac y.java && java y.java");

そのため、プログラムはこのクラスによって作成されたプロセスから実行されます。

このメソッドはプロセスを返します

したがって、実行したばかりのこのコマンドの出力を受け取るには、次のようにします

p.getOutputStream() // この outputStream を出力ストリーム wtiter でラップするか、Printwriter の場合もあり、null でなくなるまで読み取ります

そして最後に出力します。

于 2013-07-05T15:22:55.977 に答える