的Java执行命令不代码

问题描述:

我在我的Java程序运行一个命令调用java.lang.Runtime.exec(...)工作(一些FFMPEG命令)简单地传递给我的功能:的Java执行命令不代码

private static void RunCommand(String command) throws InterruptedException { 
     try { 
      // Execute command 
      Process proc = Runtime.getRuntime().exec(command); 
} 
} 

它适用于简单的FFMPEG情况,如ffmpeg -i input.avi -c copy output.avi

但是对于其中一个命令,显然它不运行。当我在命令行中复制/粘贴确切的字符串时,我可以运行它并查看输出文件。

ffmpeg -i "concat:/home/temp10.avi|/home/p2.avi|/home/temp15.avi" -c copy -y /home/output.avi 

这是下面的代码:

String c4="ffmpeg -i \"concat:"+dir+temp1+"|"+dir+ad+"|"+dir+temp3+"\" -c copy -y "+dir+output; 

这是怎么回事?任何猜测为什么它不能在代码中运行?如果"导致问题,为什么相应的字符串看起来不错?!

+1

它在我看来像这个exec函数不会执行shell风格的引用,只是简单地分割空白,所以你应该能够通过删除引号来修复它。如果文件名可能包含空格,则需要传递一个String数组来代替exec。 –

+0

你的意思是我应该删除引号吗? – Ariana

+0

哇!你是对的。 '''''''解决了这个问题,也许你想描述它,并且我将你标记为最佳答案? – Ariana

怎么写,它的命令:当shell中运行

ffmpeg -i "concat:/home/temp10.avi|/home/p2.avi|/home/temp15.avi" -c copy -y /home/output.avi 

作品。引号是shell语法的一部分,而不是ffmpeg语法的一部分。引用是必要的,因为|字符会导致shell在没有引用的情况下构建管道。当它被引用时,它只是传递给ffmpeg。

你想用java Runtime exec函数完成同样的事情,但exec不是一个shell。它不会执行管道,重定向,引用或替换。它将字符串拆分为空白字符串,并将结果字符串数组与unix execvp等效。

由于exec不会对|字符做任何特殊处理,所以不需要引用。你把这个字符串传给exec来完成同样的事情,上面的shell命令应该只是

ffmpeg -i concat:/home/temp10.avi|/home/p2.avi|/home/temp15.avi -c copy -y /home/output.avi 

有可能会碰到根据文件名的并发症。假设你的shell命令是这样的:

ffmpeg -i "concat:/home/temp 10.avi|/home/p2.avi|/home/temp15.avi" -c copy -y /home/output.avi 

(区别:第一个文件名temp 10.avi在它有一个空格)。现在是我们2个目的引用:防止|从创建一个管道,并防止空间分裂论点。如果你试试这个传递给exec去掉引号,它不会工作,因为该字符串将被分割,产生这种阵列的参数:

-i 
concat:/home/temp 
10.avi|/home/p2.avi|/home/temp15.avi 
-c 
copy 
-y 
/home/output.avi 

这不是想要的ffmpeg的;它想要包含完整输入规范的-i之后的单个字符串。你必须自己做分割字符串的工作,这样你就可以离开这个空间的说法,这样的:

Runtime.getRuntime().exec(
    new String[] { 
    "ffmpeg", 
    "-i", 
    "concat:/home/temp 10.avi|/home/p2.avi|/home/temp15.avi", 
    "-c", 
    "copy", 
    "-y", 
    "/home/output.avi" 
    } 
) 

在评论下面的例子看起来像

Runtime.getRuntime().exec(
    new String[] { 
    "ffmpeg", 
    "-i", 
    "sample.mp4", 
    "-i", 
    "ad.mp4", 
    "-filter_complex", 
    "[0:v]trim=0:15,setpts=PTS-STARTPTS[v0]; [1:v]trim=0:5,setpts=PTS-STARTPTS[v1]; [0:v]trim=20:30,setpts=PTS-STARTPTS[v2]; [v0][v1][v2]concat=n=3:v=1:a=0[out]", 
    "-map", 
    "[out]", 
    "output.mp4" 
    } 
) 

-filter_complex之后的字符串是单个参数,因为它在命令的shell版本中引用。它没有任何字符在shell中的""之间,而在Java中的""之间没有特殊字符,所以它可以不加修改地工作。

+0

运行此命令时遇到困难,你能帮我吗?'ffmpeg -i sample.mp4 -i ad.mp4 - filter_complex“[0:v] trim = 0:15,setpts = PTS-STARTPTS [v0]; [1:V]修剪= 0:5,setpts = PTS-STARTPTS [V1]; [0:V]修剪= 20:30,setpts = PTS-STARTPTS [V2]; [v0] [v1] [v2] concat = n = 3:v = 1:a = 0 [out]“-map”[out]“output.mp4' – Ariana