【JAVA】通过实现java.io.Serializable接口启用类的序列化

来源:互联网 发布:ubuntu 启动服务命令 编辑:程序博客网 时间:2024/06/05 09:09

在java中,通过java.io.Serializable接口可以实现类的序列化,从而实现类的读写操作。在之前的java上机实验中用到了这个接口,后来做课程设计,又用到了这个功能,不得不说java的这个接口功能十分强大,但是对于十分小白的我。。。功能强大归功能强大,在敲代码的过程中还是遇到了许多错误,所以写在博客里分享一下。

刚接触java时做过这样一个题:

设计学生类Student,属性:学号(整型);姓名(字符串),选修课程(名称)及课程成绩(整型)。编写一个控制台程序,能够实现Student信息的保存、读取。具体要求:(1)提供Student信息的保存功能:通过控制台输入若干个学生的学号、姓名以及每个学生所修课程的课程名和成绩,将其信息保存到data.dat中;(2)数据读取显示:能够从data.dat文件中读取学生及其课程成绩并显示于控制台。

具体代码如下:


package T4;import java.util.*;import java.io.*;public class Student implements java.io.Serializable{/** *  */private static final long serialVersionUID = 1L;private String name;private int ID;private String lesson;private int score;public static int numofstu=0;public String getName() {return name;}public void setName(String name) {this.name = name;}public int getID() {return ID;}public void setID(int iD) {ID = iD;}public String getLesson() {return lesson;}public void setLesson(String lesson) {this.lesson = lesson;}public int getScore() {return score;}public void setScore(int score) {this.score = score;}public static void showTips(){System.out.println("请输入接下来的操作:");System.out.println("in:录入学生信息");System.out.println("out:输出学生信息");System.out.println("exit:退出系统");}public static void InputInfo(List<Student> stuList){Scanner in=new Scanner(System.in);while(true){Student tmp=new Student();System.out.println("请输入学生姓名,若停止录入请输入exit:");String name=in.next();if(name.equals("exit")){break;}tmp.setName(name);System.out.println("请输入学生学号:");int ID=in.nextInt();tmp.setID(ID);System.out.println("请输入学生选修课程名称:");String lesson=in.next();tmp.setLesson(lesson);System.out.println("请输入学生课程成绩:");int score=in.nextInt();tmp.setScore(score);stuList.add(tmp);numofstu++;}in.close();}public static void OutputInfo(List<Student> stuList){FileOutputStream fos = null;ObjectInputStream ois = null;ObjectOutputStream oos = null;try {fos = new FileOutputStream("src/T4/stulist.dat");oos = new ObjectOutputStream(fos);for(int i=0;i<numofstu;++i){oos.writeObject(stuList.get(i));}} catch (IOException e1) {e1.printStackTrace();}finally{try {fos.close();oos.close();} catch (IOException e) {e.printStackTrace();}}try{ois = new ObjectInputStream(new FileInputStream("src/T4/stulist.dat"));while(true){try{Student p = (Student)ois.readObject();System.out.println("姓名:" + p.getName()+"  学号:"+p.getID()+"  选修课程:"+p.getLesson()+"  成绩:"+p.getScore());}catch(EOFException e){break;}catch(ClassNotFoundException e){break;}}}catch (IOException e){e.printStackTrace();}finally{try {ois.close();} catch (IOException e) {e.printStackTrace();}}}public static void main(String[] args) {Scanner in=new Scanner(System.in);List<Student> stuList=new ArrayList<Student>();while(true){showTips();String ope=in.nextLine();if(ope.equals("in")){InputInfo(stuList);}else if(ope.equals("out")){OutputInfo(stuList);}else if(ope.equals("exit")){break;}}in.close();}}

在student类信息写入文件这个过程中用到了Serializable接口,实现了学生类各属性的序列化写入文件。而后来的数据库课程设计功能需求与student类信息写入文件相似,是要求设计table类用来表示数据库中的数据表,并且要有相应的存储文件实现断电保存数据库中表的信息。

具体代码如下:

public void CreateTable() throws IOException {FileOutputStream fos = null;ObjectInputStream ois = null;ObjectOutputStream oos = null;// 将当前表信息写入以该表名命名的.dat文件中try {fos = new FileOutputStream("src/" + tname + ".dat");} catch (FileNotFoundException e) {// TODO Auto-generated catch blocke.printStackTrace();}try {oos = new ObjectOutputStream(fos);oos.writeObject(this);} catch (IOException e) {// TODO Auto-generated catch blocke.printStackTrace();} finally {try {fos.close();oos.close();} catch (IOException e1) {// TODO Auto-generated catch blocke1.printStackTrace();}}try {ois = new ObjectInputStream(new FileInputStream("src/" + tname + ".dat"));} catch (IOException e1) {// TODO Auto-generated catch blocke1.printStackTrace();}// 测试表信息是否写入文件保存成功while (true) {try {Table p = (Table) ois.readObject();//打印表的信息System.out.println("表名:" + p.tname);System.out.println("列名\t类型\t长度\t列级约束\t");for(int i=0;i<p.col_name.size();++i){System.out.print(p.col_name.get(i)+"\t");System.out.print(p.type.get(i)+"\t");if(p.len.get(i)==0) System.out.print("-\t");else System.out.print(p.len.get(i) + "\t");//输出列级约束System.out.print(p.c_constraints.get(i).Judge());System.out.println();}System.out.print("表级约束:");if(p.t_constraints.size()==0){System.out.println("无");}else{for(int i=0;i<p.t_constraints.size();++i){System.out.println(p.t_constraints);}}} catch (EOFException e) {break;} catch (ClassNotFoundException e) {break;}}}

但是!在运行时出现了编译错误,但经检查没有任何语法错误,在table类声明时也implements了接口java.io.Serializable。

出现编译错误的原因在于,我写的table类中包含一个ArrayList<Colconstraints>类型的属性,而Colconstraints又是一个类,但是这个类并没有实现序列化接口,这就导致了table类在实现类的写操作时出现了错误,导致编译出错。


更改后Colconstraints类代码如下:

public class Colconstraints implements java.io.Serializable {/** *  */private static final long serialVersionUID = 1L;public boolean primarykey;public boolean notnull;public boolean null_;public boolean unique;public boolean check;}

解决了这一问题。

原创粉丝点击