局部效果展示


整体架构

conf包
driverClassName=com.mysql.jdbc.Driver
url=jdbc\:mysql\://localhost\:3306/mybase?useUnicode\=true&characterEncoding\=utf-8
username=root
password=Hudie
initialSize=10
maxActive=50
maxIdle=20
minIdle=5
maxWait=60000
connectionProperties=useUnicode\=true;characterEncoding\=utf-8
defaultAutoCommit=true
defaultTransactionIsolation=READ_COMMITTED
sql语句
CREATE TABLE ACCOUNT(
cardid INT(7) PRIMARY KEY AUTO_INCREMENT,
NAME VARCHAR(15) NOT NULL,
PASSWORD VARCHAR(6) NOT NULL,
balance double
);
INSERT INTO ACCOUNT(NAME,PASSWORD,balance) VALUES('小A','123456',500);
INSERT INTO ACCOUNT(NAME,PASSWORD,balance) VALUES('小B','123456',800);
SELECT * FROM ACCOUNT;
一、view视图层
package view;
import java.util.Scanner;
import service.AccountService;
import service.AccountServiceImpl;
import entity.Account;
/**
* View表示层
*
*/
public class AccountView {
private static Scanner in = new Scanner(System.in);
//View层调用Service层
static AccountService accountService = new AccountServiceImpl();
public static void main(String[] args) {
System.out.println("************欢迎进入银行管理系统************");
System.out.println("1.存钱√ 2.取钱√");
System.out.println("3.查询余额√ 4.转账√");
System.out.println("5.注册账户√ 6.注销账户√");
System.out.println("7.更改密码√ 0.退出登录√");
while (true) {
System.out.print("请输入选项进行您的操作:");
// 输入选择的业务项
int n = in.nextInt();
switch (n) {
case 1:
save();
// 存钱
break;
case 2:
draw();
// 取钱
break;
case 3:
queryBalance();
// 查询余额
break;
case 4:
transfer();
// 转账
break;
case 5:
// 注册账户
regist();
break;
case 6:
logout();
// 注销账户
break;
case 7:
changepassword();
// 更改密码
break;
case 0:
// 退出登录
System.out.println("您已退出,感谢使用");
System.exit(0);
break;
default:
throw new RuntimeException("您的输入有误,请重新输入!");
}
}
}
//6.注销账户
private static void logout() {
//View层收集信息
int cardid = -1;
String password = null;
System.out.println("请输入账号:");
cardid = in.nextInt();
System.out.println("请输入密码:");
password = in.next();
try{
//进入Service层调用logout函数
accountService.logout(cardid,password);
System.out.println("账户注销完成!");
}catch(Exception e){
System.out.println(e.getMessage());
}
}
//7.更改密码
private static void changepassword() {
//View层收集信息
int cardid = -1;
String password = null;
String chpassword = null;
System.out.println("请输入账号:");
cardid = in.nextInt();
System.out.println("请输入密码:");
password = in.next();
System.out.println("请输入修改后的密码");
chpassword = in.next();
try{
//进入Service层调用changepassword函数
accountService.changepassword(cardid,password,chpassword);
System.out.println("密码修改完成");
}catch(Exception e){
System.out.println(e.getMessage());
}
}
//2取钱
private static void draw() {
//View层收集信息
int cardid = -1;
String password = null;
double money= 0.0;
System.out.println("请输入账号:");
cardid = in.nextInt();
System.out.println("请输入密码:");
password = in.next();
System.out.println("请输入取钱金额:");
money = in.nextDouble();
try{
//进入Service层调用draw函数
accountService.draw(cardid,password,money);
System.out.println("取钱完成");
}catch(Exception e){
System.out.println(e.getMessage());
}
}
//1.存钱
private static void save() {
//View层收集信息
int cardid = -1;
String password = null;
double money= 0.0;
System.out.println("请输入账号:");
cardid = in.nextInt();
System.out.println("请输入密码:");
password = in.next();
System.out.println("请输入存钱金额:");
money = in.nextDouble();
try{
//进入Service层调用save函数
accountService.save(cardid,password,money);
System.out.println("存钱完成");
}catch(Exception e){
System.out.println(e.getMessage());
}
}
//4.转账
private static void transfer() {
//View层收集信息
int from_cardid = -1;
int to_cardid = -1;
String password = null;
double money= 0.0;
System.out.println("请输入账号:");
from_cardid = in.nextInt();
System.out.println("请输入密码:");
password = in.next();
System.out.println("请输入对方账号:");
to_cardid = in.nextInt();
System.out.println("请输入转账金额:");
money = in.nextDouble();
try {
//进入Service层调用transfer函数
accountService.transfer(from_cardid,password,to_cardid,money);
System.out.println("转账完成!");
} catch (Exception e) {
System.out.println(e.getMessage());
}
}
//3.查询余额
private static void queryBalance() {
//View层收集信息
int cardid = -1;
String password = null;
System.out.println("请输入账户");
cardid = in.nextInt();
System.out.println("请输入密码");
password = in.next();
try{
//交给Service层处理,Service又访问Dao层,获得balance的值
Double balance = accountService.queryBalance(cardid,password);
System.out.println("您当前的余额为:"+balance);
}catch(Exception e){
System.out.println(e.getMessage());
}
}
//5.注册账户
private static void regist() {
//View层收集信息
String name = null;
String password = null;
String repassword = null;
System.out.println("请输入姓名:");
name = in.next();
System.out.println("请输入密码:");
password = in.next();
System.out.println("请确认密码:");
repassword = in.next();
Account account = new Account(null,name,password,0.0);
try{
//交给Service层处理
accountService.regist(account,repassword);
System.out.println("注册成功√");
}catch(Exception e){
//捕捉异常
System.out.println(e.getMessage());
}
}
}
二、service业务层
service层抽象接口
package service;
import entity.Account;
/**
* Service业务层接口
*
* 作用:对View层的数据进行处理
*
* @author QianliangGuo
*/
public interface AccountService {
//5.注册
public void regist(Account account,String repassword);
//3.查询余额
public Double queryBalance(int cardid,String password);
//4.转账
public void transfer(int from_cardid, String password, int to_cardid,double money);
//1.存钱
public void save(int cardid, String password, double money);
//2.取钱
public void draw(int cardid, String password, double money);
//7.修改密码
public void changepassword(int cardid, String password,String chpassword);
//6.注销账户
public void logout(int cardid, String password);
}
service实体类
package service;
import java.sql.Connection;
import java.sql.SQLException;
import util.JdbcUtil3;
import dao.AccountDao;
import dao.AccountDaoImpl;
import entity.Account;
/**
* AccountServiceImpl类(实现了Service接口层)
* 作用:对View层的数据进行处理
* 提供方法:
* 1.查询余额---queryBalance()
* 2.注册---regist()
* 3.转账---transfer()
* 4.存钱---
*
* @author QianliangGuo
*/
public class AccountServiceImpl implements AccountService {
//Service层--->Dao层
AccountDao accountDao = new AccountDaoImpl();
Connection conn = null;
// 5.注册
@Override
public void regist(Account account, String repassword) {
/**
* 异常情况:
* 1.输入空姓名
* 2.两次密码不一致
*/
String name = account.getName();
if (name == null) {
throw new RuntimeException("用户名不能为空");
}
String password = account.getPassword();
if (!password.equals(repassword)) {
throw new RuntimeException("两次密码不一致");
}
/**
* 正常情况:
*
* 创建连接,设置手动提交,控制事务
*/
try {
//创建连接
conn = JdbcUtil3.getConnection();
//使用事务,设置连接手动提交
conn.setAutoCommit(false);
//数据插入数据库
accountDao.insertAccount(account);
conn.commit();
} catch (Exception e) {
try {
//如果有异常,进行回滚
conn.rollback();
} catch (SQLException e1) {
throw new RuntimeException("事务回滚异常");
}
} finally {
try {
conn.close();
} catch (SQLException e) {
throw new RuntimeException("关闭连接异常");
}
}
}
// 3.查询余额
@Override
public Double queryBalance(int cardid, String password) {
Double balance = 0.0;
/**
* 异常情况:
* 1.账号不存在
* 2.密码输入不正确
*
*/
//查看账号是否存在
Account account = accountDao.queryAccountByCardid(cardid);
if (account == null) {
throw new RuntimeException("账号不存在");
}
if (!account.getPassword().equals(password)) {
throw new RuntimeException("密码输入错误");
}
/**
* 正常情况:
*
* 创建连接,获得balance,关闭连接
*/
try {
conn = JdbcUtil3.getConnection();
balance = account.getBalance();
} catch (Exception e) {
} finally {
try {
JdbcUtil3.release(null, null, conn);
} catch (Exception e) {
throw new RuntimeException("关闭连接异常");
}
}
return balance;
}
//4.转账
@Override
public void transfer(int from_cardid, String password, int to_cardid,double money) {
//通过账号获取两个账户对象 Service--->Dao.queryAccountByCardid();
Account from_account = accountDao.queryAccountByCardid(from_cardid);
Account to_account = accountDao.queryAccountByCardid(to_cardid);
/**
* 异常情况:
* 1.我方账号不存在
* 2.对方账号不存在
* 3.我方密码不正确
* 4.我方余额小于转账余额
*/
if(from_account == null){
throw new RuntimeException("您的账号不存在!");
}
if(to_account == null){
throw new RuntimeException("对方账号不存在!");
}
if(!from_account.getPassword().equals(password)){
throw new RuntimeException("密码输入错误!");
}
if(from_account.getBalance() < money){
throw new RuntimeException();
}
/**
* 正常情况(可以转账):
* { 1.我方余额-money;
* 2.对方余额-money; }
* 创建连接,设置手动提交,控制事务
*
*/
from_account.setBalance(from_account.getBalance()-money);
to_account.setBalance(to_account.getBalance()+money);
try{
conn = JdbcUtil3.getConnection();
conn.setAutoCommit(false);
accountDao.updateAccount(from_account);
accountDao.updateAccount(to_account);
conn.commit();
}catch(Exception e){
try {
conn.rollback();
} catch (Exception e1) {
System.out.println("事务回滚失败!");
}
}finally{
try {
conn.close();
} catch (Exception e2) {
System.out.println("数据库关闭失败");
}
}
}
//1.存钱
@Override
public void save(int cardid, String password, double money) {
/**
* 异常情况:
* 1.账号不存在
* 2.密码输入不正确
*
*/
//查看账号是否存在
Account account = accountDao.queryAccountByCardid(cardid);
if (account == null) {
throw new RuntimeException("账号不存在");
}
if (!account.getPassword().equals(password)) {
throw new RuntimeException("密码输入错误");
}
/**
* 正常情况(可以存钱):
* 创建连接,加钱,关闭连接
*
*/
//对应账号加钱
account.setBalance(account.getBalance()+money);
try {
conn = JdbcUtil3.getConnection();
accountDao.updateAccount(account);
} catch (Exception e) {
} finally {
try {
JdbcUtil3.release(null, null, conn);
} catch (Exception e) {
throw new RuntimeException("关闭连接异常");
}
}
}
//2.取钱
@Override
public void draw(int cardid, String password, double money) {
/**
* 异常情况:
* 1.账号不存在
* 2.密码输入不正确
*
*/
//查看账号是否存在
Account account = accountDao.queryAccountByCardid(cardid);
if (account == null) {
throw new RuntimeException("账号不存在");
}
if (!account.getPassword().equals(password)) {
throw new RuntimeException("密码输入错误");
}
/**
* 正常情况(可以存钱):
* 创建连接,减钱,关闭连接
*
*/
//对应账号减钱
account.setBalance(account.getBalance()-money);
try {
conn = JdbcUtil3.getConnection();
accountDao.updateAccount(account);
} catch (Exception e) {
} finally {
try {
JdbcUtil3.release(null, null, conn);
} catch (Exception e) {
throw new RuntimeException("关闭连接异常");
}
}
}
//7.修改密码
@Override
public void changepassword(int cardid, String password,String chpassword) {
/**
* 异常情况:
* 1.账号不存在
* 2.密码输入不正确
*
*/
//查看账号是否存在
Account account = accountDao.queryAccountByCardid(cardid);
if (account == null) {
throw new RuntimeException("账号不存在");
}
if (!account.getPassword().equals(password)) {
throw new RuntimeException("密码输入错误");
}
/**
* 正常情况(可以修改):
* 创建连接,修改密码,关闭连接
*
*/
account.setPassword(chpassword);
try {
conn = JdbcUtil3.getConnection();
accountDao.changepassword(account);
} catch (Exception e) {
} finally {
try {
JdbcUtil3.release(null, null, conn);
} catch (Exception e) {
throw new RuntimeException("关闭连接异常");
}
}
}
//6.注销账户
@Override
public void logout(int cardid, String password) {
/**
* 异常情况:
* 1.账号不存在
* 2.密码输入不正确
*
*/
//查看账号是否存在
Account account = accountDao.queryAccountByCardid(cardid);
if (account == null) {
throw new RuntimeException("账号不存在");
}
if (!account.getPassword().equals(password)) {
throw new RuntimeException("密码输入错误");
}
/**
* 正常情况(可以注销):
* 创建连接,注销账户,关闭连接
*
*/
try {
conn = JdbcUtil3.getConnection();
accountDao.logout(account);
} catch (Exception e) {
} finally {
try {
JdbcUtil3.release(null, null, conn);
} catch (Exception e) {
throw new RuntimeException("关闭连接异常");
}
}
}
}
三、dao数据访问层
dao层抽象接口
package dao;
import entity.Account;
/**
* Dao数据访问层
*
* 提供的方法:
* 5.数据插入数据库---insertAccount()
* 3.查询数据库---queryAccountByCardid()
*
* @author QianliangGuo
*/
public interface AccountDao {
//5.注册功能(数据插入数据库)
public void insertAccount(Account account);
//3.查询余额(查询数据库)
//根据卡号查看账号信息
public Account queryAccountByCardid(int cardid);
//4.转账(更新数据库balance)
public void updateAccount(Account account);
//7.修改密码(更新数据库password)
public void changepassword(Account account);
//6.注销账户(删除数据库记录)
public void logout(Account account);
}
dao层类
package dao;
import rowmapper.AccountRowMapper;
import util.JdbcTemplate;
import entity.Account;
/**
* AccountDaoImpl类(实现了AccountDao接口)
* 作用:访问数据库
* 提供方法:
* 1.注册账户---insertAccount()
* 2.查询余额---queryAccountByCardid()
*
* @author QianliangGuo
*/
public class AccountDaoImpl implements AccountDao {
//Dao层访问JdbcTemplate()类,创建JdbcTemplat()对象.
JdbcTemplate template = new JdbcTemplate();
//5.注册账户
@Override
public void insertAccount(Account account) {
template.update("insert into account(name,password,balance) values(?,?,?)", account.getName(),account.getPassword(),account.getBalance());
}
//3.查询余额
@Override
public Account queryAccountByCardid(int cardid) {
Account account = (Account)template.queryForObject("select * from account where cardid=?",new AccountRowMapper(),cardid);
return account;
}
//4.转账(更新数据库)
@Override
public void updateAccount(Account account) {
template.update("update account set balance = ? where cardid = ?", account.getBalance(),account.getCardid());
}
//7.修改密码(修改数据)
@Override
public void changepassword(Account account) {
template.update("update account set PASSWORD = ? where cardid = ?",account.getPassword(),account.getCardid());
}
//6.注销账户
@Override
public void logout(Account account) {
template.update("DELETE FROM `mybase`.`account` WHERE `cardid`=?",account.getCardid());
}
}
四、entity实体类
package entity;
/**
* 标配封装数据
* 1.属性全部私有√
* 2.提供get和set√
* 3.提供无参构造√
* 4.实现Serializable接口×
* 高配: toString() 有参构造√
*/
public class Account {
private Integer cardid;//卡号
private String name;//姓名
private String password;//密码
private Double balance;//余额
public Account() {
super();
// TODO Auto-generated constructor stub
}
public Account(Integer cardid, String name, String password, Double balance) {
super();
this.cardid = cardid;
this.name = name;
this.password = password;
this.balance = balance;
}
public Integer getCardid() {
return cardid;
}
public void setCardid(Integer cardid) {
this.cardid = cardid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public Double getBalance() {
return balance;
}
public void setBalance(Double balance) {
this.balance = balance;
}
@Override
public String toString() {
return "Account [cardid=" + cardid + ", name=" + name + ", password="
+ password + ", balance=" + balance + "]";
}
}
五、util工具包
JdbcTemplate模板包
package util;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.List;
import rowmapper.RowMapper;
/**
* JdbucTemplate类
* 作用:封装了增删改查操作
*
* @author QianliangGuo
*/
public class JdbcTemplate<T> {
/*
* 1.单条结果查询select_one
* 2.多条结果查询select_more
* 3.增删改 updata
*
*/
static Connection conn = null;
static PreparedStatement pstm = null;
static ResultSet rs = null;
// 1.select_one
public T queryForObject(String sql, RowMapper<T> rm, Object... args) {
T t = null;
try {
conn = JdbcUtil3.getConnection();
pstm = conn.prepareStatement(sql);
if (args.length != 0) {
for (int i = 0; i < args.length; i++) {
pstm.setObject(i + 1, args[i]);
}
}
rs = pstm.executeQuery();
if (rs.next()) {
t = rm.mappreRow(rs);
}
} catch (Exception e) {
System.out.println("数据库连接异常");
} finally {
try {
//conn留在Service层关闭
JdbcUtil3.release(rs, pstm, null);
} catch (Exception e) {
System.out.println("释放资源出现问题");
}
}
return t;
}
//2.select_more
public List<T> queryForList(String sql,RowMapper<T> rm,Object...args){
List<T> list = null;
try {
conn = JdbcUtil3.getConnection();
pstm = conn.prepareStatement(sql);
if (args.length != 0) {
for (int i = 0; i < args.length; i++) {
pstm.setObject(i + 1, args[i]);
}
}
rs = pstm.executeQuery();
list = new ArrayList();
while(rs.next()) {
T t = rm.mappreRow(rs);
list.add(t);
}
} catch (Exception e) {
System.out.println("数据库连接异常");
} finally {
try {
JdbcUtil3.release(rs, pstm,null);
} catch (Exception e) {
System.out.println("释放资源出现问题");
}
}
return list;
}
//3.updata操作
public void update(String sql, Object... args) {
try {
//开启一个连接
conn = JdbcUtil3.getConnection();
pstm = conn.prepareStatement(sql);
// args的长度如果不是0,就说明有参数,那它就是个半成品
if (args.length != 0) {
for (int i = 0; i < args.length; i++) {
pstm.setObject(i + 1, args[i]);
}
}
pstm.executeUpdate();
} catch (Exception e) {
System.out.println("数据库异常!");
} finally {
try {
JdbcUtil3.release(null, pstm, null);
} catch (Exception e) {
System.out.println("关闭连接异常!");
}
}
}
}
JdbcUtil3工具类
package util;
import java.io.IOException;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Properties;
import javax.sql.DataSource;
import org.apache.commons.dbcp.BasicDataSourceFactory;
/**
* Jdbc工具类
* 1:properties配置文件 封装获取连接 释放资源 提高代码复用性√
* 2:类加载时加载驱动√
* 3:ThreadLocal控制事务√
* 4:连接池,提高资源利用率√
* 5:rowmapper封装 减少代码冗余×
* 6:template封装 减少dao层代码冗余×
*
* 提供的方法:
* 1.获取连接---getConnection()
* 2.释放资源--- release()
*
*
* @author 郭乾亮1998
*
*/
public class JdbcUtil3 {
//声明连接池
static DataSource pool = null;
//创建properties
static Properties pro = new Properties();
//创建ThreadLocal<Connection>,可以为同一个线程保存同一个连接,为不同线程保存不同的连接
private static ThreadLocal<Connection> tl = new ThreadLocal<Connection>();
//加载驱动
static{
InputStream is = null;
try {
is = JdbcUtil3.class.getResourceAsStream("/conf/dbcp.properties");
//加载文件
pro.load(is);
//Class.forName(pro.getProperty("driverClassName"));
//properties配置文件创建连接池
pool = BasicDataSourceFactory.createDataSource(pro);
} catch (Exception e) {
e.printStackTrace();
}finally{
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
//获取连接
public static Connection getConnection() throws Exception{
Connection conn = tl.get();//获得当前线程中的连接
if(conn == null){//如果当前线程中没有连接
String url = pro.getProperty("url");
String user = pro.getProperty("username");
String password = pro.getProperty("password");
//创建连接
//conn = DriverManager.getConnection(url,user,password);
//通过连接池对象获得connection
conn = pool.getConnection();
//将连接保存到当前线程
tl.set(conn);
}
return conn;
}
//释放资源
public static void release(ResultSet rs,PreparedStatement pstm,Connection conn) throws Exception{
if(rs!=null){
rs.close();
}
if(pstm!=null){
pstm.close();
}
if(conn!=null){
conn.close();
tl.remove();//将连接从当前线程中移除
}
}
}
六、rowmapper封装结果集
RowMapper抽象类
package rowmapper;
import java.sql.ResultSet;
/**
* RowMapper接口
* 作用: 将ResultSet结果集封装成对象
*
* @author QianliangGuo
*/
public interface RowMapper<T> {
// 将ResultSet结果集封装成对象
public T mappreRow(ResultSet rs);
}
AccountRowMapper封装结果集类
package rowmapper;
import java.sql.ResultSet;
import java.sql.SQLException;
import entity.Account;
import rowmapper.RowMapper;
/**
* AccountRowMapper类
* 实现:RowMapper接口
* 作用:将Account结果集封装成Account对象
*
* @author QianliangGuo
*/
public class AccountRowMapper implements RowMapper {
@Override
public Account mappreRow(ResultSet rs) {
Account account = new Account();
try {
//处理结果集
account.setCardid(rs.getInt(1));
account.setName(rs.getString("name"));
account.setPassword(rs.getString(3));
account.setBalance(rs.getDouble(4));
} catch (SQLException e) {
e.printStackTrace();
}
return account;
}
}
转载:https://blog.csdn.net/weixin_43691058/article/details/103480292
查看评论