Java IO操作——System类对IO的支持(System.out、System.err、System.in)

学习目标

掌握System对IO的三种支持:
System.out
System.err
System.in
掌握System.out及System.err的区别
掌握输入、输出重定向

System类的常量
System表示系统类,实际上在JAVA中也对IO给予了一定的支持
1、public static final PrintStream out 常量 对应系统标准输出,一般是显示器
2、public static final PrintStream err 常量 错误信息输出
3、public static final InputStream in 常量 对应标准输出,一般是键盘
使用static final关键字声明的变量是全局常量,只要是常量,则所有的单词字母必须全部大写,按照现在的标准:System.OUT —> System.out

System.out

使用System.out输出的时候就是将输出的位置定义在了显示器之中。
FileOutputStream是定位在文件里,而System.out是定位在屏幕上输出
PrintStream就是OutputStream的子类
import java.io.OutputStream ;
import java.io.IOException ;
public class SystemDemo01{
	public static void main(String args[]){
		OutputStream out = System.out ;		// 此时的输出流是向屏幕上输出
		try{
			out.write("hello world!!!".getBytes()) ;	// 向屏幕上输出
		}catch(IOException e){
			e.printStackTrace() ;	// 打印异常
		}
		try{
			out.close() ;	// 关闭输出流
		}catch(IOException e){
			e.printStackTrace() ;
		}
	}
};


很明显就是对象多态性的体现,根据实现的子类不同,完成的功能也不相同。

System.err

System.err 表示的是错误的标准输出,如果程序中出现了错误的话,则直接使用System.err进行输出即可。程序如下:
public class SystemDemo02{
	public static void main(String args[]){
		String str = "hello" ;		// 声明一个非数字的字符串
		try{
			System.out.println(Integer.parseInt(str)) ;	// 转型
		}catch(Exception e){
			System.err.println(e) ;
		}
	}
};


使用System.out输出错误 如下:
public class SystemDemo03{
	public static void main(String args[]){
		String str = "hello" ;		// 声明一个非数字的字符串
		try{
			System.out.println(Integer.parseInt(str)) ;	// 转型
		}catch(Exception e){
			System.out.println(e) ;
		}
	}
};


System.out 和System.err 的区别:
System.out和System.err都是PrintStream的实例化对象,而且通过代码可以发现,两者都可以输出错误信息,但是一般来讲System.out是将信息显示给用户看,是正常的信息显示,而System.err的正好相反是不希望用户看到的,会直接在后台打印,是专门显示错误的。
一般来讲,如果要输出错误信息的时候最好不要使用System.out而是直接使用System.err 这一点只能从其概念上划分。

以上的代码也可以使用System.out输出,只能从概念上划分。
切记:System.out是希望用户看到的,而System.err是不希望用户看到的。

System.in

System.in实际上是一个键盘的输入流,其本身是InputStream类型的对象。那么,此时就可以利用此方式完成从键盘读取数据的功能。
InputStream对应的是输入流,输入流的话肯定是从指定位置读取的,之前使用的是FileInputStream,是从文件中读取的。
import java.io.InputStream ;
public class SystemDemo04{
	public static void main(String args[]) throws Exception {	// 所有异常抛出
		InputStream input = System.in ;	// 从键盘接收数据
		byte b[] = new byte[1024] ;	// 开辟空间,接收数据
		System.out.print("请输入内容:") ;	// 提示信息
		int len = input.read(b) ;	// 接收数据
		System.out.println("输入的内容为:" + new String(b,0,len)) ;
		input.close() ;	// 关闭输入流
	}
};

所有的数据输入进去了,但是以上的操作存在如下问题:
问题一:指定了输入数据的长度,如果现在输入的数据超过了长度范围,只能输入部分的数据。
问题二:如果byte数组是奇数的话,则还可能出现中文乱码的情况,因为一个字符是两个字节。示例如下:
import java.io.InputStream ;
public class SystemDemo04{
	public static void main(String args[]) throws Exception {	// 所有异常抛出
		InputStream input = System.in ;	// 从键盘接收数据
		byte b[] = new byte[3] ;	// 开辟空间,接收数据
		System.out.print("请输入内容:") ;	// 提示信息
		int len = input.read(b) ;	// 接收数据
		System.out.println("输入的内容为:" + new String(b,0,len)) ;
		input.close() ;	// 关闭输入流
	}
};


可以发现,开辟了三个字节的空间,但是两个字符需要四个字节的数组长度,所以剩下的一个字节就等于读到了半个字符,所以会出现乱码。
那么如果此时不指定byte数组的长度呢?是否可以完成输入的要求?
这样的话只能通过标志位的方式进行完成。实例如下:
import java.io.InputStream ;
public class SystemDemo05{
	public static void main(String args[]) throws Exception {	// 所有异常抛出
		InputStream input = System.in ;	// 从键盘接收数据
		StringBuffer buf = new StringBuffer() ;	// 使用StringBuffer接收数据
		System.out.print("请输入内容:") ;	// 提示信息
		int temp = 0 ;		// 接收内容
		while((temp=input.read())!=-1){
			char c = (char) temp ;	// 将数据变为字符
			if(c=='\n'){	// 退出循环,输入回车表示输入完成
				break ;
			}
			buf.append(c) ;	// 保存内容
		}
		System.out.println("输入的内容为:" + buf) ;
		input.close() ;	// 关闭输入流
	}
};


