java流(1) 纯用法

1. FileReader  读文件三种粒度方式

FileReader 一个字节一个字节读

FileReader fr = null;
		try {
			fr = new FileReader("D:/out.java");
			int c = 0;
			while((c = fr.read())!=-1){//这里可以fr.read
				System.out.print((char)c);//这里打出来的是中文非乱码,因为FileReader是一个字符一个字符往外读,不会把中文读出一半。
										  //而且这里的\n 也能被记成换行符。
			}							
		} catch (IOException e) {
			e.printStackTrace();
		}

FileReader 一个char数组一个char数组的读

FileReader fr = null;
		try {
			fr = new FileReader("D:/out.txt");
			char[] cbuf = new char[1000];
			while(fr.read(cbuf)!=-1){//这里可以fr.read
				System.out.print(cbuf);//这里打出来的是中文非乱码,因为FileReader是一个字符一个字符往外读,不会把中文读出一半。
										  //而且这里的\n 也能被记成换行符。
				cbuf = new char[1000];//如果没有这句话,cbuf里会有脏数据,
			}		
			fr.close();
		} catch (IOException e) {
			e.printStackTrace();
		}


FileReader + BufferedReader 一行行读( 注意:一行行读只能套一层BufferedReader ,BufferedReader 和BufferedWriter 用的非常普遍 ),执行的内存空间示意图如下面图1

public static void main(String[] args) { 
	FileReader fr = null;
	String line = null;
	try {
		fr = new FileReader(new File("d:/file.txt"));
		BufferedReader br = new BufferedReader(fr);
		while((line = br.readLine())!=null ){ //readLine方法非常好用,即使为了这个方法,也要包一层bufferedReader 缓冲流
			System.out.println(line); //这个readLine方法底层调用的是Reader的read(char [])
		}
	} catch (Exception e) {
	e.printStackTrace();
	}
}

</pre><pre>

2. FileWriter 写文件 write()函数的两种参数调用方式

public void write(int c)
           throws IOException写入单个字符。要写入的字符包含在给定整数值的 16 个低位中,16 高位被忽略。 
用于支持高效单字符输出的子类应重写此方法。 

FileWriter bw = null ;
try {
	bw = new FileWriter("D:/out.txt");
	for(int i=0;i<50000;i++) //此处的i取后16位,2的16次方能表示65536个字符,所以此处写50000都能显示。这里相当于我们把unicode大多数国家的字符都写了进去
		bw.write(i);
	bw.close();
} catch (IOException e) {
	e.printStackTrace();
}

public abstract void write(char[] cbuf,
                           int off,
                           int len)
                    throws IOException写入字符数组的某一部分。 
					
public void write(String str)
       throws IOException写入字符串。
		   
public void writeFile(){
	FileWriter bw = null ;
	bw = new FileWriter("D:/result.txt");//注意这个路径符号
	bw.write("warm up");//这里的write(String)就是调用了String的toCharArray()方法,最终调用上面的write(char[] )方法
	bw.write("first");
	bw.write("second");
	bw.close();
}

FileWriter 写文件包一层处理流中的缓冲流

try {
			BufferedWriter bw = new BufferedWriter(new FileWriter("D:/out.txt"));
			for(int i=0;i<50000;i++){
				bw.write("\t"+i);
				bw.newLine();   //写完就换行
			}
			bw.flush();   //是把小桶(管道)里面的东西倒光,全部都写到文件里去。
			bw.close();   //如果上面不调用flush(),下面直接close()也行,flush和close最终都调用一个方法去flush
		} catch (IOException e) {
			e.printStackTrace();
		}


3. FileInputStream 读文件 (注意这里文件如果有中文,则System.out.print( (char) b) 是乱码)

/**
		 *这根管道就叫流,不同的管道,就是java的流。java的流和水流完全一致。流里面都是0101,
		     如果觉得不合适,就在流外面包一层强大一点的管道,这个管道可以帮你把0101转换成字符串
		 * 
		 */
		int b = 0;
		FileInputStream in =null;
		try {
			in = new FileInputStream("D:/Users/workspaceReal1/service/src/test/java/Iplong.java");
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		}

		long num = 0 ;
		try {
			while((b = in.read())!=-1){
				System.out.print((char) b); //这里如果是int / byte,则显示数字,所以强转成char,显示字符
							    //如果被读文件里有中文,则出现乱码
				num++;
				if(num % 1000 == 0)//这里是为了照顾控制台一行输出的字符数限制
					System.out.println();
			}
			in.close();
		} catch (IOException e) {
			e.printStackTrace();
			System.exit(1);
		}


