java中System.out其实是一个对象

259 阅读3分钟

背景

函数式编程学习中,介绍方法引用中的对象::方法名的时候,对象用的是System.out,之前一直以为是一个内部类(怪丢人的),感觉很新奇,于是去查了下,在此做个记录

详情

在Java中 System.out 是一个对象。具体来说,System.outPrintStream 类的一个静态成员变量,它代表标准输出流(通常是控制台)。PrintStream 类继承自 FilterOutputStream,进而继承自 OutputStream,它是处理字节输出流的抽象类。

详细说明

  1. System

    • System 是一个包含系统级操作的最终类(final class),例如标准输入、输出和错误流。
    • 它提供了三个静态成员变量来访问这些流:
      • System.in:标准输入流,类型为 InputStream,通常连接到键盘。
      • System.out:标准输出流,类型为 PrintStream,通常连接到控制台。
      • System.err:标准错误流,类型为 PrintStream,也通常连接到控制台,但用于输出错误信息。
  2. PrintStream

    • PrintStream 是一个输出流类,专门用于格式化输出。它提供了一系列方便的方法来打印不同类型的值(如字符串、整数、浮点数等)。
    • PrintStream 的常见方法包括:
      • print()println():用于打印各种类型的数据,println() 会在输出后自动添加换行符。
      • printf():用于格式化输出,类似于C语言中的 printf 函数。
      • format():与 printf() 功能相同,只是名称不同。
      • close():关闭输出流,释放资源。
  3. 使用示例

public class Main {
    public static void main(String[] args) {
        // 使用 System.out 打印普通文本
        System.out.println("Hello, World!");

        // 使用 System.out 打印格式化文本
        int number = 42;
        System.out.printf("The answer is: %d%n", number);

        // 使用 System.err 打印错误信息
        System.err.println("An error occurred!");
    }
}

为什么 System.out 是一个对象?

  • 封装性System.out 是一个 PrintStream 对象,它封装了底层的输出流操作。通过这个对象,你可以调用其提供的各种方法来进行输出操作,而不需要直接处理复杂的流操作。

  • 灵活性:作为一个对象,System.out 可以被重定向到其他输出目标。例如,你可以将标准输出重定向到文件或网络流,而不仅仅是控制台。这在日志记录、测试和调试中非常有用。

  • 多态性PrintStream 实现了 FlushableCloseable 接口,这意味着它可以与其他流对象一起使用,并且可以作为参数传递给需要这些接口的方法。

重定向标准输出

你可以通过重新赋值 System.out 来改变它的输出目标。例如,将输出重定向到一个文件:

import java.io.PrintStream;
import java.io.FileOutputStream;
import java.io.IOException;

public class Main {
    public static void main(String[] args) {
        try {
            // 创建一个新的 PrintStream,指向一个文件
            PrintStream fileOut = new PrintStream(new FileOutputStream("output.txt"));

            // 将 System.out 重定向到文件
            System.setOut(fileOut);

            // 现在所有 System.out 的输出都会写入文件
            System.out.println("This will be written to output.txt");

            // 关闭文件输出流
            fileOut.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

总结

  • System.outPrintStream 类的一个静态成员变量,代表标准输出流。
  • 可以通过 System.out 调用 PrintStream 提供的各种方法来进行格式化输出。
  • System.out 作为一个对象,具有封装性、灵活性和多态性的特点,使得输出操作更加方便和强大。

通过理解 System.out 的本质,可以更好地利用Java的I/O功能,进行更复杂和灵活的输出操作。