You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java调用lowercase.perl脚本异常:<lower.eng>参数无法正常工作

解决Java调用Perl脚本时输入重定向失效的问题

我帮你捋清楚问题出在哪:当你在终端直接跑perl lowercase.perl < lower.eng时,< lower.eng是shell负责处理的输入重定向,它会把lower.eng的内容作为Perl脚本的标准输入。但Java的Runtime.exec()或者ProcessBuilder默认是直接启动Perl进程,不会通过shell解析命令,所以< lower.eng会被当成普通的命令行参数传给你的Perl脚本,而不是实现输入重定向——这就是为什么脚本能执行,但参数没生效的原因。

下面给你两种可行的解决方案:

方案1:通过shell执行整个命令

既然重定向是shell的功能,那我们可以让Java启动一个shell进程,让shell帮我们处理重定向逻辑。

Linux/macOS系统

用bash -c来包裹完整的命令:

import java.io.IOException;

public class CallPerlScript {
    public static void main(String[] args) {
        try {
            // 完整命令交给bash处理,包括重定向
            ProcessBuilder pb = new ProcessBuilder("bash", "-c", "perl lowercase.perl < lower.eng > output.txt");
            // 确保工作目录是脚本和文件所在的目录
            pb.directory(new java.io.File(System.getProperty("user.dir")));
            Process process = pb.start();
            
            // 等待脚本执行完成,并获取退出码
            int exitCode = process.waitFor();
            System.out.println("脚本执行完成,退出码:" + exitCode);
        } catch (IOException | InterruptedException e) {
            e.printStackTrace();
        }
    }
}

Windows系统

换成cmd /c:

import java.io.IOException;

public class CallPerlScript {
    public static void main(String[] args) {
        try {
            ProcessBuilder pb = new ProcessBuilder("cmd", "/c", "perl lowercase.perl < lower.eng > output.txt");
            pb.directory(new java.io.File(System.getProperty("user.dir")));
            Process process = pb.start();
            
            int exitCode = process.waitFor();
            System.out.println("脚本执行完成,退出码:" + exitCode);
        } catch (IOException | InterruptedException e) {
            e.printStackTrace();
        }
    }
}

方案2:Java手动处理输入输出(跨平台推荐)

这种方式不需要依赖shell,Java自己负责读取输入文件,把内容传给Perl进程,再把Perl的输出写入目标文件,兼容性更好。

import java.io.*;

public class CallPerlScript {
    public static void main(String[] args) {
        try {
            // 启动Perl脚本进程,不需要传重定向参数
            ProcessBuilder pb = new ProcessBuilder("perl", "lowercase.perl");
            pb.directory(new java.io.File(System.getProperty("user.dir")));
            Process process = pb.start();
            
            // 1. 读取lower.eng的内容,写入Perl进程的标准输入
            try (BufferedReader inputFileReader = new BufferedReader(new FileReader("lower.eng"));
                 OutputStream processInput = process.getOutputStream()) {
                String line;
                while ((line = inputFileReader.readLine()) != null) {
                    processInput.write((line + System.lineSeparator()).getBytes());
                }
                // 关闭输入流,告诉Perl脚本没有更多输入了
                processInput.flush();
                processInput.close();
            }
            
            // 2. 读取Perl进程的标准输出,写入output.txt
            try (BufferedReader processOutput = new BufferedReader(new InputStreamReader(process.getInputStream()));
                 BufferedWriter outputFileWriter = new BufferedWriter(new FileWriter("output.txt"))) {
                String line;
                while ((line = processOutput.readLine()) != null) {
                    outputFileWriter.write(line);
                    outputFileWriter.newLine();
                }
            }
            
            // 等待脚本执行完成
            int exitCode = process.waitFor();
            System.out.println("脚本执行完成,退出码:" + exitCode);
            
        } catch (IOException | InterruptedException e) {
            e.printStackTrace();
        }
    }
}

额外注意事项

  • 确保你的Java程序的工作目录确实是脚本和文件所在的目录,如果不确定,可以用绝对路径替换文件名(比如/home/you/yourdir/lower.eng)。
  • Linux/macOS下如果直接执行./lowercase.perl,要先给脚本加执行权限:chmod +x lowercase.perl,否则还是用perl lowercase.perl的方式调用更稳妥。
  • 可以打印Perl脚本的错误输出(process.getErrorStream())来排查问题,比如脚本有没有报错。

内容的提问来源于stack exchange,提问作者user9238004

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 07:18:57