图书馆系统源码详解

本项目是一个基于Scala语言开发的图书馆管理系统。系统主要由以下几个部分组成:数据访问层(DAO)、数据模型层(Models)、服务层(Service)以及用户界面层(UI)。以下是对项目中各个文件和文件夹的详细解释。

项目目录结构

scala_tushu2/
│
├── .idea/               # IntelliJ IDEA的项目配置文件夹
├── out/                 # 编译输出文件夹
├── src/                 # 源代码文件夹
│   ├── dao/             # 数据访问层
│   ├── models/          # 数据模型层
│   ├── service/         # 服务层
│   └── ui/              # 用户界面层
├── scripts/             # 脚本文件夹
├── scala_tushu2.iml     # IntelliJ IDEA的模块文件
├── books.txt            # 图书信息文件
├── borrow_records.txt    # 借阅记录文件
└── users.txt            # 用户信息文件

详细文件解释

1. 数据访问层(DAO)

文件:BookDAO.scala
  • 负责图书信息的增删改查操作。

  1. 提供与数据库交互的方法,如添加新书、删除书籍、更新书籍信息和查询书籍。

    package app.org
    package daoimport models.BookModelimport java.io.File
    import scala.collection.mutable.ListBuffer// 图书,数据操作
    class BookDAO {// 加载图书,从件中读入def loadBooks(): ListBuffer[BookModel] = {val books = new ListBuffer[BookModel]()val source = scala.io.Source.fromFile("books.txt")for (line <- source.getLines()) {val Array(id, name, author, available) = line.split(",")// 实例化一本书,保存到List中books += BookModel(id.toInt, name, author, available.toBoolean)}// 关闭连接source.close()books}// 保存图书,将图书写入文件def saveBooks(books: ListBuffer[BookModel]): Unit = {val writer = new java.io.PrintWriter(new File("books.txt"))for (book <- books) {writer.println(book.id + "," + book.name + "," + book.author + "," + book.available)}writer.close()}
    }
    

文件:BorrowRecordDAO.scala
  • 负责借阅记录的增删改查操作。

  • 提供与数据库交互的方法,如添加借阅记录、删除记录、更新记录和查询记录。

  • package app.org
    package daoimport models.BorrowRecordModelimport java.io.PrintWriter
    import scala.collection.mutable.ListBuffer
    import scala.io.Sourceclass BorrowRecordDAO {// 读出借阅记录def loadBorrowRecord(): ListBuffer[BorrowRecordModel] = {val borrowRecords =  ListBuffer[BorrowRecordModel]()val lines = Source.fromFile("borrow_records.txt")for (line <- lines.getLines()) {val parts =line.split(",")borrowRecords += BorrowRecordModel(parts(0),parts(1).toInt,parts(2),parts(3),if (parts.length>4) Some(parts(4)) else None)}borrowRecords}// 写入借阅记录def saveBorrowRecord(records: ListBuffer[BorrowRecordModel]): Unit = {val writer = new PrintWriter("borrow_records.txt")for (record <- records) {writer.println(record.userName + "," + record.bookID + "," + record.bookName + "," + record.borrowDate + "," + record.returnDate.getOrElse(""))}writer.close()}
    }
    

文件:UserDAO.scala
  • 负责用户信息的增删改查操作。

  • 提供与数据库交互的方法,如添加新用户、删除用户、更新用户信息和查询用户信息。

  • package app.org
    package daoimport models.UserModelimport java.io.File
    import scala.collection.mutable.ListBufferclass UserDAO {//加载所有的用户def loadUsers(): ListBuffer[UserModel] = {val users = new ListBuffer[UserModel]()val source = scala.io.Source.fromFile("users.txt")for (line <- source.getLines()) {val Array(username,password,role) = line.split(",")// 实例化一用户,保存到List中users += UserModel(username,password,role)}// 关闭连接source.close()users}//保存用户// 保存图书,将图书写入文件def saveUsers(users: ListBuffer[UserModel]): Unit = {val writer = new java.io.PrintWriter(new File("users.txt"))for (user <- users) {writer.println(user.username + "," + user.password + "," + user.role)}writer.close()}
    }
    

2. 数据模型层(Models)

