可使用system.setout()和system.seterr()配合printstream将标准输出或错误输出重定向到文件,需手动处理异常、建议恢复原始流,多线程安全但内容可能交错,生产环境推荐log4j等日志框架。

可以使用 System.setOut() 和 System.setErr() 配合 PrintStream 将标准输出(System.out)或错误输出(System.err)重定向到文件。
重定向 System.out 到文件
创建一个指向目标文件的 PrintStream,然后传给 System.setOut():
- 需手动处理异常(如
FileNotFoundException) - 建议在使用完毕后恢复原始输出流,避免影响后续日志或调试
- 示例代码:
PrintStream fileOut = new PrintStream(new FileOutputStream("output.log"));
System.setOut(fileOut);
System.out.println("这行会写入 output.log");
// 使用完记得关闭并恢复(可选)
fileOut.close();
同时重定向输出和错误流
若希望将 System.out 和 System.err 都写入同一文件,可分别设置:
- 用同一个
PrintStream实例赋值给setOut()和setErr(),确保输出与错误混写在同一文件 - 若需分离,应创建两个独立的
PrintStream(对应不同文件) - 注意:多个线程共用同一
PrintStream是线程安全的,但内容可能交错
恢复原始控制台输出
重定向后如需切回终端显示,可提前保存原始流:
- 在调用
setOut()前,用System.out获取原始PrintStream - 后续调用
System.setOut(originalOut)即可还原 - 这是良好实践,尤其在单元测试或命令行工具中
PrintStream originalOut = System.out;
System.setOut(new PrintStream("log.txt"));
// ... 执行业务逻辑
System.setOut(originalOut); // 恢复
注意事项与替代方案
该方式适用于简单日志或调试场景,但有局限性:
- 无法按级别(INFO/WARN/ERROR)过滤或格式化
- 不支持滚动、异步写入等高级功能
- 生产环境推荐使用 Log4j、SLF4J 等日志框架
- JDK9+ 中
System.out是 final 字段,但setOut()仍有效,只是不能直接赋值










