ok,我們在上篇博客中分享了一下簡單的學生信息管理系統,在這裏呢,我們先來做一下回顧:利用ArrayList的remove()和add()方法來將學生對象放入或移出列表中,接下來就是對列表進行增刪該查操作,而後注意一下界面的設計和用戶的交互就可以了。但是呢,這樣處理會有一個遺留問題:我們重啓程序後無法獲取之前的操作信息,爲什麼呢?顯然是沒有存儲!
上篇博客我們簡單說了一下解決方法,目前我的知識能力就能解決到1、通過數據庫;2、通過io寫入文件,那我們就來簡單說一下io:
要想了解io寫學生信息管理系統,首先要明白io是什麼,簡單來說就是input&output,也就是寫入和讀出。當然也要了解一下其中的類BufferedReader和BufferedWriter,當然輸入流、輸出流、緩衝輸入流……概念之間的關係就不是這篇博客講述的重點了,我們主要用上述這兩個類完成從線性表寫入文件和從文件讀出到線性表的操作。
我們先做一下需求分析:
1、首先要滿足的是學生信息管理系統的基本功能:增刪改查(在此附上之前的學生信息管理系統的增刪改查)
2、將線性表中的內容通過io操作寫入到文件中保存起來:可能會遇到的問題是:組數中的元素怎麼有條理的寫入到文件中,文件中的數據怎麼讀出到線性表裏
3、採用雙向測試:文件手動寫入看程序徐是否能夠讀出和程序運行看能否在文件中看到我們想要的結果
很明顯我們這個的操作界面無需改變,但是調用的參數需要改變,不能是線性表了,而是文件student.txt(一下簡稱文件)
public static void main(String[] args) throws IOException{
//定義文件路徑
String fileName = "students.txt";
//爲了讓程序能夠回到這裏來,我們使用循環
while(true) {
//這是學生管理系統的主界面
System.out.println("--------歡迎來到學生管理系統--------");
System.out.println("1 查看所有學生");
System.out.println("2 添加學生");
System.out.println("3 刪除學生");
System.out.println("4 修改學生");
System.out.println("5 退出");
System.out.println("請輸入你的選擇:");
//創建鍵盤錄入對象
Scanner sc = new Scanner(System.in);
String choiceString = sc.nextLine();
//用switch語句實現選擇
switch(choiceString) {
case "1":
//查看所有學生
findAllStudent(fileName);
break;
case "2":
//添加學生
addStudent(fileName);
break;
case "3":
//刪除學生
deleteStudent(fileName);
break;
case "4":
//修改學生
updateStudent(fileName);
break;
case "5":
default:
System.out.println("謝謝你的使用");
System.exit(0); //JVM退出
break;
}
}
}
我們要完成程序,最重要的環節在於如何完成寫入和讀出操作,大家先來看一下寫入:
1、首先確定傳參對象,我們是完成線性表和文件之間的轉換,很明顯傳參對象就是文件和線性表
2、創建對文件寫的操作對象BufferedWriter bw,完成對文件的寫
3、創建對數組元素操作的對象StringBuilder sb,完成對數組元素的整理
4、寫入注意使用newLine()方法實現換行寫入
5、最後flush一下,然後關閉資源
public static void writeData(String fileName,ArrayList<Student> array) throws IOException {
//創建輸出緩衝流對象
BufferedWriter bw = new BufferedWriter(new FileWriter(fileName));
for(int x=0; x<array.size(); x++) {
Student s = array.get(x);
StringBuilder sb = new StringBuilder();
sb.append(s.getId()).append(",").append(s.getName()).append(",").append(s.getAge()).append(",").append(s.getAddress());
bw.write(sb.toString());
bw.newLine();
bw.flush();
}
bw.close();
}
然後我們來看一下讀出操作:
1、首先確定傳參對象,我們是完成線性表和文件之間的轉換,很明顯傳參對象就是文件和線性表,也就是和寫入是一致的
2、創建對文件寫的操作對象BufferedReader br,完成對文件的讀
3、創建對當行元素操作的對象line,然後split一下,完成從文件讀入到數組中
4、然後再將數組中的元素通過student對象存儲到線性表中
5、最後關閉資源
//從文件中讀數據到集合
public static void readData(String fileName,ArrayList<Student> array) throws IOException {
//創建輸入緩衝流對象
BufferedReader br = new BufferedReader(new FileReader(fileName));
String line;
while((line=br.readLine())!=null) {
String[] datas = line.split(",");
Student s = new Student();
s.setId(datas[0]);
s.setName(datas[1]);
s.setAge(datas[2]);
s.setAddress(datas[3]);
array.add(s);
}
br.close();
}
最重要的分析完了,接下來就是對各個的操作了,我們以增爲例:我們會發現,其實和之前的內容並無太大差別,無非就是多了一步從文件中讀到線性表中和將線性表最新的內容存儲到文件中,註釋相對來說比較詳細,就不再一一展開了;
public static void addStudent(String fileName) throws IOException {
//創建集合對象
ArrayList<Student> array = new ArrayList<Student>();
//從文件中把數據讀取到集合中
readData(fileName, array);
//創建鍵盤錄入對象
Scanner sc = new Scanner(System.in);
//爲了讓id能夠被訪問到,我們就把id定義在了循環的外面
String id;
//爲了讓代碼能夠回到這裏,用循環
while(true) {
System.out.println("請輸入學生學號:");
//String id = sc.nextLine();
id = sc.nextLine();
//判斷學號有沒有被人佔用
//定義標記
boolean flag = false;
//遍歷集合,得到每一個學生
for(int x=0; x<array.size(); x++) {
Student s = array.get(x);
//獲取該學生的學號,和鍵盤錄入的學號進行比較
if(s.getId().equals(id)) {
flag = true; //說明學號被佔用了
break;
}
}
if(flag) {
System.out.println("你輸入的學號已經被佔用,請重新輸入");
}else {
break; //結束循環
}
}
System.out.println("請輸入學生姓名:");
String name = sc.nextLine();
System.out.println("請輸入學生年齡:");
String age = sc.nextLine();
System.out.println("請輸入學生居住地:");
String address = sc.nextLine();
//創建學生對象
Student s = new Student();
s.setId(id);
s.setName(name);
s.setAge(age);
s.setAddress(address);
//把學生對象作爲元素添加到集合
array.add(s);
//把集合中的數據重新寫回到文件
writeData(fileName, array);
//給出提示
System.out.println("添加學生成功");
}
下面就附上其餘操作的情況,因爲之前的博客中有過具體介紹,故不再贅述,如有疑問,可點此查看
//修改學生
public static void updateStudent(String fileName) throws IOException {
//創建集合對象
ArrayList<Student> array = new ArrayList<Student>();
//從文件中把數據讀取到集合中
readData(fileName, array);
//修改學生的思路:鍵盤錄入一個學號,到集合中去查找,看是否有學生使用的是該學號,如果有就修改該學生
//創建鍵盤錄入對象
Scanner sc = new Scanner(System.in);
System.out.println("請輸入你要修改的學生的學號:");
String id = sc.nextLine();
//定義一個索引
int index = -1;
//遍歷集合
for(int x=0; x<array.size(); x++) {
//獲取每一個學生對象
Student s = array.get(x);
//拿學生對象的學號和鍵盤錄入的學號進行比較
if(s.getId().equals(id)) {
index = x;
break;
}
}
if(index == -1) {
System.out.println("不好意思,你要修改的學號對應的學生信息不存在,請回去重新你的選擇");
}else {
System.out.println("請輸入學生新姓名:");
String name = sc.nextLine();
System.out.println("請輸入學生新年齡:");
String age = sc.nextLine();
System.out.println("請輸入學生新居住地:");
String address = sc.nextLine();
//創建學生對象
Student s = new Student();
s.setId(id);
s.setName(name);
s.setAge(age);
s.setAddress(address);
//修改集合中的學生對象
array.set(index, s);
//把集合中的數據重新寫回到文件
writeData(fileName, array);
//給出提示
System.out.println("修改學生成功");
}
}
//刪除學生
public static void deleteStudent(String fileName) throws IOException {
//創建集合對象
ArrayList<Student> array = new ArrayList<Student>();
//從文件中把數據讀取到集合中
readData(fileName, array);
//刪除學生的思路:鍵盤錄入一個學號,到集合中去查找,看是否有學生使用的是該學號,如果有就刪除該學生
//創建鍵盤錄入對象
Scanner sc = new Scanner(System.in);
System.out.println("請輸入你要刪除的學生的學號:");
String id = sc.nextLine();
//我們必須給出學號不存在的時候的提示
//定義一個索引
int index = -1;
//遍歷集合
for(int x=0; x<array.size(); x++) {
//獲取到每一個學生對象
Student s = array.get(x);
//拿這個學生對象的學號和鍵盤錄入的學號進行比較
if(s.getId().equals(id)) {
index = x;
break;
}
}
if(index == -1) {
System.out.println("不好意思,你要刪除的學號對應的學生信息不存在,請回去重新你的選擇");
}else {
array.remove(index);
//把集合中的數據重新寫回到文件
writeData(fileName, array);
System.out.println("刪除學生成功");
}
}
//查看所有學生
public static void findAllStudent(String fileName) throws IOException {
//創建集合對象
ArrayList<Student> array = new ArrayList<Student>();
//從文件中把數據讀取到集合中
readData(fileName, array);
//首先來判斷集合中是否有數據,如果沒有數據,就給出提示,並讓該方法不繼續往下執行
if(array.size() == 0) {
System.out.println("不好意思,目前沒有學生信息可供查詢,請回去重新選擇你的操作");
return;
}
//\t 其實就是一個tab鍵的位置
System.out.println("學號\t\t姓名\t年齡\t居住地");
for(int x=0; x<array.size(); x++) {
Student s = array.get(x);
System.out.println(s.getId()+"\t"+s.getName()+"\t"+s.getAge()+"\t"+s.getAddress());
}
}