4. FileOutputStream 写文件(注意这里文件如果有中文,则out.write( b ) 不是乱码,是正常的中文)

/**
		 *这根管道就叫流,不同的管道,就是java的流。java的流和水流完全一致。流里面都是0101,
		     如果觉得不合适,就在流外面包一层强大一点的管道,这个管道可以帮你把0101转换成字符串
		 * 
		 */
		int b = 0;
		FileInputStream in =null;
		FileOutputStream out = null;
		try {
			in = new FileInputStream("D:/Users/workspaceReal1/service/src/test/java/Iplong.java");
			out = new FileOutputStream("D:/out.java");//FileOutputStream 在没有这个文件时候,会自动创建这个文件
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		}

		long num = 0 ;
		try {
			while((b = in.read())!=-1){
				//System.out.print((char) b);
				out.write(b);//这里不是乱码,是正常的中文
				num++;
				if(num>3750)//如果加上这句,卡在文件中文的一半,则会出现一点点乱码如下图。
					break;	//原因:无论这里是char/int/byte,底层二进制都是一样的。一股脑写入文件,
							//不会出现乱码。中途输出char/int/byte型,则出现一半中文。如果是char型,则是乱码,
							//如果是int/byte则是数字0~255,这两个类型数据相等。
			}
			in.close();
		} catch (IOException e) {
			e.printStackTrace();
			System.exit(1);
		}
		System.out.println("total "+num+" bytes");

图 1  两部分缓冲的关系

5. outputstreamWriter 写文件

long longvar = 456;
		//String longvar = "你好";   //上面的long 型和下面的string 型都可以非乱码写入文件,改一个utf16 则是乱码,原因不明
		OutputStreamWriter osw;  
        try {                             
            FileOutputStream ss = new FileOutputStream(new File("D:/out.txt"));  
            ss.write(String.valueOf(longvar).getBytes());//如果直接用 FileOutputStream,则write方法调用  ss.write("你好".getBytes());  
            osw = new OutputStreamWriter(new FileOutputStream(new File("D:/out.txt"),true));  
            osw.write(String.valueOf(longvar));    
            osw.flush(); 
            System.out.println(osw.getEncoding());//这里显示的是当前Windows系统默认的编码是,UTF8。  
                                  //没有指定编码的情况下,OutputStreamWriter就使用当前系统默认的编码  
            //上面输出是乱码,now指定个编码,这里true的意思是在原来文件基础上追加,不写true,则把原文件擦掉  
            osw = new OutputStreamWriter(new FileOutputStream(new File("D:/out.txt"),true),"utf8");  
            osw.write(String.valueOf(longvar));  
            System.out.println(osw.getEncoding());//UTF-16  
            osw.flush();  
            osw.close();  
        } catch (IOException e) {  
            // TODO Auto-generated catch block  
            e.printStackTrace();  
        }  



6.InputStreamReader 读标准输入

InputStreamReader isr = new InputStreamReader(System.in);
		BufferedReader br =  new BufferedReader(isr);
		String s = null;
		try {                                                                          //这里是system.in 特殊,是同步的,你不输入,我不动
			s = br.readLine();   //如果不输入,程序卡在这不动,只有输入后点击回车,程序才往下走.这种叫阻塞式的方法,以后还会见到,很多。
			while(s!=null){
				if(s.equalsIgnoreCase("exit")) break;
				System.out.println(s.toUpperCase());
				s = br.readLine();    //和上面一样,如果不输入就卡住
			}
		} catch (IOException e) {
			e.printStackTrace();
		}

7.数据流 DataInputStream / DataOutputStream ( 或者 ByteArrayInputStream / ByteArrayOutputStream )

从字节数组读东西,用ByteArrayInputStream

