【问题标题】:executing cat command from java program does not work as expected从 java 程序执行 cat 命令不能按预期工作
【发布时间】:2015-08-17 02:39:47
【问题描述】:

我正在尝试使用 java 程序中的 cat 命令将两个文件合并为一个。包含 cat 命令的代码行获取两个文件 file1 和 file2 并写入名为 combinefile 的第三个文件。但是,我观察到的是,我的程序并没有创建这个文件(combinedfile)并写入它,而是仅在终端上显示输出。

如何确保确实将这两个文件复制到第三个文件。

import java.io.BufferedReader;
import java.io.InputStreamReader;

public class ExecuteShellCommand 
{

    public static void main(String[] args) 
    {

        ExecuteShellCommand obj = new ExecuteShellCommand();

        String command = "cat file1 file2 > combinedfile";

        String output = obj.executeCommand(command);

        System.out.println(output);

    }

    private String executeCommand(String command) 
    {

        StringBuffer output = new StringBuffer();

        Process p;
        try 
        {
            p = Runtime.getRuntime().exec(command);
            p.waitFor();
            BufferedReader reader = new BufferedReader(new InputStreamReader(p.getInputStream()));

            String line = "";           

            while ((line = reader.readLine())!= null) 
            {
                output.append(line + "\n");
            }

        } catch (Exception e) {
            e.printStackTrace();
        }

        return output.toString();

    }

}

编辑:

我按照建议尝试了 ProcessBuilder,但出现此错误。 代码

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.*;
import java.util.*;

public class ExecuteShellCommand
{
    public static void main(String[] args) 
    {
        try
        {            
            ProcessBuilder builder = new ProcessBuilder("cat", "/home/PepperBoy/Desktop/file1.txt","/home/PepperBoy/Desktop/file2.txt");
            File combinedFile = new File("/home/PepperBoy/Desktop/file3.txt");
            builder.redirectOutput(combinedFile);
            builder.redirectError(combinedFile);
            Process p = builder.start();
        } 
        catch(IOException e)
        {
                e.printStackTrace();
        }

    }
}

错误

ExecuteShellCommand.java:14: cannot find symbol
symbol  : method redirectOutput(java.io.File)
location: class java.lang.ProcessBuilder
            builder.redirectOutput(combinedFile);

【问题讨论】:

    标签: java shell exec cat


    【解决方案1】:

    我找到了related question。从那里找到的几个答案中总结有用的东西,文件重定向需要一个 shell,但 exec 没有 shell 上下文。幸运的是,您可以使用ProcessBuilder 执行带有重定向的进程。对于您的情况,这看起来像:

    public static void main(String[] args) 
    {
    
        try{            
            ProcessBuilder builder = new ProcessBuilder("cat", "file1","file2");
            File combinedFile = new File("combinedFile");
            builder.redirectOutput(combinedFile);
            builder.redirectError(combinedFile);
            Process p = builder.start();
        } catch(IOException e){
            //handle exception...
        }
    
    }
    

    注意:调用redirectErrorredirectOutput 时可能会收到错误消息,指出找不到符号。如果您针对 1.7 之前的 Java 版本进行编译,则会发生这种情况,因为 1.7 is when these methods were introduced. 如果可以升级您的 Java,这样做将消除此错误。

    如果不能升级Java,下面的代码会起作用:

    public static void main(String[] args) 
    {
    
        try{            
            ProcessBuilder builder = new ProcessBuilder("cat", "file1","file2");
            File combinedFile = new File("combinedFile");
            Process p = builder.start();
    
            InputStream isFromCat = p.getInputStream();
            OutputStream osCombinedFile = new FileOutputStream(combinedFile);
    
            byte[] buffer = new byte[1024];
            int read = 0;
            while((read = isFromCat.read(buffer)) != -1) {
                osCombinedFile.write(buffer, 0, read);
            }
    
        } catch(IOException e){
            //handle exception...
        }
    
    }
    

    还可能值得注意的是,对cat 进行系统调用并不是从Java 组合文件的最佳方式。我一直假设这是一个玩具案例,为您代表一个更复杂的用例。如果您真正想做的只是合并两个文件,您应该编写代码以避免系统调用,只需通过将两个文件作为输入流读入然后将它们写出结果文件来附加文件。如果您无法弄清楚,那么这些细节肯定属于另一个问题。

    【讨论】:

    • @PepperBoy 好的,我也调整了答案。您正在针对哪个版本的 Java 进行编译?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-10-19
    • 2020-05-23
    • 2016-09-29
    • 1970-01-01
    • 2013-10-25
    • 1970-01-01
    相关资源
    最近更新 更多