java基础之IO流--ObjectOutputStream(专门用于操作对象)

8 篇文章 0 订阅

ObjectOutputStream 常用于对象的持久化,也叫做对象的可串行化

ObjectOutputStream 的write(int val)方法写入的是int 类型的最低8位,也就是一个字节,大于一个字节将会出现数据丢失

应该是其另一个方法叫writeInt(int val):写入一个32位的int 值

要把数据写到一个文件里面去,而这个数据不一定是纯文本数据,什么是纯文本(就是字符,你能够看得懂的)

而对象里面的数据是以字节码的形式存储,所以往里写的不是存文本的而是字节的,既然是字节,在构造函数里写应该是FileOutputStream

其中有一个很牛的方法叫 

public final void writeObject(Object obj)
                       throws IOException

而要序列化出去的对象要实现 java.io.Serializable 接口,否则会抛出NotSerializableException

该接口是我这辈子遇到最爽的接口,因为其没有任何的方法或字段


序列化运行时使用一个称为 serialVersionUID 的版本号与每个可序列化类相关联,该序列号在反序列化过程中用于验证序列化对象的发送者和接收者是否为该对象加载了与序列化兼容的类。如果接收者加载的该对象的类的 serialVersionUID 与对应的发送者的类的版本号不同,则反序列化将会导致 InvalidClassException。可序列化类可以通过声明名为 "serialVersionUID" 的字段(该字段必须是静态 (static)、最终 (final) 的 long 型字段)显式声明其自己的 serialVersionUID:


 ANY-ACCESS-MODIFIER static final long serialVersionUID = 42L;
 如果可序列化类未显式声明 serialVersionUID,则序列化运行时将基于该类的各个方面计算该类的默认 serialVersionUID 值,如“Java(TM) 对象序列化规范”中所述。不过,强烈建议 所有可序列化类都显式声明 serialVersionUID 值,原因是计算默认的 serialVersionUID 对类的详细信息具有较高的敏感性,根据编译器实现的不同可能千差万别,这样在反序列化过程中可能会导致意外的 InvalidClassException。因此,为保证 serialVersionUID 值跨不同 java 编译器实现的一致性,序列化类必须声明一个明确的 serialVersionUID 值。还强烈建议使用 private 修饰符显示声明 serialVersionUID(如果可能),原因是这种声明仅应用于直接声明类 -- serialVersionUID 字段作为继承成员没有用处。数组类不能声明一个明确的 serialVersionUID,因此它们总是具有默认的计算值,但是数组类没有匹配 serialVersionUID 值的要求。 


package newFeatures8;

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;

public class ObjectOutputStreamDemo {

	public static void main(String[] args) {
		writeObj();
		readObj();
	}

	public static void readObj() {
		try (ObjectInputStream ois = new ObjectInputStream(new FileInputStream("person.object"));) {
			Person5 person = (Person5) ois.readObject();
			System.out.println(person);
		} catch (Exception e) {
			e.printStackTrace();
		}

	}

	public static void writeObj() {
		try (ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream("person.object"));) {
			oos.writeObject(new Person5("lisi0", 339));
		} catch (Exception e) {
			e.printStackTrace();
		}

	}

}

class Person5 implements Serializable {
	private final static long serialVersionUID = 42L;
	private String name;
	//静态的字段不能被序列化,因为static的在方法区里
	//而且静态的不属于对象
	static String country;
	//如果要想 非静态的也不被序列化加关键字
	transient int age;

	public Person5(String name, int age) {
		this.name = name;
		this.age = age;
	}

	@Override
	public String toString() {
		return "Person [name=" + name + ", age=" + age + "]";
	}

}


  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值