long longvar = 12121212121245L;
		double doublevar = Math.random();
		DataOutputStream dos;
		DataInputStream dis;
		FileOutputStream fos;
		File file;
		ByteArrayOutputStream baos;
		ByteArrayInputStream bais ;
		try {
			//DataOutputStream + FileOutputStream,写文件
			file = new File("D:/out.txt");
			fos = new FileOutputStream(file);
			dos = new DataOutputStream(fos);
			dos.writeLong(longvar);// 写二进制数据,所以打开文件看到的是乱码,但是用DataInputStream 按你写的顺序读进来,就是正常值了
			dos.writeDouble(doublevar);
			dos.flush();
			dos.close();
			//DataInputStream + FileInputStream,读文件
			dis = new DataInputStream(new FileInputStream(file));
			System.out.println(dis.readLong());
			System.out.println(dis.readDouble());
			dis.close();
			//dataOutputStream + ByteArrayOutputStream ,写内存(内存中用byte[]数组存)
			baos = new ByteArrayOutputStream();
			dos = new DataOutputStream(baos);
			dos.writeLong(longvar);// 写二进制数据,所以打开文件看到的是乱码,但是用DataInputStream 按你写的顺序读进来,就是正常值了
			dos.writeDouble(doublevar);
			dos.flush();
			dos.close();
			//dataIntputStream + ByteArrayInputStream ,读内存<span style="font-family: Arial, Helvetica, sans-serif;">(内存中用byte[]数组存)</span>
			bais = new ByteArrayInputStream(baos.toByteArray());//内存中被写入的东西,以byte[]数组的方式呈现出来,此处长度                                                                    //已存内容的byte[]数组的真实长度
			//ByteArrayInputStream bais = new ByteArrayInputStream(buf);// 这里如果有,也可以用现成的buf直接初始化 
			dis = new DataInputStream(bais);
			System.out.println(dis.readLong());
			System.out.println(dis.readDouble());
			dis.close();
		} catch (IOException e) {
			e.printStackTrace();
		}

注意,dataInputStream是java原生的,比较慢,用hessian2

ByteArrayOutputStream byt1=new ByteArrayOutputStream();
            aerospikeItem.setValue(CompressUtil.gzipToByteArray(value));
            Hessian2Output hessian2Output = new Hessian2Output(byt1);
            hessian2Output.writeObject(aerospikeItem);
            hessian2Output.flush();
            oArr1 = byt1.toByteArray();
        }
        hessian2Output.close();
        byt1.close();

        ByteArrayInputStream bis1=new ByteArrayInputStream(oArr1);
            Hessian2Input hessian2Input = new Hessian2Input(bis1);
            AerospikeItem to2 = (AerospikeItem)hessian2Input.readObject();
            if (to2.isCompressed()) {
                CompressUtil.ungzip(to2.getValue());
            } else {
                new String(to2.getValue(), "utf-8");
            }
            hessian2Input.close();
            bis1.close();



8.PrintStream 三个用法

//format 格式控制
		int s = 6;
		boolean b = true;
		System.out.format("我们现在有%d个", s).print(b);//我们现在有6个true
		System.out.format("我们现在有%d个", s).println();//我们现在有6个
		//System.out.print 分解
		PrintStream ps;
		ps = System.out;
		ps.print(true);
		//改变标准输出位置
		try {
			ps = new PrintStream(new FileOutputStream(new File("D:/out.txt")));
			System.setOut(ps);  //设置标准输出不在是控制台,而是文件out.txt
			for(char c=0;c<50000;c++)
				System.out.print(c);  //此时标准输出不在是控制台,而是文件out.txt
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		}

9.ObjectOutputStream 的用法

Object 流,用的比较多,叫做序列化,其他语言上也叫序列化,就是把一个object 直接变成字节流,写到硬盘上,或者直接写到网络上。
class Iplong{
	public void ObjectOutputStreamTest(){
		T t = new T();
		t.k = 9;
		ObjectOutputStream oos;
		try {
			//写对象
			oos = new ObjectOutputStream(new FileOutputStream(new File("d:/out.txt")));
			oos.writeObject(t);
			//读对象
			ObjectInputStream ois = new ObjectInputStream(new FileInputStream(new File("d:/out.txt")));
			T getTObjct = (T) ois.readObject();
			System.out.println(getTObjct.d +" "+ getTObjct.i +" "+ getTObjct.j +" "+ getTObjct.k);//2.3 0 9 9
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		} catch (ClassNotFoundException e) {
			e.printStackTrace();
		}
	}	
}

class T 
	implements Serializable{   //如果想把某个类的对象序列化,必须实现Serializable 接口
	int i=0;
	int j=9;
	double d = 2.3;
	transient int k = 15;  //transient是瞬时的意思,往硬盘序列化的时候只写前三个值,这个transient 修饰的值不考虑
}













  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值