The various overloads of Runtime.getRuntime().exec(...)
take either an array of strings or a single string. The single-string overloads of exec()
will tokenise the string into an array of arguments, before passing the string array onto one of the exec()
overloads that takes a string array. The ProcessBuilder
constructors, on the other hand, only take a varargs array of strings or a List
of strings, where each string in the array or list is assumed to be an individual argument. Either way, the arguments obtained are then joined up into a string that is passed to the OS to execute.
So, for example, on Windows,
Runtime.getRuntime().exec("C:DoStuff.exe -arg1 -arg2");
will run a DoStuff.exe
program with the two given arguments. In this case, the command-line gets tokenised and put back together. However,
ProcessBuilder b = new ProcessBuilder("C:DoStuff.exe -arg1 -arg2");
will fail, unless there happens to be a program whose name is DoStuff.exe -arg1 -arg2
in C:
. This is because there's no tokenisation: the command to run is assumed to have already been tokenised. Instead, you should use
ProcessBuilder b = new ProcessBuilder("C:DoStuff.exe", "-arg1", "-arg2");
or alternatively
List<String> params = java.util.Arrays.asList("C:DoStuff.exe", "-arg1", "-arg2");
ProcessBuilder b = new ProcessBuilder(params);
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…