环境windows下,比如我要通过java调用一个程序,程序有一个参数:
程序路径:C:\my dir\myexe.exe
参数:[color=red]param="my parameter"[/color]
调用时:cmd[0] = "C:\my dir\myexe.exe"
cmd[1] = "param=\"my parameter\""
说明:其中整个红色部分是参数,参数中有一个空格,我使用Runtime.getRuntime().exec(String[] cmdarry)以后,发现传进去的参数个数为3,从my后面被截断了,而且引号也不见了,难道不是把cmd[1]整个当作参数吗?疑惑。

请教Runtime.getRuntime().exec(String[] cmdarry)参数的问题
- 写回答
- 好问题 0 提建议
- 关注问题
- 邀请回答
-
2条回答 默认 最新
- rednaxelafx 2008-12-26 17:52关注
啊,原来如此。JDK里java.lang.ProcessImpl.start()的实现:
[quote="JDK 1.6.0_05"][code="java"] // System-dependent portion of ProcessBuilder.start()
static Process start(String cmdarray[],
java.util.Map environment,
String dir,
boolean redirectErrorStream)
throws IOException
{
String envblock = ProcessEnvironment.toEnvironmentBlock(environment);
return new ProcessImpl(cmdarray, envblock, dir, redirectErrorStream);
}private long handle = 0; private FileDescriptor stdin_fd; private FileDescriptor stdout_fd; private FileDescriptor stderr_fd; private OutputStream stdin_stream; private InputStream stdout_stream; private InputStream stderr_stream; private ProcessImpl(String cmd[], String envblock, String path, boolean redirectErrorStream) throws IOException { // Win32 CreateProcess requires cmd[0] to be normalized cmd[0] = new File(cmd[0]).getPath(); StringBuilder cmdbuf = new StringBuilder(80); for (int i = 0; i < cmd.length; i++) { if (i > 0) { cmdbuf.append(' '); } String s = cmd[i]; if (s.indexOf(' ') >= 0 || s.indexOf('\t') >= 0) { if (s.charAt(0) != '"') { cmdbuf.append('"'); cmdbuf.append(s); if (s.endsWith("\\")) { cmdbuf.append("\\"); } cmdbuf.append('"'); } else if (s.endsWith("\"")) { /* The argument has already been quoted. */ cmdbuf.append(s); } else { /* Unmatched quote for the argument. */ throw new IllegalArgumentException(); } } else { cmdbuf.append(s); } } String cmdstr = cmdbuf.toString(); stdin_fd = new FileDescriptor(); stdout_fd = new FileDescriptor(); stderr_fd = new FileDescriptor(); handle = create(cmdstr, envblock, path, redirectErrorStream, stdin_fd, stdout_fd, stderr_fd); java.security.AccessController.doPrivileged( new java.security.PrivilegedAction() { public Object run() { stdin_stream = new BufferedOutputStream(new FileOutputStream(stdin_fd)); stdout_stream = new BufferedInputStream(new FileInputStream(stdout_fd)); stderr_stream = new FileInputStream(stderr_fd); return null; } }); }[/code][/quote]
可以看到Java标准库自作主张的给带有空白字符的参数的头尾加了引号。也就是说原本给进去的参数是:
[quote]param="my parameter"[/quote]
的话,被处理了之后就变成:
[quote]"param="my parameter""[/quote]
于是Win32的CreateProcess看到的就是:
[quote]param=my parameter[/quote]
(引号会由操作系统决定如何吃掉)本回答被题主选为最佳回答 , 对您是否有帮助呢?解决 无用评论 打赏 举报