但是输入中文就会乱码。

这是因为每读取一个字节就将其转为字符,字母和数字都是占1个字节 可以正常显示。但是如果是中文的话,就相当于每读取到一个字节就是半个字符就进行转化,所以导致乱码的错误。
最好的输出方式:
最好的输出方式是将全部输入的数据暂时存放在一块内存之上,之后一次性的从内存中读取数据,这样所有数据就整体只读了一次,则不会造成乱码,而且也不会受到长度的限制。

如果要想实现以上的功能,则只能通过IO中的下一个类 BufferedReader类完成。

输入输出重定向

从之前的操作中知道System.out、System.err、System.in三个常量的作用,但是通过System类也可以改变System.in的输入流来源,以及System.out和System.err两个输出流的输出位置。
1、public static void setOut(PrintStream out) 普通方法 重定向“标准”输出流
2、public static void setErr(PrintStream err) 普通方法 重定向 “标准”错误输出流
3、public static void setIn(InputStream in) 普通方法 重定向“标准” 输入流

为System.out输出重定向

使用setOut()方法完成
import java.io.File ;
import java.io.FileOutputStream ;
import java.io.PrintStream ;
public class SystemDemo06{
	public static void main(String args[]) throws Exception {
		System.setOut(
			new PrintStream(
				new FileOutputStream("d:" + 
					File.separator + "red.txt"))) ;	// System.out输出重定向
		System.out.print("刘勋") ;	// 输出时,不再向屏幕上输出
		System.out.println(",黄淮学院") ;
	}
};

此时将输出的位置重定向,所以所有的内容都向指定的文件中打印。
实际上通过此操作就可以完成错误的重定向。
System.out是希望用户看得到信息,一旦有错误,最好保存起来。
import java.io.File ;
import java.io.FileOutputStream ;
import java.io.PrintStream ;
public class SystemDemo07{
	public static void main(String args[]){
		String str = "hello" ;		// 声明一个非数字的字符串
		try{
			System.out.println(Integer.parseInt(str)) ;	// 转型
		}catch(Exception e){
			try{
				System.setOut(
					new PrintStream(
						new FileOutputStream("d:"
							+ File.separator + "err.log"))) ;	// 输出重定向
			}catch(Exception e1){
			
			}
			System.out.println(e) ;
		}
	}
};

为System.err重定向

利用System.err向屏幕上输出信息,此时,为了方便起见,使用内存操作流。
import java.io.ByteArrayOutputStream ;
import java.io.PrintStream ;
public class SystemDemo08{
	public static void main(String args[]) throws Exception{	// 所有异常抛出
		ByteArrayOutputStream bos = null ;		// 声明内存输出流
		bos = new ByteArrayOutputStream() ;		// 实例化
		System.setErr(new PrintStream(bos)) ;	// 输出重定向
		System.err.print("刘勋") ;	// 错误输出,不再向屏幕上输出
		System.err.println("是好人") ;			// 向内存中输出
		System.out.println(bos) ;	// 输出内存中的数据
	}
};

一般不建议去修改System.err的输出位置,因为这样的信息都不太希望用户可以看见。

为System.in重定向

默认情况下System.in是指屏幕的建瓯按输入,也可以通过setIn()方法,将其输入流的位置改变,例如,现在从文件中读取。
有如下文件:demo.txt

使用System.in将数据读取进来
import java.io.FileInputStream ;
import java.io.InputStream ;
import java.io.File ;
public class SystemDemo09{
	public static void main(String args[]) throws Exception{	// 所有异常抛出
		System.setIn(new FileInputStream("d:"
			+ File.separator + "demo.txt")) ;	// 设置输入重定向
		InputStream input = System.in ;	// 从文件中接收数据
		byte b[] = new byte[1024]	;// 开辟空间,接收数据
		int len = input.read(b) ;	//接收
		System.out.println("输入的内容为:" + new String(b,0,len)) ;
		input.close() ;	// 关闭输入流
	}
};

总结:

三个常量的使用:
  • System.out是希望用户可以看见的信息。用IDE(Eclipse)的话错误信息使用黑颜色显示的。
  • System.err 是不希望用户可以看见的信息。则在IDE中将以红色的文字显示错误信息。
  • System.in 对应键盘输入
  • 以上三个常量的输入、输出都可以重定向,但是一般建议只修改setOut的重定向。
  • System.in读取的时候会出现中文乱码的问题,则可以通过BufferedReader完成读取功能。
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值