使用带有输入和输出流的ProcessBuilder的Java程序不起作用

时间:2014-10-09 21:03:53

标签: java c processbuilder

我已经在Stack Overflow上搜索了类似的问题,但是,我似乎无法做到这一点。

我有一个java程序,必须使用 ProcessBuilder 来加载C可执行文件。该文件只是通过CLI接受一个字符串并将其转换为大写。 java程序使用ProcessBuilder创建一个系统进程来管理这个可执行文件,并且必须发送字符串并接收转换后的字符串以在CLI中打印它。

这是 uppercases.c

的代码
#include <stdio.h>

int main(int argc, char *argv[]) {
    char text[1024];
    scanf("%s", &text[0]);

    int i;
    for(i = 0; i < strlen(text); i++) {
        text[i] = toupper(text[i]);
    }

    printf("%s\n", text);
    return 0;
}

我用

编译了它
$ gcc uppercases.c -o uppercases

运行它
$ ./uppercases

一切正常。现在这是 Uppercase.java 的代码。我必须创建一个OutputStream来将字符串发送到C可执行文件(大写),然后我创建一个InputStream来保存其输出并将其打印到CLI:

public class Uppercase {

public static void main(String[] command) {
    String textIn, textOut;
    Scanner reader = new Scanner(System.in);

    // This is what we want to send
    System.out.println("Write something: ");
    textIn = reader.nextLine();

    try {
        // Here I create a process to handle "uppercases"
        Process process = new ProcessBuilder(command).start();

        OutputStream os = process.getOutputStream();
        BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(os));

        // According to me, this will send the string to "uppercases"
        bw.write(textIn);
        bw.flush();

        // This is to read the output of "uppercases"
        InputStream is = process.getInputStream();
        BufferedReader br = new BufferedReader (new InputStreamReader(is));

        while ((textOut = br.readLine()) != null) {
             System.out.println(textOut);
        }

        os.close();
        is.close();

    } catch (IOException e) {
        System.out.println("I/O error:" + e.getMessage());
    } catch (Exception e) {
        System.out.println("Error:" + e.getMessage());
    }
  }
}

要编译,我输入:

$ javac Uppercase.java

执行:

$ java Uppercase ./uppercases

问题是,当我输入一个字符串然后点击回车时,光标会永远停留在那里,我再次点击输入并且没有任何反应,最后我必须按CTRL + C退出。任何帮助将不胜感激。

1 个答案:

答案 0 :(得分:2)

所有这些都适用于您的java程序,但有一个例外:您使用正确刷新的BufferedWriter,但由于您编写的行不包含换行符,C程序仍会等待更多输入。< / p>

如果你写:

// According to me, this will send the string to "uppercases"
bw.write(textIn);
bw.write("\n");
bw.flush();

这就足够了,程序正常终止。

但如果你真的希望这些东西能够防弹,你应该关闭bw以清楚地向子进程表明不应该等待更多输入:

// According to me, this will send the string to "uppercases"
bw.write(textIn);
bw.close();

然后程序正常终止(并且正确),即使没有结束新行。当然,在这种情况下,最后os.close()不再是必要的,但仍然是无害的。