做完這個eclipse控制台版本的圖書管理系統,感覺略有收獲,對類與對象的一些關系,接口的使用,以及HashMap,語句判定等有了更深刻的了解.
而這個系統還會繼續進化. 加入資料庫, web展示.亦或者使用java圖形界面.
1.首先第一步,我要做這個圖書管理系統,我更了解為一個圖書館 管理系統, 而不僅僅是圖書. 首先java是面向對象的.那麼好吧,有一個圖書館接口,一些書架,一些書放在書架上.
之後功能需求要能實作注冊,登陸,退出.
登陸之後實作書的借閱,歸還.
2.這一步使用了大量的邏輯判定判斷,因為覺得是練手的小項目,前期做得有點"備援",多餘的一些雜質讓我感覺做不動.通過放低要求,才發現,原來簡單而美妙.
package 圖書管理系統2;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Scanner;
import java.util.Set;
public class LoginStuff {
static Scanner in = new Scanner(System.in);
// 登陸方式選區,通過卡号呢還是使用者名密碼
public static void loginSelect() {
System.out.println("1.刷卡登陸.<輸入卡号>\n2.使用者名密碼登陸.\n#.傳回上級");
String loginSelectNum = in.next();
boolean numRight = loginSelectNum.equals("1") || loginSelectNum.equals("2") || loginSelectNum.equals("#");
if (numRight) {
if (loginSelectNum.equals("1")) {
LoginStuff.loginWithID();
}
if (loginSelectNum.equals("2")) {
LoginStuff.loginWithUserAndPassword();
}
if (loginSelectNum.equals("#")) {
Service.getHello();
}
} else {
System.out.println("輸入錯誤,請輸入1或2或#.");
System.out.println();
loginSelect();
}
}
// 執行login(ID)前必須執行該方法
// 使用ID卡号登陸
public static void loginWithID() {
System.out.println("請輸入您的卡号,以#号結束,(或隻輸入#傳回上一層)");
String ID_numberStr = "";
String nextNumber = in.next();
int OriginalIDlength = Library.IDLength;
ID_numberStr = nextNumber.trim();
boolean IDPassed = false;
if (ID_numberStr.endsWith("#")) {
if (ID_numberStr.length() == 1 && ID_numberStr.equals("#")) {
loginSelect();
return;
}
ID_numberStr = ID_numberStr.replace("#", "");
if (ID_numberStr.length() != OriginalIDlength) {
IDPassed = false;
System.out.println("正确卡号長度為" + OriginalIDlength + "位.請重新輸入:");
}
if (ID_numberStr.length() == OriginalIDlength) {
IDPassed = true;
}
}
if (IDPassed) {
long ID_number = (long) Long.valueOf(ID_numberStr);
login(ID_number);
} else {
loginWithID();
}
}
// 通過使用者名及密碼登陸的方法,這一方法隻是判定其格式,之後再調用了 login(inputUserName, inputPassWord)
public static void loginWithUserAndPassword() {
System.out.println("請輸入使用者名及密碼登陸.,(或隻輸入#傳回上一層)");
String inputUserName = in.next();
if(inputUserName.equals("#")) {
loginSelect();
return;
}
String inputPassWord = in.next();
boolean regexFailed = inputUserName == null || inputUserName == "" || inputUserName.length() == 0
|| inputPassWord == null || inputPassWord == "" || inputPassWord.length() == 0;
while (regexFailed) {
System.err.println("使用者名或密碼不能為空!");
loginWithUserAndPassword();
}
if (!regexFailed) {
login(inputUserName, inputPassWord);
}
}
// 登陸方式的選擇2, 通過使用者名和密碼登陸 之前已經使用loginWithUserAndPassword()進行了使用者名和密碼的接受和格式判定
// 而這一步是判定使用者資料庫的userList中和輸入的使用者名密碼進行比對,如果正确則提示登陸成功,
// 如果對比失敗則重新調用loginWithUserAndPassword()方法進行使用者名和密碼的接受和判定,其後再這個login方法進行比對.循環往複
public static void login(String userName, String passWord) {
Set<User> userList = UserDatabase.getUserInstance();
boolean userInList = false;
boolean userAuthPassed = false;
String thisNick = null;
String pass = null;
User thisUser_ = null;
Iterator<User> userIt = userList.iterator();
while (userIt.hasNext()) {
thisUser_ = userIt.next();
if (userName.equals(thisUser_.getUserName())) {
pass = thisUser_.getPassWord();
userInList = true;
}
if (userInList) {
if (passWord.equals(pass)) {
userAuthPassed = true;
thisNick = thisUser_.getNickName();
break;
}
}
}
// 登陸通過之後
if (userAuthPassed) {
System.out.println(thisNick + "登陸成功!");
System.out.println("快和小夥伴們一起玩耍(看書)吧!");
MemberService.showMemberSerivce(thisUser_);
} else {
System.out.println("賬号或密碼錯誤,請重新登陸!");
loginWithUserAndPassword();
}
}
// 通過使用者ID進行登陸,先通過User中的IDNumberSet這個Set集合進行取出,
// 使用了IDNumberJudge(Long ID)方法進行了"是否有這個ID"的比對
public static void login(long ID_Number) {
long inputID = User.getID_number();
// 該boolean值就是去确定是否有這個ID号碼,有則為true.沒有這個ID也就是
// 說明使用者ID是不存在的,不能登陸,其後可以再設定讓其進行注冊
boolean IDReady = User.IDNumberJudge(inputID);
if (IDReady) {
HashMap<Long, User> userData = UserDatabase.getUserDataMap();
User thisUser = userData.get(inputID);
System.out.println("------------------------");
System.out.println(thisUser);
System.out.println("刷卡成功,可以随意看書啦.當您離開記得再次刷卡以扣除時間段内消費!");
System.out.println("------------------------");
MemberService.showMemberSerivce(thisUser);
} else {
System.out.println("抱歉,沒有找到關于您卡号的資訊!請稍後再試.如需幫助請聯系管理者.");
System.out.println("或者您也可以進行使用面闆的1号選項進行注冊.");
Service.getHello();
}
}
}
package 圖書管理系統2;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Scanner;
import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class RegisterStuff {
static Scanner in = new Scanner(System.in);
private static String userName;
private static String passWord;
private static String sex;
private static String nickName;
private static int age;
public User newRegisterStuff(String username, String password1, String password2, String sex, String nickname,
int age) {
String regex = "^[a-zA-Z0-9\u4E00-\u9FA5]+$";
Pattern pattern = Pattern.compile(regex);
Matcher match = pattern.matcher(username);
boolean b = match.matches();
int alreadyHasUserName = 1;
boolean userNamePassed = (username != "" || username != null || username.length() != 0);
if (userNamePassed) {
if (!b) {
System.out.println("使用者名隻能由數字字母和下劃線組成!請重新輸入!");
register();
// return;
} else {
// 使用者名格式通過後,再判定使用者名是否存在于已有使用者的使用者名字段中,已存在則傳回true,不存在傳回false
alreadyHasUserName = userNameAgain(username);
if (alreadyHasUserName == 1) {// 已經存在該賬戶名,則重新輸入
// 去判定使用者名有一個什麼标記才行呢?使用boolean和int去判定最終還是會不行.
System.out.println("該使用者名已經存在,請選用其他使用者名~");
username = null;
register();
// return;
} else if (alreadyHasUserName == 0) {// 不重複則通過,并指派給this.userName
this.userName = username;
}
}
} else {
while (!userNamePassed) {
System.out.println("使用者名為空,請重新填寫注冊資訊.");
register();
// return;
}
}
// 判定密碼
boolean passwordPassed = password1.equals(password2);
if (passwordPassed) {
this.passWord = password1;
} else {
while (!passwordPassed) {
System.out.println("密碼兩次不一緻,請核對後再次輸入!(隻輸入兩次密碼)");
String password_ = in.next();
String password2_ = in.next();
passwordPassed = passWordAgain(password_, password2_);
if (passwordPassed) {
this.passWord = password_;
}
}
}
// 判定性别輸入 (不足)英文隻支援小寫.
boolean sexPassed = (sex.equals("男") || sex.equals("女") || sex.equals("man") || sex.equals("man")
|| sex.equals("woman") || sex.equals("boy") || sex.equals("girl"));
if (sexPassed) {
this.sex = sex;
} else {
while (!sexPassed) {
System.out.println("性别填寫錯誤,請再次填寫:");
String sex_ = in.next();
sexPassed = sexAgain(sex_);
if (sexPassed) {
this.sex = sex_;
}
}
}
// 判定昵稱合法性
boolean nickNamePassed = (nickname != "" || nickname != null || nickname.length() != 0);
if (nickNamePassed) {
this.nickName = nickname;
} else {
while (!nickNamePassed) {
System.out.println("昵稱為空,請再次填寫:");
String nickname_ = in.next();
nickNamePassed = nickNameAgain(nickname_);
if (nickNamePassed) {
this.nickName = nickname_;
}
}
}
// 判斷年齡合法性
boolean agePassed = (age < 999 && age > 0);
if (agePassed) {
this.age = age;
} else {
while (!agePassed) {
System.out.println("隻接受0歲以上兒童以及999歲以内的銀河系生物!請再次輸入年齡!");
int age_ = in.nextInt();
agePassed = ageAgain(age_);
if (agePassed) {
this.age = age_;
}
}
}
// 結束了所有資料的判斷
/////////////////////////////////////////////////////////////////////////////////
boolean AuthPassed = alreadyHasUserName == 0 && userNamePassed && b && passwordPassed && sexPassed
&& nickNamePassed && agePassed;
User newUser = null;
// 如果注冊成功則建立新user對象.
if (AuthPassed) {
newUser = new User(this.userName, this.passWord, this.sex, this.nickName, this.age);
}
return newUser;
}// RegisterStuff(.......注冊資訊.......)_END
private static String getUserName() {
return userName;
}
private static String getPassWord() {
return passWord;
}
private static String getSex() {
return sex;
}
private static String getNickName() {
return nickName;
}
private static int getAge() {
return age;
}
public RegisterStuff() {
}
// 注冊
public static void register() {
System.out.println("請輸入您的>>賬戶名<<>>密碼<<>>确認密碼<<>>性别<<>>昵稱<<>>年齡<<\n以空格隔開~(*^_^*)");
RegisterStuff rs = new RegisterStuff();
User newUser = rs.newRegisterStuff(in.next(), in.next(), in.next(), in.next(), in.next(), in.nextInt());
if (newUser != null) {
registerToUser(newUser);// 在将注冊資訊注冊入了使用者資料庫後. 可能會為null 此時在這個方法中判斷
printOK(newUser);// 登陸成功提示,并提示使用者的昵稱等.
}
}
// 注冊完成後使用者資料放入UserDatabase
public static void registerToUser(User newUser) {
UserDatabase.setUserNameList(newUser.getUserName());
UserDatabase.setUserInstance(newUser);
HashMap<Long, User> userDatabaseInRegister = UserDatabase.getUserDataMap();
long ID = newUser.getID_number();
userDatabaseInRegister.put(ID, newUser);
UserDatabase.setUserData(userDatabaseInRegister);
// 注冊資訊已送入UserDatabase 可以将使用者資料使用IO寫入txt檔案
}
// // 最後補的 暫未加入
// public static void afterRegister() {
// printOK();
// BookShelf bs = new BookShelf();
// bs.BookShelfInit();
// bs.getAllCategory();
// System.out.println("請問你要查閱哪些書籍?或哪一本?");
// }
// 注冊成功之後
private static void printOK(User user) {
System.out.println("注冊成功!");
HashMap<Long,User> userInstanceInRegister = UserDatabase.getUserDataMap();
User thisUser = userInstanceInRegister.get(user.getID_number());
System.out.println("***"+thisUser+"***");
}
// 從資料庫取出使用者名,檢視這次的使用者是否存在重複
public int userNameAgain(String userName) {
// 從使用者資料庫List擷取已經存在的賬戶對象
Set<String> userAlreadyHave = UserDatabase.getUserNameList();
// 從資料庫取出,去判定使用者名是否存在,單獨寫個方法
for (String alreadyHaveName : userAlreadyHave) {
if (userName.equals(alreadyHaveName)) {
return 1;// 重複使用者名傳回1
}
}
// 不重複使用者名傳回0
return 0;
}
// 重新寫入passWord屬性
public boolean passWordAgain(String password1, String password2) {
if (password1.equals(password2)) {
System.out.println("本次密碼核對正确!");
return true;
}
return false;
}
// 重新寫入sex屬性
private boolean sexAgain(String sex_) {
if ((sex_.equals("男") || sex_.equals("女") || sex_.equals("man") || sex_.equals("man") || sex_.equals("woman")
|| sex_.equals("boy") || sex_.equals("girl"))) {
return true;
}
return false;
}
// 重新寫入nickName屬性
public boolean nickNameAgain(String nickname_) {
if (nickname_ != "" || nickname_ != null || nickname_.length() != 0) {
return true;
}
return false;
}
// 重新寫入age屬性
public boolean ageAgain(int age_) {
if (age_ < 999 && age_ > 0) {
return true;
}
return false;
}
}
3. 有了登陸注冊,在使用者登陸後要提供會員服務,我直接建立了一個MemberService類.其實還有管理者Service和計算機Service類,應該提取某些Service作為一個Service接口,不過還沒想好.
package 圖書管理系統2;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Scanner;
import java.util.Set;
public class MemberService {
static Scanner in = new Scanner(System.in);
public static void showMemberSerivce(User thisUser_) {
System.out.println("您好," + thisUser_.getNickName() + ",這是會員服務欄目,您可享受一下服務,Enjoy it!");
System.out.println("1.借書\t\t2.還書\n3.點個咖啡\t\t4.上網沖浪\n5.健身運動\t\t6.圖書館留言\n#.傳回上級目錄(退出登陸)");
String serNum = in.next();
switch (serNum) {
case "1":borrowBookSer(thisUser_);
break;
case "2":giveBackBookSer(thisUser_);
break;
case "3":
break;
case "4":
break;
case "5":
break;
case "6":
break;
case "#":LoginStuff.loginSelect();
break;
default:
System.out.println("請輸入正确的服務選擇~!");
showMemberSerivce(thisUser_);
break;
}
}
public static void borrowBookSer(User user) {
System.out.println("您好"+user.getNickName()+",請問您想借閱哪本書呢?");
HashMap<String, Books> books = BookShelf.getBookMap();
Set<String> bookNames = books.keySet();
for(String bns : bookNames) {
System.out.print(bns+" : "+books.get(bns).beBorrowed);
}
System.out.println("輸入書名,借閱書籍.");
String wantedBook = in.next();
user.borrow(books.get(wantedBook));
showMemberSerivce(user);
}
public static void giveBackBookSer(User user) {
System.out.println("您好"+user.getNickName()+",請問您想還哪本書呢?");
ArrayList<String> userBorrowedBooks = user.getBorrowedBooks();
if(userBorrowedBooks == null) {
System.out.println("抱歉您沒有書要還~");
return;
}
System.out.println("您借閱的書此時還有如下:");
int hasBorrowedCount = 0;
for(String books:userBorrowedBooks) {
hasBorrowedCount++;
System.err.println(books);
}
if(hasBorrowedCount != 0) {
System.out.println("請輸入您要還的書的書名~:");
String giveBackBookName = in.next();
//從使用者已借閱清單中删除這本書
boolean giveback = userBorrowedBooks.remove(giveBackBookName);
HashMap<String, Books> bookInstanceMap =BookShelf.getBookMap();
Books backBookInstance = bookInstanceMap.get(giveBackBookName);
user.giveBack(backBookInstance, giveback);
showMemberSerivce(user);
}else {
System.err.println("Sorry,您沒有書要還~");
showMemberSerivce(user);
}
}
}
還有很多代碼就不貼了直接上
https://www.processon.com/view/link/5b24b04ae4b06d15ca94aedb請見諒為了友善查閱,包名使用了中文.
全部代碼
https://github.com/deadzq/LibrarySystem/tree/master/%E5%9B%BE%E4%B9%A6%E7%AE%A1%E7%90%86%E7%B3%BB%E7%BB%9F2通過做這個系統,感覺對類和對象的概念更清晰了,接口使用和一些備援還是有待加強.
最近看<重構>這書覺得還是有些許作用,比如當感覺必須要規整一下編碼,把類似的放到一起,或者按照某些原則,這些我還是不太懂.
總之,收獲頗豐~~~
将程式設計看作是一門藝術,而不單單是個技術。
敲打的英文字元是我的黑白琴鍵,
思維圖紙畫出的是我編寫的五線譜。
當美妙的華章響起,現實通往二進制的大門即将被打開。