文件:BookModel.scala
  • 定义图书的数据模型。

  • 包含图书的属性,如ID、书名、作者、是否可借等。

  • package app.org
    package models// 图书类
    // id,书名,作者,状态
    case class BookModel(id: Int, name: String, author: String, var available: Boolean) {override def toString: String ={val availableStr = if (available) "可外借" else "已借出"s"编号:$id \t 书名: $name \t 作者:$author \t 这本书——$availableStr"}
    }

文件:BorrowRecordModel.scala
  • 定义借阅记录的数据模型。

  • 包含借阅记录的属性,如用户ID、书籍ID、借阅时间、归还时间等。

  • package app.org
    package modelscase class BorrowRecordModel(userName:String,               // 借书人bookID:Int,                  // 图书IDbookName:String,           // 书名borrowDate:String,          // 借阅日期var returnDate:Option[String] =None   // 归还日期)
    

文件:UserModel.scala
  • 定义用户的数据模型。

  • 包含用户的属性,如ID、用户名、密码、用户类型(管理员或普通用户)等。

  • package app.org
    package modelscase class UserModel(username:String,password:String,role:String)
    

3. 服务层(Service)

文件:BookService.scala
  • 提供图书相关的业务逻辑。

  • 调用DAO层的方法,实现图书的增删改查等业务操作。

  • package app.org
    package serviceimport models.{BookModel, BorrowRecordModel}
    import dao.{BookDAO, BorrowRecordDAO}import java.time.LocalDateTime
    import scala.collection.mutable.ListBuffer// 图书业务逻辑层
    class BookService {private val bookDAO = new BookDAO()private val borrowRecordDAO = new BorrowRecordDAO()// 查询所有的图书
    //  def searchBooks(query:String): 图书列表List(Book对象)def searchBooks(query:String): ListBuffer[BookModel] = {// 从文本文件中读取书本信息,并保存列表中,返回val books = bookDAO.loadBooks()query match {case "" => books  // 没有条件,就返回全部case _ => books.filter(b => b.name.contains(query) || b.author.contains(query))  // 根据条件过滤}}// 普通用户,借阅图书def borrowBook(username:String,bookId:Int): Boolean = {//   (1) 根据图书的ID,查询图书, 判断图书是否存在val books = bookDAO.loadBooks()val records = borrowRecordDAO.loadBorrowRecord()val book = books.find(b => b.id == bookId)if (book.nonEmpty) {val b = book.get//   (2) 判断图书是否已经被借出if (b.available) {//   (3) 借阅图书//        更新这本书的状态b.available = false// 把更新之后的图书的信息写回txt文件中bookDAO.saveBooks(books)//    TODO    添加一条借书记录// 读出当前全部的记录// 添加一条记录records += BorrowRecordModel(username,b.id,b.name,LocalDateTime.now().toString)// 写回txt文件中borrowRecordDAO.saveBorrowRecord(records)println("借阅成功,已保存借阅记录!!!")true} else {println("这本书已经被借走了!!!")false}} else {false}}// 普通用户,查询自己的借阅记录def queryBorrowRecords(username: String):ListBuffer[BorrowRecordModel] = {// 读出全部的借阅记录val records = borrowRecordDAO.loadBorrowRecord()// 过滤出当前用户的借阅记录records.filter(r => r.userName == username)}// 普通用户,归还自己借的某一本书def returnBook(username: String, bookId: Int): Boolean = {// 1.确定这本书是他本人借的并归还处于没有归还的状态queryBorrowRecords(username).find(r => r.bookID == bookId && r.returnDate.isEmpty) match {case Some(record) =>// 2.更新这本书的状态// 2.1 加载全部的图书信息val books = bookDAO.loadBooks()// 2.2选择当前这一本书val b = books.find(_.id == bookId).getb.available = true// 2.3 把更新之后的状态写回txt文件中bookDAO.saveBooks(books)// 3.更新借阅记录的状态// 3.1 加载全部的借阅记录val records = borrowRecordDAO.loadBorrowRecord()// 3.2 找到当前这本书的借阅记录val r = records.find(r => r.bookID == bookId && r.userName ==username && r.returnDate.isEmpty).getr.returnDate = Some(LocalDateTime.now().toString)// 3.3 把更新之后的状态写回txt文件中borrowRecordDAO.saveBorrowRecord(records)truecase None => false}}// 添加图书def addBook(book: BookModel): Unit = {// 1. 生成一个book ID// 查询所有的图书,找到最大的ID,+1var id = 1val books = bookDAO.loadBooks()if (books.nonEmpty) {id = books.map(_.id).max + 1}// 2. 更新val newBook = book.copy(id = id)// 3. 把新的图书添加到books.txt中books += newBook// 4. 把更新之后的状态写回txt文件中bookDAO.saveBooks(books)}private def queryBooks(): ListBuffer[BookModel] = {// 1. 加载全部的图书val books = bookDAO.loadBooks()// 2. 返回books}}
    

文件:UserService.scala
  • 提供用户相关的业务逻辑。

  • 调用DAO层的方法,实现用户的增删改查等业务操作。

  • package app.org
    package serviceimport dao.UserDAOimport models.UserModelclass UserService {private val userDAO = new UserDAO()// 身份校验def authenticateUser(username: String, password: String): Option[UserModel] = {// 去根据用户名和密码查询,是否有符合要求的用户val users = userDAO.loadUsers()users.find(user => user.username == username && user.password == password)}// 注册用户def addUser(username: String): Boolean = {// 1. 查询用户名是否已经存在val users = userDAO.loadUsers()val user =users.find( _.username == username)if (user.isEmpty) {// 可以继续添加// 2.添加// 2.1 读取所有的用户// 2.2 创建新的用户users += UserModel(username, "[\\d]", "普通用户")// 2.3 保存用户userDAO.saveUsers(users)true} else {false}}
    }
    

4. 用户界面层(UI)

文件:LPT.scala
  • 提供用户界面的实现。

  • 负责与用户的交互,如显示图书列表、显示借阅记录、用户登录等。

  • package app.org
    package uiimport models.{BookModel, UserModel}
    import service.{BookService, UserService}import scala.io.StdIn
    import scala.io.StdIn.readLineclass LPT {private val BookService = new BookService()private val UserService = new UserService()// 辅助方法: 输入图书的信息,返回一个BookModel对象private def inputBookInfo(): BookModel = {println("请输入图书的名称:")val name = readLine().trimprintln("请输入图书的作者:")val author = readLine().trimprintln("请输入图书是否可以外借(true/false):")val available = StdIn.readBoolean()// 初始设置编号为0BookModel(0,name, author, available)}// 显示游客的菜单def showVisitorMenu(): Unit = {var running = truewhile (running) {println("欢迎来到我的图书管理系统,请选择:")println("1. 查看所有图书")println("2. 查询图书")println("3. 登录")println("4. 退出")// 获取用户操作val choice = StdIn.readLine().trimchoice match {case "1" =>// 调用业务逻辑层的方法val results = BookService.searchBooks("")if (results.nonEmpty) {results.foreach(println)} else {println("没有找到图书")}case "2" =>// 提示用户输入查询关键字val query = readLine("请输入查询关键字:").trim// 根据关键字去查询图书列表,找到满足条件的书val results = BookService.searchBooks(query)// 显示出来if (results.nonEmpty) {println("=================查询图书的结果结果====================")results.foreach(println)} else {println("没有找到图书")}case "3" =>println("请输入用户名:")val username = StdIn.readLine().trimprintln("请输入密码:")val password = StdIn.readLine().trim// 调用service的方法,进行登录val userOPT =UserService.authenticateUser(username, password)if (userOPT.isEmpty) {println("用户名或密码错误")} else {// 登录成功,显示登录用户的菜单val user = userOPT.getuser.role match {case "管理员" => showAdminMenu(user)case "普通用户" => showUserMenu(user)}}case "4" =>running = falseprintln("感谢你的使用,下次再见")case _ => println("无效的选择,请重新输入")}}}// 显示管理员的菜单def showAdminMenu(user: UserModel): Unit = {var running = truewhile (running) {println(s"欢迎管理员${user.username}来到我的图书管理系统,请选择:")println("1. 添加图书")println("2. 查询图书")println("3. 添加用户")println("4. 退出")// 获取用户的操作val choice = StdIn.readLine().trimchoice match {case "1" =>// 1.获取图书信息-书名,作者,状态val book = inputBookInfo()// 2. 调用service的方法,做添加到books.txt中操作BookService.addBook(book)println(s"图书《${book.name}》添加成功")case "2" =>// 提示用户输入查询关键字println("请输入查询关键字:")val query = readLine().trimval results = BookService.searchBooks(query)if (results.nonEmpty) {println("=================查询图书的结果====================")results.foreach(println)println("=================以上是查询图书的结果!!!!====================")println()} else {println("没有找到图书")}case "3" =>// 1.获取用户信息-用户名,密码,角色val username = StdIn.readLine("请输入用户名:")// 2. 调用service的方法,做添加到users.txt中操作if (UserService.addUser(username)) {println(s"用户${username}添加成功")} else {println("用户添加失败")}case "4" => running = falsecase _ => println("无效的选择,请重新输入")}}}// 显示登录用户的菜单def showUserMenu(user: UserModel): Unit = {var running = truewhile (running) {println(s"欢迎用户${user.username}来到我的图书管理系统,请选择:")println("1. 借阅图书")println("2. 查询借阅图书")println("3. 还书")println("4. 退出")// 获取用户的操作val choice = StdIn.readLine().trimchoice match {case "1" =>// UI : 提示用户输入图书ID。校验:判断是否整数try {val id = readLine("请输入图书的ID:").toIntprintln(id)BookService.borrowBook(user.username,id)} catch {case e: Exception =>println(e)println("输入的图书ID无效,请重新输入:")}case "2" => println("查询图书")val borrowRecords = BookService.queryBorrowRecords(user.username)//if (borrowRecords.isEmpty) {println("您还没有借阅过任何图书!!!")} else {// 打印借阅记录println("查询结果,一共借了?本,?本已归还,?本未归还")for (record <- borrowRecords) {val returnDate = record.returnDate.getOrElse("未归还")println(s"用户名:${record.userName},图书ID:${record.bookID},图书名称:${record.bookName},借阅日期:${record.borrowDate},归还日期:$returnDate")}}case "3" => println("还书")try {val id = readLine("请输入要归还的图书的ID:").toIntif(BookService.returnBook(user.username, id)) {println("归还图书成功!!!")} else {println("归还图书失败,请检查输入的图书ID是否正确")}} catch {case e: Exception =>println(e)println("输入的图书ID无效,请重新输入")}case "4" => running = falsecase _ => println("无效的选择,请重新输入")}}}def showMenu(): Unit = {showVisitorMenu()}
    }
    

文件:Main.scala

Main.scala 文件是Scala应用程序的入口点,它通常包含 main 函数,该函数是程序执行的起始点。在这个图书馆管理系统中,Main.scala 可能承担以下职责:

  1. 初始化系统:设置系统运行所需的环境,例如初始化数据库连接、加载配置文件等。

  2. 启动服务:启动系统中的服务层,例如图书服务、用户服务等,这些服务可能负责处理业务逻辑。

  3. 用户界面启动:启动用户界面层,例如命令行界面或图形用户界面,允许用户与系统交互。

  4. 运行主循环:对于需要持续运行的系统,Main.scala 可能包含一个主循环,用于不断监听用户输入或处理后台任务。

  5. 错误处理:设置全局错误处理机制,确保系统在遇到错误时能够优雅地处理并给出用户友好的反馈。

    package app.orgimport ui.LPTobject Main {def main(args: Array[String]): Unit = {val m = new LPT()m.showMenu()}
    }
    

5. 其他文件

文件:books.txt
  • 存储图书信息的文本文件。

  • 每行包含图书的ID、书名、作者和是否可借的信息。

文件:borrow_records.txt
  • 存储借阅记录的文本文件。

  • 每行包含用户ID、图书ID、借阅时间和归还时间的信息。

文件:users.txt
  • 存储用户信息的文本文件。

  • 每行包含用户的用户名、密码和用户类型(管理员或普通用户)的信息。

总结

本项目通过分层架构实现了一个图书馆管理系统,各层之间职责明确,便于维护和扩展。数据访问层负责与数据库的交互,数据模型层定义了系统中使用的数据结构,服务层实现了具体的业务逻辑,用户界面层负责与用户的交互。通过这种方式,系统具有良好的可读性和可维护性。

 # # #本项目并不是完美的项目, 嗨有缺少的功能自行添加!!!!!!!!!!!!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/23074.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

RT-Thread+STM32L475VET6——USB鼠标模拟

文章目录 前言一、板载资源二、具体步骤1.配置icm20608传感器2.打开CubeMX进行USB配置3. 配置USB3.1 打开USB驱动3.2 声明USB3.3 剪切stm32xxxx_hal_msp.c中的void HAL_PCD_MspInit(PCD_HandleTypeDef* hpcd)和void HAL_PCD_MspDeInit(PCD_HandleTypeDef* hpcd)函数至board.c3.…

Vue 中单向数据流原则

做一个 ElementUI 弹框组件的二次封装 效果如下: 点击取消按钮发现弹出如下报错信息 : [Vue warn]: Avoid mutating a prop directly since the value will be overwritten whenever the parent component re-renders. Instead, use a data or computed property based on the …

前后端分离系统架构:基于Spring Boot的最佳实践

前后端分离系统架构图描绘了一个基于Springboot的前端后台分离的系统架构。它强调了前端&#xff08;客户端&#xff09;与远程&#xff08;服务器&#xff09;的解耦&#xff0c;通过API接口进行交互&#xff0c;分别独立开发和部署。 前后端分离系统架构图 从上到下&#xff…

Neo4j使用neo4j-admin导入csv数据方法

在neo4j desktop里创建project&#xff0c;创建dbms&#xff0c;创建database。 将csv文件放入如下import路径中&#xff0c;然后就可以使用相对路径来使用csv了。 在neo4j desktop中打开Terminal 键入导入数据语句&#xff1a; neo4j-admin database import full --nodes&qu…

【Transformer架构】

目录 一、Transformer介绍 1.1 Transformer的诞生 1.2 什么是Transformer 1.3 Transformer的优势 1.4 Transformer的市场 二、Transformer架构 2.1 Transformer模型的作用 2.2 Transformer总体架构图 2.2.1 Transformer总体架构 2.2.2 输入部分 2.2.3 输出部分 2.2.…

设计模式-组合模式、模板模式

组合模式 定义 将对象组合成树形结构以表示"部分-整体"的层次结构&#xff0c;组合模式使得用户对单个对象和组合对象的使用具有一致性&#xff1b; 组合模式实现的最关键的地方是-简单对象和复合对象必须实现相同的接口。这就是组合模式能够将组合对象和简单对象进…

Spring Boot 概要(官网文档解读)

Spring Boot 概述 Spring Boot 是一个高效构建 Spring 生产级应用的脚手架工具&#xff0c;它简化了基于 Spring 框架的开发过程。 Spring Boot 也是一个“构件组装门户”&#xff0c;何为构件组装门户呢&#xff1f;所谓的“构件组装门户”指的是一个对外提供的Web平台&#x…

SkyWalking集成Kafka实现日志异步采集经验总结

SkyWalking日志异步采集架构 【重点知识】 1、【Agent】kafka-reporter-plugin-x.x.x.jar包放plugins目录后必走kafka&#xff08;kafka没有正确配置就会报错&#xff09; 2、【Agent】异步如不开启数据压缩&#xff0c;日志数据较大&#xff0c;pod多、业务大时容易造成网络…

2025前端框架最新组件解析与实战技巧:Vue与React的革新之路

作者&#xff1a;飞天大河豚 引言 2025年的前端开发领域&#xff0c;Vue与React依然是开发者最青睐的框架。随着Vue 3的全面普及和React 18的持续优化&#xff0c;两大框架在组件化开发、性能优化、工程化支持等方面均有显著突破。本文将从最新组件特性、使用场景和编码技巧三…

Orange 单体架构 - 快速启动

1 后端服务 1.1 基础设施 组件说明版本MySQLMySQL数据库服务5.7/8JavaJava17redis-stackRedis向量数据库最新版本Node安装Node22.11.0 1.2 orange-dependencies-parent 项目Maven依赖版本管理 1.2.1 项目克隆 GitHub git clone https://github.com/hengzq/orange-depende…

Layer2 扩容解决方案详解

Layer2 扩容解决方案详解 &#x1f504; 1. Layer2 基础概念 1.1 什么是 Layer2&#xff1f; Layer2 是建立在以太坊主网&#xff08;Layer1&#xff09;之上的扩容解决方案&#xff0c;它&#xff1a; 继承以太坊的安全性提供更高的交易吞吐量降低交易费用保持去中心化特性…

小智机器人CMakeLists编译文件解析

编译完成后&#xff0c;成功烧录&#xff01; 这段代码是一个CMake脚本&#xff0c;用于配置和构建一个嵌入式项目&#xff0c;特别是针对ESP32系列芯片的项目。CMake是一个跨平台的构建系统&#xff0c;用于管理项目的编译过程。 set(SOURCES "audio_codecs/audio_code…

银河麒麟系统安装mysql5.7【亲测可行】

一、安装环境 cpu&#xff1a;I5-10代&#xff1b; 主板&#xff1a;华硕&#xff1b; OS&#xff1a;银河麒麟V10&#xff08;SP1&#xff09;未激活 架构&#xff1a;Linux 5.10.0-9-generic x86_64 GNU/Linux mysql版本&#xff1a;mysql-5.7.34-linux-glibc2.12-x86_64.ta…

【Linux】动静态库

目录 站在库提供者的角度 静态库 制作静态库 静态库的内容 发布静态库 用户使用静态库 找头文件 找库文件 动态库 制作动态库 动态库报错 动态库是怎么被加载的&#xff1f; 地址相关问题 程序加载前的地址 程序加载后的地址 如何执行第一条指令&#xff1f; …

500字理透react的hook闭包问题

在react中hook的闭包问题很容易在不经意间犯错&#xff0c;项目写大了之后更是难以找到到底是哪里出了问题。 为什么会出现闭包问题 出现闭包问题的原因就是函数中操作的变量不是最新的变量&#xff0c;什么意思呢&#xff0c;我们知道函数组件每次刷新都是重新运行一次函数&…

Unity Shader Graph 2D - 一个简单的魔法阵激活效果

前言 在魔幻类游戏里通常会有魔法阵的存在,而当某个机关被触发或者某个剧情被触发时,需要对魔法阵进行激活,这个时候就需要一个魔法阵的激活效果来让这个游戏的这一时刻的交互性更强,生动性更强,本文将用一种十分简单的方式来实现一个魔法阵的激活效果。 创建一个…

C++ 类和对象(友元、内部类、匿名对像)

目录 一、前言 二、正文 1.友元 1.1友元函数的使用 1.1.1外部友元函数可访问类的私有成员&#xff0c;友员函数仅仅是一种声明&#xff0c;他不是类的成员函数。 1.1.2一个函数可以是多个类的友元函数 2.友元类的使用 2.1什么是友元类 2.2 友元类的关系是单向的&#x…

Docker Network

1.简介 容器之间的通讯时通过网桥通讯的&#xff0c;跨主机通讯可以使用flannel进行通讯 那么为什么主机可以访问到虚拟机内部呢&#xff1f;因为VMware虚拟出一个虚拟的网卡&#xff0c;而这个虚拟网卡和主机在同一个局域网下 NAT是映射一个虚拟网卡&#xff0c;进行路由通信…

【Linux系统】—— 冯诺依曼体系结构与操作系统初理解

【Linux系统】—— 冯诺依曼体系结构与操作系统初理解 1 冯诺依曼体系结构1.1 基本概念理解1.2 CPU只和内存打交道1.3 为什么冯诺依曼是这种结构1.4 理解数据流动 2 操作系统2.1 什么是操作系统2.2 设计OS的目的2.3 操作系统小知识点2.4 如何理解"管理"2.5 系统调用和…

【行业解决方案篇十八】【DeepSeek航空航天:故障诊断专家系统 】

引言:为什么说这是“航天故障终结者”? 2025年春节刚过,航天宏图突然官宣"DeepSeek已在天权智能体上线",这个搭载在卫星和空间站上的神秘系统,号称能提前48小时预判99.97%的航天器故障。这不禁让人想起年初NASA禁用DeepSeek引发的轩然大波,更让人好奇:这套系…