MySQL数据库
1、DDL数据定义语言
00)常用约束&数据类型
主键约束 | primary key |
---|---|
主键自动增长 | auto_increment |
非空约束 | not null |
唯一性约束 | unique |
默认值 | default |
主外键约束 | foreign key |
数值类型
tinyint(m) | 1个字节 范围(-128~127) |
---|---|
smallint(m) | 2个字节 范围(-32768~32767) |
mediumint(m) | 3个字节 范围(-8388608~8388607) |
int(m) | 4个字节 范围(-2147483648~2147483647) |
bigint(m) | 8个字节 范围(±9.22*10的18次方) |
浮点型(float和double)
float(m,d) | 单精度浮点型 8位精度(4字节) m总个数,d小数位 |
---|---|
double(m,d) | 双精度浮点型 16位精度(8字节) m总个数,d小数位 |
字符类型
char(n) | 固定长度,最多255个字符 |
---|---|
varchar(n) | 固定长度,最多65535个字符 |
tinytext | 可变长度,最多255个字符 |
text | 可变长度,最多65535个字符 |
mediumtext | 可变长度,最多2的24次方-1个字符 |
longtext | 可变长度,最多2的32次方-1个字符 |
日期时间类型
date | 日期 ‘2008-12-2’ |
---|---|
time | 时间 ‘12:25:36’ |
datetime | 日期时间 ‘2008-12-2 22:06:44’ |
timestamp | 自动存储记录修改时间 |
01)创建数据库并且设置字符集
create database 数据库名 character set 字符集;
02)创建表
create table 表名( 字段名 字段类型 字段约束,字段名 字段类型 字段约束);
绑定主外键:
语法:fore
示例:ign key (外建字段名) references 主键表名(主键字段名)
示例:create table toursInfo(
id int primary key auto_increment,
introduce varchar(500),
pubTime date,
price decimal(6,2),
cityId int,
foreign key (cityId) references city(cityId)
);
03)显示所有数据库
show databases;
04)查看当前数据库中所有表名称
show tables;
05)切换数据库
use 数据库名;
07)修改列类型
alter table 表名 modify 列名 列类型;
08)增加列
alter table 表名 add 列名 列类型;
09)删除列
alter table 表名 drop 列名;
10)列改名
alter table 表名 change 旧列名 新列名 列类型;
11)更改表名
alter table 表名 rename 新表名;
12)查看表结构
desc 表名;
13)删除表
drop table 表名;
14)删除数据库
drop databases 数据库名;
2、DML 数据操纵语言
01)插入单行数据
insert into 表名(字段列表) values(列表值);
02)插入多行数据
insert into 表名(字段1,字段2) values(字段值1,字段值2);
03)更新数据
update 表名 set 列1 = 新值1 , 列2 = 新值2 where 条件;
04)可以根据条件删除,可以回滚数
delete from 表名 [where 条件]
05)永久删除,无法回滚
truncate table 表名;
3、DQL数据查询语言数据
单表查询
00)关键字
A)and:表示连接多个条件,表示并且关系。 |
---|
B)or:表示连接多个条件,表示或者的关系。 |
C)in(): 包含哪些值 |
D)not in():不包含哪些值 |
E)sql中null的写法 是空的:is null 不是空的:is not null |
F)between … and : 表示范围内的记录, 表示闭区间。 |
G)<>:表示:不等于 |
H)模糊查询 |
01)基础查询的语法
select 字段名 from 表名 where 条件
02)字段控制查询
注:distinct字段: 去除字段的重复记录
select distinct 字段名 from 表名 where 条件;
IFNULL(字段,0):函数表示:如果字段是空的,用0代替
select 字段1+IFNULL(字段2,0),字段名 from 表名;
concat()函数:连接字段,形成字符串
select concat(字段名,'的工资是',字段1+IFNULL(字段2,0),'美元' )from 表名;
order by:
字段 asc : 升序排序,默认升序:如果不写,默认升序。
字段 desc: 降序排序,desc必须写。如果有多个排序条件:order by 字段1 desc,字段2 asc,…
order by:排序
03)求年龄
select timestampdiff (year, 字段名, CURDATE())as 年龄 from 表名;
04)聚合函数
count()函数:
统计有多少条记录
语法:select count(*)/count(1) from 表名;
统计某个字段不为空的记录
语法:select count(字段) from from 表名;
sum()函数:统计某个字段的总和
语法:select sum(字段) from 表名;
avg()函数:统计某个字段的平均值
语法:select avg(字段) from 表名;
max()函数:统计某个字段的大值
语法:select max(字段) from 表名;
min()函数:统计某个字段的小值
语法:select min(字段) from 表名;
05)分组查询
语法:group by 要分组的字段
select * from 表名
where 条件
group by 分组
having 对聚合函数进行过滤
order by 排序
limit 分页
having和where的区别?:
01)having:对聚合进行过滤,写在group by 后面,千万不能写where中!!
02)where:对普通字段进行过滤
06)模糊查询
关键字:like
查询不包含某个字符
select * from student where 列名 not like'王%'
查询包含某个字符
select * from student where 列名 like'王%'
07)分页查询
limit:查询指定的记录
语法:limit 起始行-1,行数
select * from 表名 limit 起始行-1,查询几行记录;
公式:
查询前5条 每一页显示5行 pageSize=5
currentPage:显示第几页
pageSize:每页显示几行
select * from 表名 limit (currentPage-1)*pageSize,pageSize
多表查询
01)合并结果集
union 去除重复记录
union all 不去除重复记录
select 字段名 from 表名1
union
select 字段名 from 表名2
02)内连接
select * from 主表 , 子表 where 主表主键字段 = 子表外键字段;
03)等值连接
select 字段名 from 左表名 inner join 右表 on 左表主键 = 从表外键;
04)左外连接
做外链接把左表作为主表
select 字段名 from 左表名 left join 右表 on 左表主键 = 从表外键;
05)右外连接
select 字段名 from 左表名 right join 右表 on 左表主键 = 从表外键;
06)全连接
select 字段名 from 左表名 left join 右表 on 左表主键 = 从表外键;
union
select 字段名 from 左表名 right join 右表 on 左表主键 = 从表外键;
4、DCL数据控制语言用户权限
01)创建新的mysql账户
注:localhost代表只有本机可以登录,远程不可以,也可以省掉
[ @‘localhost’ ]
create user '用户名'@'localhost' identified by '密码';
02)给这个用户授所有权限
注:这是把所有的权限授权给这个用户并允许这个用户给其他用户授权,[
with grant option ] 代表此用户可以给其他用户授权
grant all on *.* to '用户名'@'localhost' with grant option;
03)刷新权限列表
FLUSH PRIVILEGES;
04)收回用户权限
revoke all on *.* from 用户名 cascade;
5、MySQL数据库备份与还原
01)生成SQL脚本
在控制台使用mysqldump命令可以用来生成指定数据库的脚本文本,但要注意,脚本文本中只包含数据库的内容,而不会存在创建数据库的语句!所以在恢复数据时,还需要自已手动创建一个数据库之后再去恢复数据。
未完待续…
JDBC封装源码
JDBC的API组成
01)DriverManager类:加在数据库驱动得到数据库的连接对象
02)Connection接口:表示连接对象,创建这个对象成功,表示数据库连接成功
03)Statement接口:sql语句执行器 增删改:executeUpdate(sql) 查:executeQuery(sql)
04)ResultSet接口:表示一个结果及对象
05)PreparedStatement子接口: 继承自Statement,预编译对象,使用占位符
ResultSetMetaData rsmd= rs.getMetaData();
得到rs这个结果集列的信息
6)CallableStatement 是PreparedStatement子接口,子程序【存储过程,函数】,调用或执行数据库存储过程
{?= call <function-name>[(<arg1>,<arg2>, ...)]}
{call <procedure-name>[(<arg1>,<arg2>, ...)]}
连接池
javax.sql.* DataSource连接池的一个标准 c3p0 实现了DataSource这个接口
ComboPooledDataSource ds=new ComboPooledDataSource();
自动到src下找c3p0-config.xml,读取这个文件中的连接信息
ds.getConnection();
1)连接数据库
使用JDBC连接数据库进行查询的步骤:
1) 导入驱动程序jar包 :mysql-connector-java-5.1.7-bin.jar
2) 加载驱动程序 Class.forName(“com.mysql.jdbc.Driver”);
3) 获取数据库连接对象:Connection
4) 获取发送SQL语句的对象:Statement
5) 创建sql语句
6) 把SQL语句发送到数据库执行
7) 返回结果集对象:ResultSet
8) 遍历结果集对象,获取数据9)关闭连接,释放资源图示:
#连接数据库
import com.mysql.jdbc.Driver;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
public class JdbcConn {
public static void main(String[] args) throws SQLException, ClassNotFoundException {
//2.加载驱动程序
//mysql的驱动对象
//Driver driver = new Driver();
//DriverManager:jav提供的管理驱动的类,调用registerDriver来注册驱动程序
//问题:
// 1)重复注册
//2)有硬编码
//DriverManager.registerDriver(driver);
//解决问题:使用类加载的方式来加载驱动程序
Class.forName("com.mysql.jdbc.Driver");
//3.创建连接数据库的对象:Connection
/*
* 参数1: url : 连接到数据库的url
* jdbc:mysql://IP地址:3306/数据库名?charsetEncoding=utf8
* charsetEncoding=utf8:指定连接数据库的编码格式
* 参数2:数据库用户名
* 参数3:数据库密码
* */
//java.sql包下面
Connection conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/employee5?charsetEncoding=utf8",
"root","sa123");
if(conn!=null){
System.out.println("数据库连接成功!");
}else{
System.out.println("数据库连接失败!");
}
}
}
向数据库插入数据
public void add() throws ClassNotFoundException, SQLException {
//1.加载驱动程序
Class.forName("com.mysql.jdbc.Driver");
//2.获取数据库连接对象
Connection conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/employee5?charsetEncoding=utf8",
"root","sa123");
//3.获取发送sql语句的对象:statement
Statement stmt = conn.createStatement();
//4.创建sql语句
//注意:这里写的SQL语句跟在mysql中语法完全一样!
String sql = "insert into dept values (null,'抖音部','777777')";
//5,把SQL语句发送到数据库执行
//executeUpdate: 执行增/删/改的操作
//i: 表示增/删/改影响的行数
int i = stmt.executeUpdate(sql);
if(i>0){
System.out.println("成功插入["+i+"]条记录!");
}else{
System.out.println("插入失败!");
}
//6.关闭连接,释放资源
stmt.close();
conn.close();
}
2)向数据库修改数据:
注:增、删、改都一样,只需要修改sql语句
//向数据库修改数据
@Test
public void delete() throws ClassNotFoundException, SQLException {
//1.加载驱动程序
Class.forName("com.mysql.jdbc.Driver");
//2.获取数据库连接对象
Connection conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/employee5?charsetEncoding=utf8",
"root","sa123");
//3.获取发送sql语句的对象:statement
Statement stmt = conn.createStatement();
//4.创建sql语句
//注意:这里写的SQL语句跟在mysql中语法完全一样!
String sql = " delete from dept where did=7 ";
//5,把SQL语句发送到数据库执行
//executeUpdate: 执行增/删/改的操作
//i: 表示增/删/改影响的行数
int i = stmt.executeUpdate(sql);
if(i>0){
System.out.println("成功删除["+i+"]条记录!");
}else{
System.out.println("删除失败!");
}
//6.关闭连接,释放资源
stmt.close();
conn.close();
}
3)从数据库查询数据
- 导入驱动程序jar包 :mysql-connector-java-5.1.7-bin.jar
2) 加载驱动程序 Class.forName(“com.mysql.jdbc.Driver”);
3) 获取数据库连接对象:Connection
4) 获取发送SQL语句的对象:Statement
5) 创建sql语句
6) 把SQL语句发送到数据库执行
7) 返回结果集对象:ResultSet
8) 遍历结果集对象,获取数据
9)关闭连接,释放资源图示:
//从数据库查询数据
//使用JDBCUtils工具类
@Test
public void select2() throws ClassNotFoundException, SQLException {
Connection conn = JDBCUtils.getConn();
//3.获取发送sql语句的对象:statement
Statement stmt = conn.createStatement();
//4.创建sql语句
//注意:这里写的SQL语句跟在mysql中语法完全一样!
String sql = " select * from dept ";
//5.把SQL语句发送到数据库执行
//executeQuery:表示查询操作
//6.返回结果集对象:ResultSet
//ResultSet:结果集对象
ResultSet rs = stmt.executeQuery(sql);
//next():当调用next()的时候,游标会向下移动一行
//返回boolean类型,如果没有下一行了,返回false
while (rs.next()){
/*
* 获取数据的方式:
* 1)通过 get数据类型(行下标);
* 2)通过 get数据类型("列的名字");
*
*
* 数据库的类型 java类型
* int getInt()
* char/varchar getString()
* date getDate()
* time getTime()
* timestamp getTimestamp()
* float getFloat()
* double getDouble()
*
* */
System.out.println(rs.getInt(1)+","+
rs.getString("dname")+","+rs.getString(3));
}
//7.关闭连接,释放资源
JDBCUtils.closeAll(conn,stmt,rs);
}
JDBC代码简单优化
方案1:Class反射机制连接
使用工具类来封装JDBC
创建类:JDBCUtils.java
封装加载驱动和获取数据库连接
1) 创建类:JDBCUtils.java 来封装
2) 使用 .properties配置文件来存放jdbc的连接信息案例演示:
db.properties
预编译对象:PreparedStatement , 继承自Statement
#配置文件,用来配置数据库连接信息
#mysql
className=com.mysql.jdbc.Driver
url=jdbc:mysql://localhost:3306/students?characterEncoding=utf8
username=root
password=ROOT
连接数据库的工具类
import java.io.FileReader;
import java.io.IOException;
import java.sql.*;
import java.util.Properties;
/**
* @ClassName JDBCUtils
* @Description TODO 连接数据库的工具类
* @Author zhaojing
* @Date 2020/3/12 17:15
* @Version 1.0
*/
public class JDBCUtils {
//创建全局属性
private static String className;
private static String url;
private static String username;
private static String password;
static {
//加载配置文件,获取连接信息
Properties pro = new Properties();
try {
//写法1:读取配置文件,获取信息
//pro.load(new FileReader("db.properties"));
//写法2:从当前运行的文件根目录去找文件也就是JDBCPackaging的根目录src
pro.load(JDBCPackaging.class.getResourceAsStream("/db.properties"));
//根据key获取value
className = pro.getProperty("className");
url = pro.getProperty("url");
username = pro.getProperty("username");
password = pro.getProperty("password");
} catch (IOException e) {
e.printStackTrace();
}
}
static {
//加载驱动程序
try {
Class.forName(className);
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
//获取数据库连接对象
public static Connection getConn(){
try {
return DriverManager.getConnection(url,username,password);
} catch (SQLException e) {
e.printStackTrace();
throw new RuntimeException("数据库连接错误!");
}
}
//关闭连接,释放资源
public static void closeAll(Connection conn, Statement stmt, ResultSet rs){
if(rs!=null){
try {
rs.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if(stmt!=null){
try {
stmt.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if(conn!=null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
//方法的重载
public void closeAll(Connection conn, Statement stmt){
if(stmt!=null){
try {
stmt.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if(conn!=null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
public void closeAll(Connection conn){
if(conn!=null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}
方案2:线程池技术连接
1.通过线程池方式建立连接
2.提取重复代码封装,子类继承封装后的父类
3.切记一定要导入相关jar包,和配置xml文件
4.命名规范实体类的名+DAO
DAO封装==父类
package day14.exercise.dao;
import day14.exercise.utils.ConnectionPrepared;
import java.sql.*;
/**
* 父类==封装重复的代码
*/
public class BaseDao {
/**
*
* @param sql 要执行的sql语句
* @param params 这个sql中的?所需要参数
*/
protected void executeUpdate(String sql,Object[] params){
//1.得到连接==线程池
Connection conn = ConnectionPrepared.getConnection();
PreparedStatement pstmt = null;
//2.得到预编译对象
try {
pstmt = conn.prepareStatement(sql);
//如果有参数表示sql有占位符
if (pstmt != null){
for (int i = 0; i < params.length; i++) {
pstmt.setObject(i+1,params[i]);
}
}
pstmt.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
}finally {
close(pstmt,conn);
}
}
/**
* 线程池归还连接 两个方法重载
* @param stmt
* @param conn
*/
protected void close(Statement stmt,Connection conn){
try {
if (stmt != null){
stmt.close();
}
} catch (SQLException e) {
e.printStackTrace();
}
try {
if (conn != null){
conn.close();
}
} catch (SQLException e) {
e.printStackTrace();
}
}
protected void close(ResultSet rs,Statement stmt,Connection conn){
try {
if (rs != null){
stmt.close();
}
} catch (SQLException e) {
e.printStackTrace();
}
try {
if (stmt != null){
stmt.close();
}
} catch (SQLException e) {
e.printStackTrace();
}
try {
if (conn != null){
conn.close();
}
} catch (SQLException e) {
e.printStackTrace();
}
}
}
DAO封装==子类
继承了父类封装的方法
优点:
1.优化了占位符
package day14.exercise.dao;
import day14.exercise.utils.ConnectionPrepared;
import day14.exercise.entity.Student;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
public class StudentDao extends BaseDao{
/**
* 实现修改属性
* @param id
*/
public void delete(int id){
String sql = "delete from student where stuid=?";
Object[] params = {id};
executeUpdate(sql,params);
}
/**
* 实现增加记录
* insert into student values(null,?,?,?,?)
*/
public void insert(Student stu){
String sql = "insert into student values(?,?,?,?,?)";
Object[] params = {stu.getStuid(),stu.getName(),stu.getSex(),stu.getBirthday(),stu.getSclass()};
executeUpdate(sql,params);
}
/**
*更新一条记录
*/
public void update(Student stu){
String sql = "update student set name=?,sex=? where id=?";
Object[]params = {stu.getName(),stu.getSex(),stu.getStuid()};
executeUpdate(sql,params);
}
/**
* 查询表记录
*/
public List<Student>findAll(){
String sql = "select * from student";
PreparedStatement pstmt = null;
ResultSet rs = null;
List<Student>list = new ArrayList<>();
Student stu = null;
Connection conn = null;
try {
conn = ConnectionPrepared.getConnection();
pstmt = conn.prepareStatement(sql);
rs = pstmt.executeQuery();
while (rs.next()){
int id = rs.getInt("id");
String name = rs.getString("name");
String sex = rs.getString("sex");
String birthday = rs.getString("birthday");
String sclass = rs.getString("sclass");
stu = new Student(id,name,sex,birthday,sclass);
list.add(stu);
}
} catch (SQLException e) {
e.printStackTrace();
}finally {
close(rs,pstmt,conn);
}
return list;
}
public Student findById(int id){
//1.定义sql
String sql = "select * from student where id = ?";
PreparedStatement pstmt = null;
ResultSet rs = null;
Student stu = null;
Connection conn = null;
try {
conn = ConnectionPrepared.getConnection();
pstmt = conn.prepareStatement(sql);
pstmt.setInt(1,id);
rs = pstmt.executeQuery();
if (rs.next()){//true表示有一条记录
int sid = rs.getInt("id");
String name = rs.getString("name");
String sex = rs.getString("sex");
String birthday = rs.getString("birthday");
String aClass = rs.getString("class");
stu = new Student(sid,name,sex,birthday,aClass);
return stu;
}
}catch (Exception e){
e.printStackTrace();
}finally {
close(rs,pstmt,conn);
}
return stu;
}
}
实体类==实例化存储表对象
package day14.exercise.entity;
public class Student {
private Integer stuid;
private String name;
private String sex;
private String birthday;
private String sclass;
public Student() {
}
public Student(Integer stuid, String name, String sex, String birthday, String sclass) {
this.stuid = stuid;
this.name = name;
this.sex = sex;
this.birthday = birthday;
this.sclass = sclass;
}
public Integer getStuid() {
return stuid;
}
public void setStuid(Integer stuid) {
this.stuid = stuid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
public String getBirthday() {
return birthday;
}
public void setBirthday(String birthday) {
this.birthday = birthday;
}
public String getSclass() {
return sclass;
}
public void setSclass(String sclass) {
this.sclass = sclass;
}
@Override
public String toString() {
return "Student{" +
"stuid=" + stuid +
", name='" + name + '\'' +
", sex='" + sex + '\'' +
", birthday='" + birthday + '\'' +
", sclass='" + sclass + '\'' +
'}';
}
}
工具类==创建线程池
package day14.exercise.utils;
import com.mchange.v2.c3p0.ComboPooledDataSource;
import java.sql.Connection;
import java.sql.SQLException;
public class ConnectionPrepared {
private static ComboPooledDataSource dataSource;
public ConnectionPrepared() {
}
static {
dataSource = new ComboPooledDataSource();
}
public static Connection getConnection(){
try {
return dataSource.getConnection();
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
}
模拟用户登录
//模拟用户登录操作
@Test
public void login() throws SQLException {
/*
* 1、如果用户登录成功,提示登录成功
* 2、如果登录失败,提示登录失败
* */
Scanner input = new Scanner(System.in);
System.out.println("请输入用户名:");
String username = input.nextLine();
System.out.println("请输入密码:");
String userpwd = input.nextLine();
//根据输入的用户名和密码去数据库查询
Connection conn = JDBCUtils.getConn();
Statement stmt = conn.createStatement();
String sql = "select * from users where username = '"+username+"' and userpwd = '"+userpwd+"'";
System.out.println("sql:"+sql);
ResultSet rs = stmt.executeQuery(sql);
/*
* SQL注入问题:
* 输入: 123' or '1'='1
*
* 为什么会产生问题:
* 1)statement是通过拼接字符串来创建SQL语句的,所以就可以改变SQL语句的结构
* 正常:select * from users where username='admin' and userpwd = 'admin';
* 改造后:select * from users where username = 'root' and userpwd = '123' or '1'='1'
* 2)statment是创建完SQL语句之后,再发送到数据库执行,这样就可能执行修改过的语句。
* */
//如果查询的是一条数据,不需要while
//使用if判断
if(rs.next()){
System.out.println("登录成功!");
}else{
System.out.println("登录失败!");
}
JDBCUtils.closeAll(conn,stmt,rs);
}
//模拟用户登录操作
//使用预编译对象进行改造
@Test
public void login2() throws SQLException {
/*
* 1、如果用户登录成功,提示登录成功
* 2、如果登录失败,提示登录失败
* */
Scanner input = new Scanner(System.in);
System.out.println("请输入用户名:");
String username = input.nextLine();
System.out.println("请输入密码:");
String userpwd = input.nextLine();
//根据输入的用户名和密码去数据库查询
Connection conn = JDBCUtils.getConn();
//创建SQL语句
String sql = "select * from users where username = ? and userpwd = ?";;
//创建预编译的对象
PreparedStatement ps = conn.prepareStatement(sql);
//给占位符设置值
//语法:set数据类型(占位符的位置,占位符的值);
ps.setString(1,username);
ps.setString(2,userpwd);
//执行查询
//注意:这里不能再添加sql参数了!
ResultSet rs = ps.executeQuery();
System.out.println("sql:"+sql);
/*
* 预编译对象解决SQL注入问题:
* 1)使用占位符? 来创建SQL语句,当创建预编译对象的时候,就提前把SQL语句发送到数据库保存(缓存)
* 数据库获取到该SQL语句的结构,无法再修改。
* 2)执行查询的时候,发送的不是SQL语句,而是占位符的值!!!
* */
//如果查询的是一条数据,不需要while
//使用if判断
if(rs.next()){
System.out.println("登录成功!");
}else{
System.out.println("登录失败!");
}
JDBCUtils.closeAll(conn,ps,rs);
}
线程池技术
jdbc java.sql.*这个包
DataSource javax.sql.* 也是一个接口,表示是一个标准是一个规范 连接池
连接池:集合,中保存了100个连接
连接Connection java程序 sql connection 数据库
连接池的实现 dbcp 连接池 c3p0 …
1.增加c3p0支持jar
2.在src中增加c3p0-config.xml文件
package com.kgc.utils;
import com.mchange.v2.c3p0.ComboPooledDataSource;
import javax.sql.DataSource;
public class DataSourcePooled {
//构造DataSource对象作为返回值对象
private static DataSource dataSource;
//创建无参构造
private DataSourcePooled(){}
//new ComboPooledDataSource();对象连接线程池
static {
//创建一个连接池的对象,读取src下的那个连接文件
dataSource=new ComboPooledDataSource();
}
public static DataSource getDataSource(){
return dataSource;
}
}
c3p0
<?xml version="1.0" encoding="UTF-8"?>
<c3p0-config>
<!-- 默认配置,如果没有指定则使用这个配置 -->
<default-config>
<property name="user">root</property>
<property name="password">root</property>
<property name="jdbcUrl">jdbc:mysql://localhost:3306/test</property>
<property name="driverClass">com.mysql.jdbc.Driver</property>
</default-config>
</c3p0-config>
DBUtils组件
DBUtils组件所提供的API
QueryRunner类
query() 完成查询的方法
update() 增加删除修改的方法,
需要提供DataSource或Connection就对象
ResultSetHandler 查询的API
Serializable 8 个包装类+String 都实现了
将查询结果集中每一行映射成一个类型的对象
自动匹配【字段的值 赋给对象的属性】要求,表中字段的名称与属性名相同
new BeanHandler(Student.class) 将查询出来一条记录映射成Student类的对象 返回
new BeanListHandler<Student>(Student.class) 将查询出来一条记录映射成Student类的对象 返回
QueryRunner queryRunner=new QueryRunner(datasource);
queryRunner.update(sql,objs[])
runner.update(sql,Object ... parms});
runner.query(sql,new BeanHandler<Student>(Student.class),new Object[]{1,2,3})
runner.query(sql,new BeanListHandler<Student>(Student.class),new Object[]{1,2,3})
select count(*) from student;
三层架构
Dao层
父接口Dao
命名规范:Dao
import java.io.Serializable;
import java.util.List;
public interface Dao <T>{
/**
* 增加
*/
public void insert(T t);
/**
* 删
*/
public void delete(T t);
/**
* 改
*/
public void update(T t);
/**
* 查
*/
//public void select(Serializable serializable);
List<T>findAll();
T findById(Serializable id);
继承接口
命名规范:实体名+Dao
import day15.entity.Student;
import java.util.List;
public interface StudentDao extends Dao<Student> {
public Student login(String name,String pwd);
/**
* 用于分页查询
* @param page
* @param size
* @return
*/
List<Student>findByPage(int page,int size);
}
impl实现类
命名规范:实体名+Dao+Impl
import day15.dao.StudentDao;
import day15.entity.Student;
import day15.utils.DataSourcePooled;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import java.io.Serializable;
import java.sql.SQLException;
import java.util.List;
public class StudentDaoImpl implements StudentDao {
//utils提供的方法==简化了SQL查询功能
QueryRunner runner = new QueryRunner(DataSourcePooled.getDataSource());
@Override
public Student login(String name, String pwd) {
String sql="select * from student where name=? and pwd=?";
Student student = null;
try {
//通过反射得到user对象,new BeanHandler<Student>获取一个目标对象;
// new BeanListHandler<Student>获取多个目标对象的集合;
runner.query(sql,new BeanHandler<Student>(Student.class));
} catch (SQLException e) {
e.printStackTrace();
}
return student;
}
@Override
public List<Student> findByPage(int page, int size) {
String sql="select * from tbl_user where name=? and pwd=?";
List<Student> list = null;
try {
list = runner.query(sql,new BeanListHandler<Student>(Student.class));
} catch (SQLException e) {
}
return list;
}
@Override
public void insert(Student student) {
String sql = "insert into student values(null,?,?,?,?)";
int i= 0;
try {
i = runner.update(sql, student.getSname(), student.getSex(), student.getBirthday(), student.getS_class());
} catch (SQLException e) {
e.printStackTrace();
}
if (i>0) {
System.out.println("成功添加了" + i + "条记录");
}else {
System.out.println("添加失败!");
}
}
@Override
public void delete(Student student) {
String sql = "delete from student where stuid=?";
int i =0;
try {
i = runner.update(sql, student.getStuid());
} catch (SQLException e) {
e.printStackTrace();
}
if (i>0) {
System.out.println("成功删除了" + i + "条记录");
}else {
System.out.println("删除失败!");
}
}
@Override
public void update(Student student) {
String sql = "update student set sname = ? ,sex = ? ,birthday = ? , s_class = ? where stuid= ?";
int i =0;
Object[] params=new Object[]{
student.getSname(), student.getSex(),student.getBirthday(),student.getS_class(),student.getStuid()
};
try {
i = runner.update(sql, params);
} catch (SQLException e) {
e.printStackTrace();
}
if (i>0) {
System.out.println("成功修改了" + i + "条记录");
}else {
System.out.println("修改失败!");
}
}
@Override
public List<Student> findAll() {
String sql = "select * from student";
List<Student> list = null;
try {
list = runner.query(sql,new BeanListHandler<Student>(Student.class));
} catch (SQLException e) {
e.printStackTrace();
}
return list;
}
@Override
public Student findById(Serializable id) {
String sql = "select * from student";
Student student = null;
try {
student = runner.query(sql,new BeanHandler<Student>(Student.class));
} catch (SQLException e) {
e.printStackTrace();
}
return student;
}
}
entity层
实体类
命名规范:跟表名一直,属性名也要一直
public class Student {
private Integer stuid;
private String sname;
private String sex;
private String birthday;
private String s_class;
public Student(Integer stuid) {
this.stuid = stuid;
}
public Student(){
}
public Student(Integer stuid, String sname, String sex, String birthday, String s_class) {
this.stuid = stuid;
this.sname = sname;
this.sex = sex;
this.birthday = birthday;
this.s_class = s_class;
}
public Integer getStuid() {
return stuid;
}
public void setStuid(Integer stuid) {
this.stuid = stuid;
}
public String getSname() {
return sname;
}
public void setSname(String sname) {
this.sname = sname;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
public String getBirthday() {
return birthday;
}
public void setBirthday(String birthday) {
this.birthday = birthday;
}
public String getS_class() {
return s_class;
}
public void setS_class(String s_class) {
this.s_class = s_class;
}
@Override
public String toString() {
return "Student{" +
"stuid=" + stuid +
", s
name='" + sname + '\'' +
", sex='" + sex + '\'' +
", birthday='" + birthday + '\'' +
", s_class='" + s_class + '\'' +
'}';
}
}
utils层
工具类
import com.mchange.v2.c3p0.ComboPooledDataSource;
import javax.sql.DataSource;
public class DataSourcePooled {
private static DataSource dataSource;
public DataSourcePooled() {
}
static {
//utils提供的连接线程池方法
dataSource = new ComboPooledDataSource();
}
public static DataSource getDataSource(){
return dataSource;
}
}
Tomcat
url地址语法格式
http : //ip地址 : 端口号/项目名/资源路径?参数=值
目录结构
bin : 放的是启动tomcat的程序:startup.bat shutdown.bat
conf : 放的是配置文件 : server.xml tomcat- user.xml web.xml
webapps : 放的是所有的资源文件(web项目)
work : 动态资源文件编译之后存放的位置
lib : 存放tomcat启动的jar包,和第3方jar包
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ijQ0WzaU-1603283389750)(java封装源码.assets/1599229762205.png)]
01)Tomcat启动和访问
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-WA3CBcUQ-1603283389754)(java封装源码.assets/1599229784689.png)]
使用cmd来启动和关闭tomcat:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Fblfltys-1603283389756)(java封装源码.assets/1599229804725.png)]
02)端口占用问题
步骤:
1)在DOS下键入netstat -ano|findstr 8080查看占用8080端口的
配置文件都在 conf 文件夹下面 ,可以关掉相关进程
1、 修改端口号:修改server.xml
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-rCQVL63s-1603283389757)(java封装源码.assets/1599229997207.png)]
1、 配置用户名和密码:修改tomcat-users.xml
<user username="zhaojing" password="123456" roles="manager-gui"/>
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-iUJqi2b7-1603283389759)(java封装源码.assets/1599230111188.png)]
03)设置资源同步tomcat
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ODmR6wk1-1603283389760)(java封装源码.assets/1599802369510.png)]
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-tAQhUclk-1603283389760)(java封装源码.assets/1599802382104.png)]
JSP
01)jsp技术连接数据库
dao文件代码
public class UserDaoImpl implements UserDao {
//创建 QueryRunner对象 连接线程池
QueryRunner runner = new QueryRunner(DataSourcePooled.getDataSource());
@Override
//查找的方法
public User login(String u_name, String u_pwd) {
String sql = "select * from s_user where u_name =? and u_pwd = ? ";
User user = null;
try {
user = runner.query(sql,new BeanHandler<User>(User.class),u_name,u_pwd);
} catch (SQLException e) {
e.printStackTrace();
}
return user;
}
}
登录页面代码
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>用户登录</title>
</head>
<body>
//yanzheng.jsp 验证的jsp文件
<form method="post" action="yanzheng.jsp">
账号:<input type="text" name="amin"/> <br/>
密码:<input type="password" name="pwd"/><br/>
<input type="submit" value="提交"/>
</form>
</body>
</html>
验证jsp代码
<%
User user = new User();
UserDaoImpl userDao = new UserDaoImpl();
//通过request.getParameter方法得到value的值
String amin = request.getParameter("amin");
String pwd = request.getParameter("pwd");
//如果返回的对象为空则数据库没有
if (userDao.login(amin,pwd)!=null ){
response.sendRedirect("register.jsp");
}else {
//window.location.href='amids.jsp';如果密码错误回到登录页面
out.print("<script>alert('账号或密码不正确!');window.location.href='amids.jsp'; </script>");
}
%>
02)Web程序的结构
工程名 myweb
src 源码目录
web 目录 根目录 通过浏览器访问的是这个目录下的文件
WEB-INF 这个目录是web程序的私有目录,外部不能不能直接访问
web.xml web程序的描述文件 完成程序的注册
<welcome-file-list>
<welcome-file>index.jsp</welcome-file>
<welcome-file>hello.jsp</welcome-file>
</welcome-file-list>
发一个请求http://localhost:8080/index.jsp
lib目录 存放第三方jar包 c3p0 mysql…
classes目录 存放src目录下所有源码编译后的字节码文件 class文件
03)jsp执行原理
java server page java服务器端的页面
jsp=html+java代码 html可以使用浏览器直接打开 java 要有java运行的环境 浏览器不能直接打开jsp文件
jsp 运行环境 tomcat
1.转译 index.jsp----转译—index_jsp.java文件
2.编译 -index_jsp.java 编译成 -index_jsp.class 字节码
3.执行这个字节码全部生成html标签
4.浏览器就可以打开这个html标签
第一次通过tomcat来访问jsp,经过上面这个流程
04)jsp指令
page import taglib uri prefix include file
指令<% @ 指令名 属性="" 属性=“”%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
1) page:设置页面属性导包
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ page import ="com.kgc.entity.*,com.kgc.dao.*"%>
<%@ page import ="com.kgc.utils.*"%>
2)taglib指令 导入标签库 jstl
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
3)index.jsp index_jsp.java
index.jsp index_jsp.java
<%@ include file="table.jsp"%> 静态包含 默诵与编译不生新文件,只有一个文件 index_jsp.java
…未完待续
05)JSP内置对象
对象名 | 作用 | 作用域 |
---|---|---|
out | 输出对象 类型是PrintWriter打印流,在页面输出 | 把文本输出到客户端 : out.write() |
response | 响应对象 | 一次请求中有效 |
session | 会话对象 | 在一次会话中有效 |
application | 应用程序对象 | 在整个tomcat运行期间有效 |
page | 当前页面对象 跟this同理 | |
pageContext | 上下文对象,通过这个对象可以得到其它8内置jsp的对象 | 在当前页面有效 |
config | 配置对象 | |
exception | 异常对象 |
response
session
application
pageContext
//四个内置对象都具有以下共同方法
getAttribute()
setAttribute()
removeAttribute()
06)JS常用API
方法名 | 作用 |
---|---|
request.getHeaderNames(); | 返回所有请求头的名称 |
request.getHeader(name); | 根据请求头的名称来得到它的值 |
request.getParameter(“name”); | 返回对象的value的值 |
代码块 jsp中加java代码
<table width="500px" border="1px">
<tr>
<th>编号</th> <th>姓名</th> <th>年龄</th>
</tr>
<%
for(int i=10;i<100;i+=10) {
%>
<tr>
<td>101</td><td>张三</td><td>23</td>
</tr>
<%}
%>
</table>
<%
Date date=new Date();
SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd");
String rq=sdf.format(date);
out.print(rq);
out.print("<br/>")
out.prnt("<hr width=200px/>")//out.print()会内容输出在网页面上
%>
表达式:计算并输出计算结果
<%=表达式 %> 在jsp的当前位置输出这个表达式的结果
name=<%=name %> 变量表达式后没有;
name=<%out.print(name);%>
<%=变量名/10+100 %>
07)表达式
脚本 | 代码片段 | 作用 |
---|---|---|
Java语句 | <% 内容%> | 方法的范围:方法中可以写啥,这里就可以写啥 |
Java表达式 | <%= 内容 %> | Systerm.out.println() 中可以写啥,这里就可以写啥 |
Java定义类成员 | <%! 内容%> | 类的范围,类中可以写啥,这里就可以写啥 |
08)转发
<%--转发--%>
<%--<% request.getRequestDispatcher("/test04.jsp").forward(request,response); %>--%>
<%--使用动作标签进行转发--%>
<%--
注意:
1)如果不加参数:不能换行写,只能这么写:<jsp:forward page="/test04.jsp"></jsp:forward>
2)如果加了参数,参数不能写任何注释
--%>
<%--设置request请求中文编码--%>
<%request.setCharacterEncoding("utf-8");%>
<jsp:forward page="/test04.jsp">
<jsp:param name="username" value="郭德纲"></jsp:param>
</jsp:forward>
可通过转发功能简化打开登录界面的步骤
<%--通过jsp转发功能简化访问的步骤--%>
<jsp:forward page="pages/main.jsp"></jsp:forward>
Servlet
Servlet的Web.xml配置
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
http://java.sun.com/xml/ns/javaee/web-app_4_0.xsd"
version="4.0">
<servlet>
<!--servlet的名字-->
<servlet-name>ServletDemo</servlet-name>
<!--servlet的全路径-->
<servlet-class>cn.kgc.ServletDemo</servlet-class>
<!--设置初始化参数-->
<init-param>
<param-name>code</param-name>
<param-value>utf-8</param-value>
</init-param>
<!--servlet加载的优先级,配置之后,当tomcat一启动,就创建servlet对象==不过这个一般情况不配置!!!-->
<!--里面的数字表示如果有多个配置存在的话,执行的顺序,1代表第一个,2代表第二个-->
<load-on-startup>1</load-on-startup>
</servlet>
<!--映射配置-->
<servlet-mapping>
<!--servlet的名字,必须要跟servlet-name标签中的完全一致!-->
<servlet-name>ServletDemo</servlet-name>
<!--url的虚拟路径-->
<url-pattern>/ServletDemo</url-pattern>
</servlet-mapping>
</web-app>
01)实现Servlet的方式
1) 实现javax.servlet.Servlet接口
2) 继承javax.servlet.GenericServlet类
3) 继承javax.servlet.http.HttpServlet类 = 常用的方式
1)实现Servlet接口
Servlet接口相关类型:
接口名 | 作用 |
---|---|
ServletRequest | 表示请求对象,请求对象里面保存的就是浏览器发送的请求数据 |
ServletResponse | 表示响应对象,响应对象里面保存的就是服务器返回给浏览器的响应数据 |
ServletConfig | 它表示Servlet配置对象,它对应Servlet的配置信息 |
ServletConfig | 对象一般用来获取项目配置的初始化信息 |
2)继承GenericServlet类
(范围太大,需要强转,比较麻烦)
3)继承HttpServlet类==常用
继承自GenericServlet类
ctrl+o重写doGet和doPost方法
01)实现添加的代码
package cn.kgc.servlet;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
public class MyServlervlet02 extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
UserDaoImpl userDao = new UserDaoImpl();
//处理中文乱码问题
req.setCharacterEncoding("utf-8");
resp.setContentType("text/html;charset=utf-8");
//接收请求
String name = req.getParameter("name");
String pwd = req.getParameter("pwd");
String pwd2 = req.getParameter("pwd2");
//处理请求
if (pwd.equals(pwd2)){
if (userDao.login(name,pwd) == null) {
User user = new User(name,pwd);
String insert = userDao.insert(user);
//返回响应
resp.getWriter().write("<script>alert('成功添加"+insert+"条记录'); window.location.href='amids.jsp'; </script>");
}else {
resp.getWriter().write("<script>alert('您注册的账号已存在,请更换用户名!');window.location.href='amids.jsp'; </script>");
}
}else {
resp.getWriter().write("<script>alert('两次输入密码不一致!'); window.location.href='amids.jsp'; </script>");
}
}
}
//在一个方法里调用另外一个方法可以让所有都在doPost或者doGet内执行
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
this.doGet(req,resp);
}
}
02)实现查找的代码
//可代替xml配置 @WebServlet(urlPatterns = "/SelectServlet")
@WebServlet(urlPatterns = "/SelectServlet")
public class SelectServlet extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doGet(request,response);
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
UserDaoImpl userDao = new UserDaoImpl();
//实现Dao层封装的查找方法
List<User> list = userDao.findAll();
//request.getSession();得到一个会话对象:session
HttpSession session = request.getSession();
//通过list可自定义,通过此方法可传递对象到jsp中
session.setAttribute("list",list);
//完成响应,作出跳转
response.sendRedirect("jsp/listUser.jsp");
}
}
03)JSP中的代码
<html>
<head>
<title>Title</title>
</head>
<body>
<h2>用户浏览信息</h2>
<%
//从session中取出list属性
List<User>list = (List<User>)session.getAttribute("list");
//使用java中的命名list取出对象的值
Object list1 = session.getAttribute("list");
//得到的是一个Object类型,所以需要强制转换
List<User>list2 = (List<User>)list1;
%>
<table width="500px" border="1">
<tr>
<th>用户</th><th>密码</th>
</tr>
<%
if (list != null){
for (User user : list) {
%>
<tr>
<td><%=user.getU_name()%></td>
<td><%=user.getU_pwd()%></td>
</tr>
<%}}%>
</table>
</body>
</html>
04)登录界面代码
<html>
<head>
<title>用户登录</title>
</head>
<body>
<div>
//通过java配置 @WebServlet(urlPatterns = "/SelectServlet")之后 //action="SelectServlet"可以直接写类名调用
<form method="post" action="SelectServlet">
<input type="submit" value="显示所有用户数据"/>
</form>
</div>
<div>
<h1>验证用户登录</h1>
<form method="post" action="jsp/yanzheng.jsp">
账号:<input type="text" name="amin"/> <br/>
密码:<input type="password" name="pwd"/><br/>
<input type="submit" value="提交"/>
</form>
</div>
<div>
<h1>添加用户数据</h1>
<form method="post" action="HttpServletUser">
用户名:<input type="text" name="name"><br/>
密码: <input type="text" name="pwd"><br/>
确密码:<input type="text" name="pwd2"><br/>
<input type="submit" value="提交"/>
</form>
</div>
<div>
<h1>删除用户数据</h1>
<form method="post" action="DeleteServlet">
删除的用户名:<input type="text" name="name"/><br/>
请输入用户密码:<input type="text" name="pwd"/><br/>
<input type="submit" value="确认"/>
</form>
</div>
<div>
//还没实现
<h1>修改用户数据</h1>
<form method="post" action="DeleteServlet">
删除的用户名:<input type="text" name="name"/><br/>
请输入用户密码:<input type="text" name="pwd"/><br/>
<input type="submit" value="确认"/>
</form>
</div>
</body>
</html>
02)Response对象==响应体
1)Response对象概述(重点)
负责对浏览器进行响应的对象
ServletResponse接口,HttpServletResponse接口继承自ServletResponse 使用的是子接口 HttpServletResponse,此接口对象由Tomcat引擎提供 可以实现对客户端的响应, 响应行,响应头,响应体
2)Response设置响应行(重点)
设置状态码: setStatus(int 状态码)
状态码 | 状态 |
---|---|
404 | 找不到资源=路径错误 |
500 | 程序错误 |
302 | 重定向 |
200 | 正确成功响应 |
一般都是浏览器自动设置好的,浏览器会自动检测,设置合适的状态码
3)Response设置响应头(重点)
返回值 | 方法 | 作用 |
---|---|---|
void | setHeader(String key,String value) | HTTP协议的响应头,数据格式键值对 k:v 包含指导性信息,指导客户端 |
4)Response设置响应体(重点)
HTTP的响应体,就是页面的正文部分
1)getWriter() :返回值是打印流
resp.getWriter().write("网页输出内容");
2)响应中的中文乱码问题
1、 post请求和响应中文乱码
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
2、get请求和响应中文乱码怎么解决==9版本解决方式
在server.xml中加上URIEncoding=“utf-8”
<Connector port="8089" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" URIEncoding="utf-8"/>
03)Request对象==接收请求
1)Request对象获取请求行
返回值类型 | 方法 | 作用 |
---|---|---|
String | getMethod() | 获取提交的方式 (GET,POST) |
String | getContextPath() | 获取WEB应用名称(重点) |
String | getRemoteAddr() | 返回当前客户端的IP地址 |
2)Request对象获取请求头(了解)
请求头数据格式键值对, k:v 指导性信息,指导服务器
返回值类型 | 方法 | 作用 |
---|---|---|
String | getHeader(String key) | 根据请求头名称,返回请求头的值 |
Enumeration | getHeaderNames() | 得到所有的键(请求头),并存在一个Enumeration枚举类型里。 |
3)Request获取请求参数(重点)
01)数据通过request的请求参数传递到服务器。
返回值类型 | 方法 | 作用 |
---|---|---|
String | getParameter(“表单中的name值”) | 获取指定的请求参数 |
String[] | getParameterValues(“表单中的name值”) | 获取参数中的一键多值 |
Map<String,String[]> | getParameterMap() | 获取提交的所有参数 |
02)beanUtils的使用:
//populate:可以直接把map中的数据赋值给实体类的属性!!!
//注意:表单中的name属性的名字必须要跟实体中的属性的名字完全一致!!!
BeanUtils.populate(实体对象,map集合);
03)对象里包含时间日期类型解决方法
//populate:可以直接把map中的数据赋值给实体类的属性!!!
//注意:表单中的name属性的名字必须要跟实体中的属性的名字完全一致!!!
UserDemo userdemo = new UserDemo();
try {
//需要把String类型的日期转换成Date类型的日期
//DateConverter:日期转换器
DateConverter dateConverter = new DateConverter();
//设置转换格式
dateConverter.setPatterns(new String[]{"yyyy-MM-dd","yyyy-MM-dd HH:mm:ss"});
//实现注册转换
ConvertUtils.register(dateConverter, Date.class);
BeanUtils.populate(userdemo,parameterMap);
//爱好单独处理
userdemo.setChk(Arrays.toString(chks));
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
System.out.println(userdemo);
4)Request域对象(重点)
返回值类型 | 方法 | 作用 |
---|---|---|
void | setArratibute(String key, Object value) | 域对象存储数据: |
Object | getAttribute(String key) | 取出域对象数据 |
void | removeAttribute(String key) | 移除域对象数据 |
04)重定向(重点)
作用:
1、通过一个servlet访问到另外一个servlet
2、通过一个servlet访问到一个js页面
概念:两次访问和请求:
1、页面先发送请求给A服务器,A服务器给页面响应另外一个服务器B的地址。
2、页面重新访问B服务器完成响应;
//两步合成一步:
//注意:如果有项目名,那么在url中必须写项目名;
response.sendRedirect("文件路径");
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-gYQGA19w-1603283389762)(java封装源码.assets/1599611771595.png)]
05)转发(重点)
转发的实现步骤:
1) request对象方法获取转发器 RequestDispatcher getRequestDispatcher(“转发地址”)返回值就是转发器
request.getRequestDispatcher("jsp/UpleUser.jsp").forward(request,response);
2) 使用转发器对象的方法 forward
3) 转发的时候:注意:不需要再写项目名!!
06)转发和重定向区别
1)转发和重定向的区别?
1、 转发是1次请求和响应;重定向2次请求和响应。
2、 转发的URL地址不变;重定向URL地址会发生变化。
3、 转发是发生在服务器的内部;重定向返回了客户端
4、 转发的请求里面的数据一直有效;重定向的请求不会携带数据的。
5、 转发不需要再写应用的名字;重定向是需要写应用的名字。
2)什么时候用转发,什么时候用重定向?
如果你想得到request请求的数据,必须用转发; 如果我们不需要request请求的数据,用重定向。
07)作用域
概念:实现数据通过共享来实现数据的传递
作用域对象 | 范围 | 调用方式 |
---|---|---|
pageContext | 本页面 | jsp内置对象 |
request | 一个请求中共享数据,生命周期短 | 内置对象,可直接调用 |
session | 每用户 购物车 session.invalidate(); 同一个浏览器不同窗口打开文件都可以共享,关闭浏览器销毁; | 需创建 |
application | 每应用程序,tomcat服务器为每一个应用创建一个application对象,这个对象可以供所有用户访问 | jsp内置对象 |
//存数据
request.setAttribute(key,value)
//取数据
request.getAttribute(key,value)
//示例 得到一个会话对象
HttpSession session = request.getSession();
session.setAttribute("list",list);
<%
//application对象
//点一次页面num++;
Object obj= application.getAttribute("num");
Integer num=null;
if(obj==null){
application.setAttribute("num",new Integer(1));
num=1;
}else{
num=(Integer)obj;
num++;
application.setAttribute("num",num);
}
%>
num=2
实现修改功能
1.获取当前点击用户的一个id属性值
2.通过id去数据库查找该行的所有属性值,返回一个对象集合,通过session作用域对象存入
3.从session中取出属性,显示在页面上,在提交给修改的类方法
4.返回修改结果
<html>
<head>
<title>Title</title>
</head>
<body>
<h2>用户浏览信息</h2>
<%
//从session中取出list属性
List<User> list = (List<User>)session.getAttribute("list");
%>
<table width="500px" border="1">
<tr>
<th>用户</th><th>密码</th>
</tr>
<%
if (list != null){
for (User user : list) {
%>
<tr>
<%--<td><a href="/UpleServlet?u_name=<%=user.getU_name()%>"><%=user.getU_name()%></a></td>--%>
<td><%=user.getU_name()%></td>
<td><%=user.getU_pwd()%></td>
//获取当前属性的name属性值
<td><a href="../../UpleServlet?u_name=<%=user.getU_name()%>">修改</a></td>
</tr>
<%}}%>
</table>
</body>
</html>
@WebServlet(urlPatterns = "/UpleServlet")
public class UpleServlet extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
String name = request.getParameter("u_name");
UserDaoImpl userDao = new UserDaoImpl();
User user = userDao.findById(new User(name));
request.setAttribute("user",user);
System.out.println(user);
request.getRequestDispatcher("jsp/UpleUser.jsp").forward(request,response);
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doPost(request,response);
}
}
<html>
<head>
<title>修改</title>
</head>
<body>
<%
User user = (User) request.getAttribute("user");
%>
<div>
<h1>修改用户数据</h1>
<form method="post" action="upServlet">
更改用户名:<input type="text" name="amid" value="<%=user.getU_name()%>"/><br/>
更改用户密码:<input type="text" name="pwd" value="<%=user.getU_pwd()%>"/><br/>
<input type="submit" value="确认"/>
</form>
</div>
</body>
</html>
@WebServlet(urlPatterns = "/upServlet")
public class upServlet extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
String amid = request.getParameter("amid");
String pwd = request.getParameter("pwd");
UserDaoImpl userDao = new UserDaoImpl();
String user = userDao.update(new User(amid, pwd));
response.getWriter().write("<script>alert('"+user+"');window.location.href='amids.jsp'; </script>");
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doPost(request,response);
}
}
08)Servlet封装
1、Servlet封装
@WebServlet(urlPatterns = "/UserServlet")
public class UserServlet extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String method = request.getParameter("method");
if (method.equals("doList")){
this.dofindAll(request,response);
}else if (method.equals("insert")){
this.doInsert(request,response);
}else if (method.equals("doEnter")){
this.doEnter(request,response);
}else if (method.equals("doDelete")){
this.doDelete(request,response);
}else if (method.equals("doUpdate")){
this.doUpdate(request,response);
}else if (method.equals("doUpdateUser")){
this.doUpdateUser(request,response);
}else {
this.doList(request,response);
}
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doPost(request,response);
}
//验证登录
protected void doEnter(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
UserDaoImpl userDao = new UserDaoImpl();
//处理中文乱码问题
req.setCharacterEncoding("utf-8");
resp.setContentType("text/html;charset=utf-8");
//接收请求
String name = req.getParameter("amin");
String pwd = req.getParameter("pwd");
String mm = req.getParameter("mm");
User login = userDao.login(name, pwd);
Cookie cookiename = null;
Cookie cookiepwd = null;
if (login != null){
/*if (mm.equals("1")){
cookiename = new Cookie("name",name);
cookiepwd = new Cookie("pwd",pwd);
cookiename.setMaxAge(60*60*60);
cookiepwd.setMaxAge(60*60*60);
System.out.println(cookiename.getName()+"---"+cookiepwd);
}*/
HttpSession session = req.getSession();
session.setAttribute("amin",name);
doList(req, resp);
/*resp.sendRedirect("jsp/listUser.jsp");
req.getRequestDispatcher("jsp/listUser.jsp").forward(req,resp);*/
}else {
resp.getWriter().write("<script>alert('账号或密码不正确!');" +
"window.location.href='Enter.jsp'; </script>");
}
}
//用户注册
protected void doInsert(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
UserDaoImpl userDao = new UserDaoImpl();
//处理中文乱码问题
req.setCharacterEncoding("utf-8");
resp.setContentType("text/html;charset=utf-8");
//接收请求
String amin = req.getParameter("amin");
System.out.println(amin);
String pwd = req.getParameter("pwd");
String pwd2 = req.getParameter("pwd2");
//处理请求
User byId = userDao.findById(new User(amin));
System.out.println(byId);
if (byId == null){
if (pwd.equals(pwd2)){
userDao.insert(new User(amin,pwd));
resp.getWriter().write("<script>alert('注册成功!'); " +
"window.location.href='Enter.jsp'; </script>");
}else {
resp.getWriter().write("<script>alert('两次输入密码不一致!'); " +
"window.location.href='Enter.jsp'; </script>");
}
}else {
resp.getWriter().write("<script>alert('您注册的账号已存在,请更换用户名!');" +
"window.location.href='UserLogin.jsp'; </script>");
}
}
//用户浏览
protected void doList(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
List<User> list = null;
String amd = request.getParameter("amd");
String pw = request.getParameter("pw");
// List<User> list= null;
UserDao userDao=new UserDaoImpl();
//List<User> list = userDao.findAllwhere(new User(amd, pw));
if (amd==null && pw ==null){
list = userDao.findAll();
}else {
list = userDao.findAllwhere(new User(amd,pw));
}
//得到一个会话对象
HttpSession session = request.getSession();
session.setAttribute("list",list);
request.getRequestDispatcher("jsp/listUser2.jsp").forward(request,response);
}
//删除用户
protected void doDelete(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
UserDaoImpl userDao = new UserDaoImpl();
//获取请求
String name = request.getParameter("u_name");
System.out.println(name);
User byId = userDao.findById(new User(name));
System.out.println(byId);
userDao.delete(new User(name));
System.out.println("调用删除的方法");
//response.sendRedirect("jsp/listUser.jsp");
doList(request,response);
/* request.getRequestDispatcher("jsp/listUser.jsp").forward(request,response);*/
}
//修改用户
protected void doUpdate(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
String amid = request.getParameter("amid");
String pwd = request.getParameter("pwd");
UserDaoImpl userDao = new UserDaoImpl();
userDao.update(new User(amid,pwd));
response.getWriter().write("<script>alert('数据已更新!');" +
"window.location.href='Enter.jsp'; </script>");
doList(request,response);
}
//修改用户传值
protected void doUpdateUser(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
String amid = request.getParameter("u_name");
UserDaoImpl userDao = new UserDaoImpl();
User user = userDao.findById(new User(amid));
System.out.println("这组数据是:"+user);
request.setAttribute("user",user);
request.getRequestDispatcher("jsp/UpleUser.jsp").forward(request,response);
}
}
2、传值表达式
servlet获取name属性值的同时还传递一个当前的对象属性值过去
语法:url地址?提交的name名=提交的name值&传递的当前需要获取的属性名=属性值
<a href="../../UserServlet?method=doUpdateUser&u_name=<%=user.getU_name()%>">修改</a>
3、jsp的代码
<h1>欢迎登陆User管理系统</h1>
<form method="POST" action="UserServlet">
<!--method传递的name名,doEnter对应的name值,通过这个值到servlet判断当前执行的操作
hidden通过隐藏域的形式传递 -->
<input type="hidden" name="method" value="doEnter">
用户名:<input type="text" name="amin"><br/>
密码: <input type="text" name="pwd"><br/><br/>
<input type="submit" value="登录">
<input type="reset">
<input type="radio" value="1" name="mm">记住我
<a href="Userlogin.jsp">立即注册</a>
</form>
09)模糊查询
UserDaoImpl
@Override
public List<User> findAll(User user) {
List<User> list=null;
//1.sql语句
String sql="select * from tbl_user where 1=1";
if(user.getName()!=null){//表示用户提交了一个name的查询条件
sql=sql+ " and name like '%"+user.getName()+"%'";
}
if(user.getAge()!=null){
sql=sql+" and age="+user.getAge();
}
try {
list=runner.query(sql,new BeanListHandler<User>(User.class));
} catch (SQLException e) {
e.printStackTrace();
}
return list;
}
查询
protected void doList(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
List<User> list = null;
String amd = request.getParameter("amd");
String pw = request.getParameter("pw");
// List<User> list= null;
UserDao userDao=new UserDaoImpl();
//List<User> list = userDao.findAllwhere(new User(amd, pw));
//根据查询条件创建查询对象
if (amd==null && pw ==null){
list = userDao.findAll();
}else {
list = userDao.findAllwhere(new User(amd,pw));
}
//得到一个会话对象
HttpSession session = request.getSession();
session.setAttribute("list",list);
request.getRequestDispatcher("jsp/listUser2.jsp").forward(request,response);
}
常见问题
1.检查数据库是否开启状态
2.地址问题,注意引用路径
3.jsp表达式出错也可能导致页面不显示
Cookie技术
概念
保存客户端浏览器中一组小文件
Cookie 是存储在客户端计算机上的文本文件,并保留了各种跟踪信息。Java Servlet 显然支持 HTTP Cookie。
识别返回用户包括三个步骤:
服务器脚本向浏览器发送一组 Cookie。例如:姓名、年龄或识别号码等。
浏览器将这些信息存储在本地计算机上,以备将来使用。
当下一次浏览器向 Web 服务器发送任何请求时,浏览器会把这些 Cookie 信息发送到服务器,服务器将使用这些信息来识别用户。
案例:将用户提交的name与pwd保存到 cookie中
response.addCookie(cookie),将cookie的内容写以浏览器中
发请求,request对象会自动带上cookie的值
request.getCookies(); 得到这个一个服务器在这个浏览器上保存所有 cookie
写cookie
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String rem= req.getParameter("rem");
//1.取数据,从request对象中取
String name=req.getParameter("name");
String pwd=req.getParameter("pwd");
System.out.println(name+","+pwd);
Cookie cookieName = new Cookie("name", name);
Cookie cookiePwd = new Cookie("pwd", pwd);
if("1".equals(rem)) {
//构造一个cookie对象,这个对象的保存的key是name 值是admin
cookieName.setMaxAge(60 * 60 * 24);
cookiePwd.setMaxAge(60 * 60 * 24);
//将cooke写到客户端
}else{
cookieName.setMaxAge(0);
cookiePwd.setMaxAge(0);
}
resp.addCookie(cookieName);
resp.addCookie(cookiePwd);
resp.sendRedirect("index.jsp");
}
读取cookie
<%
//取cookie
Cookie[] cookies=request.getCookies();
for(Cookie cookie:cookies){
out.print(cookie.getName()+":"+cookie.getValue());
}
%>
<%
String name="";
String pwd="";
Cookie[] cookies=request.getCookies();
for(Cookie cookie:cookies){
if("name".equals(cookie.getName()))
name=cookie.getValue();
if("pwd".equals(cookie.getName()))
pwd=cookie.getValue();
}
%>
<form action="UserServlet" method="get">
<input type="hidden" name="method" value="login"/>
用户名:<input type="text" name="name" value="<%=name %>"/><br/>
密码:<input type="password" name="pwd" value="<%=pwd %>"/><br/>
<input type="checkbox" name="rem" value="1"/>记住我<br/>
<input type="submit" value="提交"/>
</form>
MVC模式
概念
mvc模式 是一种 模型
一种编程经验,解决一类问题的方法的总结;
(类似的23种设计模式)
mvc是为web程序结构定义一种模式 springmvc struts1.x struts2.x 都实现了mvc模式
M:Model 模型 dao层数据访问对象 UserDaoImpl
V: View 视图 提供用户操作的界面,提供数据输入与输出 view提供输入,输入的数据提交给Controller来处理
视图要为用户展示数据,也由Controller来提供
C:Controller 控制器 接受用户浏览器的请求,为请求产生响应 Servlet mode2 mode1
EL表达式&jstl
EL表达式
EL表达式是jsp2.0中的一个标准,它的主作用取作用域对象中的值 在jsp页面上输入或计算后再输出 4个
request sessjon applicaiton
01)语法
如果jsp页面中直接使用${属性名}方式 如${name}
相于先在pageContext这个作用域对象中找它的name属性值,找到就输出,没有找开,找request session application
02)获取文件的绝对路径
获取文件的根路径
${pageContext.request.contextPath}
示例:
<img src="${pageContext.request.contextPath}/images/c2.jpg">
EL中有4跟作用域有关内置对象
pageScope requestScope sessionScope applicationScope
sessionName:${sessionScope.name} 指定输入指作用域对象中的属性值
调用 user对象的get方法
${user.name}${user.pwd}${user.addr} 调用 user对象的get方法
$(user.name) user.getName(); getAddr();同上,两个方法的效果一样
getName1 将get去 首字母小写name1
pageContext对象
${pageContext.request.contextPath} 通过El表达得到当前应用的根目录
作运算
Age=${user.age+10}
${a>b?1:2}
JSTL java标准标签库
在jsp页面通过标签形式来完成java代码的功能
jsp=html+java代码 html+jstl形式 EL集成使用
导入jstl1.2.jar
c.tld文件中c标签的描述文件,c是jstl的核心标签库
01)引用jstl
在html标签上面引入
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
02)声明变量
定义一个变量,变量名是name 值为 admin 放到request作有域对象中
jstl写法
<c:set var="name" value="admin" scope="request"/>
jsp写法
<%
request.setAttribute("name",admin)
%>
EL写法
Name=${reqeuestScope.name}
03)if判断
if的test是一个条件判断,test=“"写EL表达式 将判断的结果给到stat
<c:if test="${user==null}" var="stat"scope="request">
user不存在!
</c:if>
<!--相当于else,直接取反-->
<c:if test="${!stat}" >
user存在!
</c:if>
04)for循环
将list循环遍历 每一个值都赋值给obj
<c:forEach items="${list}" var="obj">
</c:forEach>
for(User user:list){}
CURD操作(含分页查询)
utils层
PageBean==分页查询属性
**
* 封装分页的数据
* */
public class PageBean {
private int pageSize = 5;//定义每一页显示的行数
private int totalPage;//总的页面数
private int currPage;//当前页面号
private int totalRows;//总行数
private List<?>list;//用于封装当前页面的数据
public int getPageSize() {
return pageSize;
}
public void setPageSize(int pageSize) {
this.pageSize = pageSize;
}
public int getTotalPage() {
return totalPage;
}
public void setTotalPage(int totalPage) {
this.totalPage = totalPage;
}
public int getCurrPage() {
return currPage;
}
//对要显示的当前页面做判断
public void setCurrPage(int currPage) {
if (currPage<1){
this.currPage=1;
}else if (currPage>this.totalPage){
this.currPage=this.totalPage;
}else {
this.currPage = currPage;
}
}
public int getTotalRows() {
return totalRows;
}
//设置总行数,根据总行数计算出总页面数
public void setTotalRows(int totalRows) {
this.totalRows = totalRows;
if (totalRows % this.pageSize == 0){
this.totalPage = totalRows/pageSize;
}else {
this.totalPage = totalRows/pageSize+1;
}
}
public List<?> getList() {
return list;
}
public void setList(List<?> list) {
this.list = list;
}
@Override
public String toString() {
return "PageBean{" +
"pageSize=" + pageSize +
", totalPage=" + totalPage +
", currPage=" + currPage +
", totalRows=" + totalRows +
", list=" + list +
'}';
}
}
GoodLike==封装的查询条件类
/**
* 封装的条件查询
*/
public class GoodLike {
private Integer typeId;//商品品种
private Integer priceBetween ;//商品价格最小范围
private Integer priceAnd ;//商品价格最大范围
public GoodLike() {
}
public GoodLike(Integer priceBetween, Integer priceAnd) {
this.priceBetween = priceBetween;
this.priceAnd = priceAnd;
}
public GoodLike(Integer typeId, Integer priceBetween, Integer priceAnd) {
this.typeId = typeId;
this.priceBetween = priceBetween;
this.priceAnd = priceAnd;
}
public Integer getTypeId() {
return typeId;
}
public void setTypeId(Integer typeId) {
this.typeId = typeId;
}
public Integer getPriceBetween() {
return priceBetween;
}
public void setPriceBetween(Integer priceBetween) {
this.priceBetween = priceBetween;
}
public Integer getPriceAnd() {
return priceAnd;
}
public void setPriceAnd(Integer priceAnd) {
this.priceAnd = priceAnd;
}
@Override
public String toString() {
return "GoodLike{" +
"typeId=" + typeId +
", priceBetween=" + priceBetween +
", priceAnd=" + priceAnd +
'}';
}
}
Empty==判断是否为空
import java.util.Collection;
import java.util.Map;
/**
* <p>判断是否是空的 工具类</p>
* @author zzshang
* @version v1.0
* @since 2015/5/5
*/
public class EmptyUtils {
//判空
public static boolean isEmpty(Object obj){
if (obj == null)
return true;
if (obj instanceof CharSequence)
return ((CharSequence) obj).length() == 0;
if (obj instanceof Collection)
return ((Collection) obj).isEmpty();
if (obj instanceof Map)
return ((Map) obj).isEmpty();
if (obj instanceof Object[]) {
Object[] object = (Object[]) obj;
if (object.length == 0) {
return true;
}
boolean empty = true;
for (int i = 0; i < object.length; i++) {
if (!isEmpty(object[i])) {
empty = false;
break;
}
}
return empty;
}
return false;
}
public static boolean isNotEmpty(Object obj){
return !isEmpty(obj);
}
private boolean validPropertyEmpty(Object ...args) {
for (int i = 0; i < args.length; i++) {
if(EmptyUtils.isEmpty(args[i])){
return true;
}
}
return false;
}
}
StringUtils==生成随机数
用于文件上传!
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.Map;
import java.util.Random;
import java.util.UUID;
import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.NoSuchPaddingException;
import javax.crypto.SecretKey;
import javax.crypto.spec.SecretKeySpec;
public class StringUtils {
private static String[] binaryArray =
{"0000","0001","0010","0011",
"0100","0101","0110","0111",
"1000","1001","1010","1011",
"1100","1101","1110","1111"};
// private static String[] chineseDigits = new String[] { "零", "壹", "贰", "叁", "肆", "伍", "陆", "柒", "捌", "玖"};
public static String[] chineseDigits = new String[] { "零", "一", "二", "三", "四", "五", "六", "七", "八", "九"};
private static final char[] charBytes = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9','a', 'b', 'c', 'd', 'e', 'f', 'g', 'h',
'i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z'};
private static final char[] numberBytes = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9'};
/**
* 生成指定位数的随机数子.
* @param number
* @return
*/
public static String randomNumbers(int number) {
int count = 0; //生成的密码的长度
int i; //生成的随机数
final int maxNum = numberBytes.length;
StringBuffer randomStr = new StringBuffer("");
Random r = new Random();
while(count < number){
//生成随机数,取绝对值,防止生成负数,
i = Math.abs(r.nextInt(maxNum)); //生成的数最大为36-1
if (i >= 0 && i < numberBytes.length) {
randomStr.append(numberBytes[i]);
count ++;
}
}
return randomStr.toString();
}
public static String randomStrByNumber(int number) {
int count = 0; //生成的密码的长度
int i; //生成的随机数
final int maxNum = charBytes.length;
StringBuffer randomStr = new StringBuffer("");
Random r = new Random();
while(count < number){
//生成随机数,取绝对值,防止生成负数,
i = Math.abs(r.nextInt(maxNum)); //生成的数最大为36-1
if (i >= 0 && i < charBytes.length) {
randomStr.append(charBytes[i]);
count ++;
}
}
return randomStr.toString();
}
public static String randomUUID() {
UUID uuid = UUID.randomUUID();
return uuid.toString().replace("-", "").toUpperCase();
}
public static String digitsTochinese(int i){
//大于10的需要重写
return chineseDigits[i];
}
public static String toAllUpperCase(String uuid) {
StringBuffer buffer = new StringBuffer();
for (int i = 0; i < uuid.length(); i++) {
char c = uuid.charAt(i);
if (Character.isLowerCase(c)) {
buffer.append(Character.toUpperCase(c));
} else {
buffer.append(c);
}
}
return buffer.toString();
}
// 十六进制字符串转byte数组
public static byte[] hexStringToBytes(String hexString) {
if (hexString == null || hexString.equals("")) {
return null;
}
hexString = hexString.toUpperCase();
int length = hexString.length() / 2;
char[] hexChars = hexString.toCharArray();
byte[] d = new byte[length];
for (int i = 0; i < length; i++) {
int pos = i * 2;
d[i] = (byte) (charToByte(hexChars[pos]) << 4 | charToByte(hexChars[pos + 1]));
}
return d;
}
private static byte charToByte(char c) {
return (byte) "0123456789ABCDEF".indexOf(c);
}
// 数组转字符串、以空格间隔
public static String bytesToHexString(byte[] src) {
StringBuilder stringBuilder = new StringBuilder("");
if (src == null || src.length <= 0) {
return null;
}
for (int i = 0; i < src.length; i++) {
int v = src[i] & 0xFF;
String hv = Integer.toHexString(v);
if (hv.length() < 2) {
stringBuilder.append(0);
}
if (i == src.length - 1) {
stringBuilder.append(hv);
} else {
stringBuilder.append(hv);
}
}
return stringBuilder.toString();
}
public static String bytesToHexStringNoAppendBit(byte[] src) {
StringBuilder stringBuilder = new StringBuilder("");
if (src == null || src.length <= 0) {
return null;
}
for (int i = 0; i < src.length; i++) {
int v = src[i] & 0xFF;
String hv = Integer.toHexString(v);
/*if (hv.length() < 2) {
stringBuilder.append(0);
}*/
if (i == src.length - 1) {
stringBuilder.append(hv);
} else {
stringBuilder.append(hv);
}
}
return stringBuilder.toString();
}
public static String bytesToString(byte[] src, String split) {
StringBuilder stringBuilder = new StringBuilder("");
if (src == null || src.length <= 0) {
return null;
}
for (int i = 0; i < src.length; i++) {
int v = src[i] & 0xFF;
String hv = String.valueOf(v);
if (i == src.length - 1) {
stringBuilder.append(hv);
} else {
stringBuilder.append(hv + split);
}
}
return stringBuilder.toString();
}
public static String generateHexString(int paramInt) {
StringBuffer localStringBuffer = new StringBuffer();
Random localRandom = new Random();
int i = 16;
for (int j = 0; j < paramInt; j++) {
if (j % 2 == 0) {
localStringBuffer.append("0123456789ABCDEF".charAt(localRandom
.nextInt(i)));
} else {
localStringBuffer.append("0123456789ABCDEF".charAt(localRandom
.nextInt(i)) + " ");
}
}
return localStringBuffer.toString();
}
public static byte[] decodeTripleDES(byte[] data, byte[] key)
throws NoSuchAlgorithmException, NoSuchPaddingException,
InvalidKeyException, IllegalBlockSizeException, BadPaddingException {
byte[] keys;
if (key.length == 16) {
keys = new byte[24];
System.arraycopy(key, 0, keys, 0, 16);
System.arraycopy(key, 0, keys, 16, 8);
} else {
keys = key;
}
Cipher cipher = Cipher.getInstance("DESede/ECB/NoPadding");
SecretKey secretKey = new SecretKeySpec(keys, "DESede");
cipher.init(Cipher.DECRYPT_MODE, secretKey);
return cipher.doFinal(data);
}
public static boolean equals(byte[] b1, byte[] b2) {
if (b1.length != b2.length) {
return false;
}
for (int i = 0; i < b1.length; i++) {
if (b1[i] != b2[i]) {
return false;
}
}
return true;
}
/**
*
* @return 转换为二进制字符串
*/
public static String bytes2BinaryStr(byte[] bArray){
String outStr = "";
int pos = 0;
for(byte b:bArray){
//高四位
pos = (b&0xF0)>>4;
outStr+=binaryArray[pos];
//低四位
pos=b&0x0F;
outStr+=binaryArray[pos];
}
return outStr;
}
/**将二进制转换成16进制
* @param buf
* @return
*/
public static String binaryToHexString(byte[] bytes) {
StringBuffer sb = new StringBuffer();
for (int i = 0; i < bytes.length; i++) {
String hex = Integer.toHexString(bytes[i] & 0xFF);
if (hex.length() == 1) {
hex = '0' + hex;
}
sb.append(hex.toUpperCase());
}
return sb.toString();
}
/**将16进制转换为二进制
* @param hexStr
* @return
*/
public static byte[] hexStringToBinary(String hexStr) {
if (hexStr.length() < 1)
return null;
byte[] result = new byte[hexStr.length()/2];
for (int i = 0;i< hexStr.length()/2; i++) {
int high = Integer.parseInt(hexStr.substring(i*2, i*2+1), 16);
int low = Integer.parseInt(hexStr.substring(i*2+1, i*2+2), 16);
result[i] = (byte) (high * 16 + low);
}
return result;
}
//十六进制转为字符
public static String hexStringToString(String s) {
byte[] baKeyword = new byte[s.length() / 2];
for (int i = 0; i < baKeyword.length; i++) {
try {
baKeyword[i] = (byte) (0xff & Integer.parseInt(
s.substring(i * 2, i * 2 + 2), 16));
} catch (Exception e) {
e.printStackTrace();
}
}
try {
s = new String(baKeyword, "utf-8");// UTF-16le:Not
} catch (Exception e1) {
e1.printStackTrace();
}
return s;
}
/**
* 给某个日期加几天后的日期 eg:2013-06-28号+1天是 2013-06-29 ,+3天是2013-07-01
* @param date 日期
* @param dump 数字
* @return
*/
public static String getDateByAddSomeDay(Date date,int dump){
Calendar ca=Calendar.getInstance();
SimpleDateFormat sm = new SimpleDateFormat("yyyy-MM-dd"); //构造任意格式
String today = sm.format(date);
String[] timeArray= today.split("-");
ca.set(Calendar.YEAR,Integer.parseInt(timeArray[0]));
ca.set(Calendar.MONTH, Integer.parseInt(timeArray[1])-1);
ca.set(Calendar.DAY_OF_MONTH,Integer.parseInt(timeArray[2]));
ca.add(Calendar.DAY_OF_MONTH, dump);
String someDay = sm.format(ca.getTime());
return someDay;
}
/**
* 生成公钥
* @param pubkey
* @return
* add by yaoyuan
*/
public static String generatePublicKey(String pubkey) {
// BASE64Encoder base64en = new BASE64Encoder();
// String encode = base64en.encode(hexStringToBinary(pubkey));
// encode = "-----BEGIN RSA PUBLIC KEY-----" + encode + "-----END RSA PUBLIC KEY-----";
// if (encode.getBytes().length < 256) {
// encode = org.apache.commons.lang.StringUtils.rightPad(encode, 256, "0");
// }
// return encode;
return null;
}
/**
* 获取当前时间 精确到毫秒
*/
public static String getCurrentTime(){
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSS");
String currentTime = sdf.format(new Date());
return currentTime;
}
/**
* @功能: BCD码转为10进制串(阿拉伯数据)
* @参数: BCD码
* @结果: 10进制串
*/
public static String bcd2Str(byte[] bytes) {
StringBuffer temp = new StringBuffer(bytes.length * 2);
for (int i = 0; i < bytes.length; i++) {
temp.append((byte) ((bytes[i] & 0xf0) >>> 4));
temp.append((byte) (bytes[i] & 0x0f));
}
return temp.toString().substring(0, 1).equalsIgnoreCase("0") ? temp
.toString().substring(1) : temp.toString();
}
/**
* @功能: 10进制串转为BCD码
* @参数: 10进制串
* @结果: BCD码
*/
public static byte[] str2Bcd(String asc) {
int len = asc.length();
int mod = len % 2;
if (mod != 0) {
asc = "0" + asc;
len = asc.length();
}
byte abt[] = new byte[len];
if (len >= 2) {
len = len / 2;
}
byte bbt[] = new byte[len];
abt = asc.getBytes();
int j, k;
for (int p = 0; p < asc.length() / 2; p++) {
if ((abt[2 * p] >= '0') && (abt[2 * p] <= '9')) {
j = abt[2 * p] - '0';
} else if ((abt[2 * p] >= 'a') && (abt[2 * p] <= 'z')) {
j = abt[2 * p] - 'a' + 0x0a;
} else {
j = abt[2 * p] - 'A' + 0x0a;
}
if ((abt[2 * p + 1] >= '0') && (abt[2 * p + 1] <= '9')) {
k = abt[2 * p + 1] - '0';
} else if ((abt[2 * p + 1] >= 'a') && (abt[2 * p + 1] <= 'z')) {
k = abt[2 * p + 1] - 'a' + 0x0a;
} else {
k = abt[2 * p + 1] - 'A' + 0x0a;
}
int a = (j << 4) + k;
byte b = (byte) a;
bbt[p] = b;
}
return bbt;
}
/**
* 去除字符串中的符合${}形式的子串.
* @param
* @return 去除${}的字符串
*/
public static String escape$String(String input) {
return input.replaceAll("\\$\\{[^}]*\\}", "");
}
public static String replace$String(String input, String newStr) {
return input.replaceAll("\\$\\{[^}]*\\}", newStr);
}
public static String replace$SpecifyString(String input, String str,
String newStr) {
if(input != null){
input = input.replaceAll("\\$\\{" + str + "\\}", newStr);
}
return input;
}
public static String replace$String(Map<String, Object> map, String src) {
if (src != null && map != null) {
for (String key : map.keySet()) {
String value = String.valueOf(map.get(key));
src = replace$SpecifyString(src, key, value);
}
}
return src;
}
/**
* 生成验证码
* @return
*/
public static String createValidateCode(){
String str = "0,1,2,3,4,5,6,7,E,F,G,H,I,J,K,L,M,N,O,P,Q,R,S,T,U,V,W,X,Y,Z,8,9,a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z,A,B,C,D";
String str2[] = str.split(",");//将字符串以,分割
String code="";
for(int i=0;i<4;i++){
int a=(int)(Math.random()*36);
code=code+str2[a];
}
return code;
}
/**
* 根据身份证计算年龄
* @param idNumber
* @return
*/
public static int calculateAgeByIdNumber(String idNumber){
int leh = idNumber.length();
int years =0;
if (leh == 18) {
years=Integer.parseInt(idNumber.substring(6, 10));
}else {
years = Integer.parseInt("19" + idNumber.substring(6, 8));
}
Calendar a=Calendar.getInstance();
return a.get(Calendar.YEAR)-years;
}
/**
* 根据身份证计算性别
* @param idNumber
* @return
*/
public static int calculateSexByIdNumber(String idNumber){
int leh = idNumber.length();
int se =0;
if (leh == 18) {
se=Integer.valueOf(idNumber.substring(16,17)) % 2;
}
return (se==1?1:2);
}
/**
* 查找数字在数组中得区间.
* @param sortedData 排序数组
* @param findValue
* @return
*/
public static int searchValueSectionInArr(Integer[] sortedData,int findValue) {
int start = 0;
int end = 0;
for (int i = 0; i < sortedData.length; i++) {
if (findValue >= sortedData[i]) {
start = i;
} else {
end = i;
break;
}
}
return start;
}
/**
* 循环二分查找数组区间,返回第一次出现该值的位置
* @param sortedData 已排序的数组
* @param findValue 需要找的值
* @return 值在数组中的位置,从0开始。找不到返回-1
*/
public static int binarySearch(Integer[] sortedData,int findValue) {
int start=0;
int end=sortedData.length-1;
while(start<=end) {
//中间位置
int middle=(start+end)>>1; //相当于(start+end)/2
// System.out.println("middle==>>" + middle);
//中值
int middleValue=sortedData[middle];
if(findValue < middleValue) {
//小于中值时在中值前面找
end = middle-1;
//如果小于前边的值 和前 前边的值 则继续下一次查找
if (end >= 0) {
int end_v =sortedData[end];
if (findValue >= end_v) {
return end;
}
} else {
return middle;
}
}
else {
//大于中值在中值后面找
start=middle+1;
if (start <= sortedData.length -1) {
int end_v = sortedData[start];
if (findValue < end_v) {
return middle;
}
} else {
return middle;
}
}
}
//找不到
return -1;
}
public static void main(String[] args) {
/*Integer age=calculateAgeByIdNumber("133022198201242396");
Integer sex=calculateSexByIdNumber("133022198201242396");
System.out.println("age"+age+">>>>>>sex>>>>>>>>>"+sex);*/
String oldFileName="c101.jpg";
//取上传文件的扩展名
String suff=oldFileName.substring(oldFileName.lastIndexOf("."));
System.out.println(StringUtils.randomUUID()+suff);
}
}
DataSourcePooled==连接池
import com.mchange.v2.c3p0.ComboPooledDataSource;
import javax.sql.DataSource;
public class DataSourcePooled {
private static DataSource dataSource;
public DataSourcePooled() {
}
static {
//utils提供的连接线程池方法
dataSource = new ComboPooledDataSource();
}
public static DataSource getDataSource(){
return dataSource;
}
public static void main(String[] args) {
System.out.println(dataSource);
}
}
Dao层===模型
Dao的父类接口
package com.kgc.dao;
import java.io.Serializable;
import java.util.List;
/**
* 定义一个Dao类型对象的规范 ,要求所有Dao对象要实现这个接口中的方法
* @param <T> T是一个参数化的数据类型
*/
public interface Dao<T> {
//增加
void insert(T t);
//修改
void update(T t);
//删除
void delete(Serializable id);
//查询
List<T> findAll();
//通过id查询
T findById(Serializable id);
}
Dao的子类接口
package com.kgc.dao;
import com.kgc.entity.Goods;
import com.kgc.utils.GoodLike;
import java.util.List;
public interface GoodsDao extends Dao<Goods> {
/*不带查询条件的分页*/
List<Goods>LikeGoodsAll(int currentPage, int pageSize);
/*带查询条件的分页*/
List<Goods>LikeGoodsAll(GoodLike goodLike, int currentPage, int pageSize);
/*不带条件的记录数*/
Long getRows();
/*根据条件查询记录数*/
int getRows(GoodLike goodLike);
package com.kgc.dao;
import com.kgc.entity.Goods;
import com.kgc.entity.GoodsType;
import java.util.List;
public interface GoodsTypeDao extends Dao<GoodsType> {
/*把页面的类型换成名称*/
List<Goods> GoodTypeAll();
}
Dao的实现类impl
package com.kgc.dao.impl;
import com.kgc.dao.GoodsDao;
import com.kgc.entity.Goods;
import com.kgc.utils.DataSourcePooled;
import com.kgc.utils.EmptyUtils;
import com.kgc.utils.GoodLike;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.apache.commons.dbutils.handlers.ScalarHandler;
import java.io.Serializable;
import java.sql.SQLException;
import java.util.List;
public class GoodsDaoImpl implements GoodsDao {
QueryRunner runner = new QueryRunner(DataSourcePooled.getDataSource());
@Override
public void insert(Goods goods) {
String sql = "insert into goods values(null,?,?,?,?)";
Object[]obj = new Object[]{goods.getName(),goods.getTypeId(),goods.getPrice(),goods.getCreateTime()};
try {
runner.update(sql,obj);
} catch (SQLException e) {
e.printStackTrace();
}
}
@Override
public void update(Goods goods) {
String sql = "update goods set name=?,typeId=?,price=?,createTime=? where id=?";
Object[]obj = new Object[]{goods.getName(),goods.getTypeId(),goods.getPrice(),goods.getCreateTime(),goods.getId()};
try {
runner.update(sql,obj);
} catch (SQLException e) {
e.printStackTrace();
}
}
@Override
public void delete(Serializable id) {
String sql = "delete from goods where id=?";
try {
runner.update(sql,id);
} catch (SQLException e) {
e.printStackTrace();
}
}
@Override
public List<Goods> findAll() {
String sql = "select * from goods";
try {
return runner.query(sql,new BeanListHandler<Goods>(Goods.class));
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public Goods findById(Serializable id) {
String sql = "select id,name,typeId,price,createTime from goods where id=?";
try {
return runner.query(sql,new BeanHandler<Goods>(Goods.class),id);
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public List<Goods> LikeGoodsAll(int currentPage, int pageSize) {
String sql = "select goods.*,goodstype.`name` as typename from goods,goodstype where goods.`typeId`=goodstype.`id` limit ?,?";
try {
return runner.query(sql,new BeanListHandler<Goods>(Goods.class),(currentPage-1)*pageSize,pageSize);
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public List<Goods> LikeGoodsAll(GoodLike goodLike, int currentPage, int pageSize) {
System.out.println("传入的sql值是"+goodLike);
String sql = "select goods.*,goodstype.`name` as typename from goods,goodstype where goods.`typeId`=goodstype.`id`";
if (EmptyUtils.isNotEmpty(goodLike.getTypeId()) && goodLike.getTypeId() != -1){
sql = sql+" and typeId="+goodLike.getTypeId();
}
if (EmptyUtils.isNotEmpty(goodLike.getPriceAnd()) &&
EmptyUtils.isNotEmpty(goodLike.getPriceBetween())){
sql = sql+" and price between "+goodLike.getPriceBetween()+" and "+goodLike.getPriceAnd();
}
sql = sql+" limit ?,?";
System.out.println("执行分页查询的sql语句"+sql);
try {
return runner.query(sql,new BeanListHandler<Goods>(Goods.class),(currentPage-1)*pageSize,pageSize);
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public Long getRows() {
String sql = "select count(*) from goods";
try {
return runner.query(sql,new ScalarHandler<Long>());
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public int getRows(GoodLike goodLike) {
String sql = "select count(*) from goods where 1=1 ";
Long num = 0L;
if (EmptyUtils.isNotEmpty(goodLike.getTypeId()) && goodLike.getTypeId() != -1) {
sql = sql+" and typeId = "+goodLike.getTypeId();
}else if (EmptyUtils.isNotEmpty(goodLike.getPriceAnd()) && EmptyUtils.isNotEmpty(goodLike.getPriceBetween())){
sql = sql+"and price between "+goodLike.getPriceBetween()+" and "+goodLike.getPriceAnd();
}
try {
num = runner.query(sql,new ScalarHandler<Long>());
} catch (SQLException e) {
e.printStackTrace();
}
//Long类型转换为int类型返回
return num.intValue();
}
}
package com.kgc.dao.impl;
import com.kgc.dao.GoodsTypeDao;
import com.kgc.entity.Goods;
import com.kgc.entity.GoodsType;
import com.kgc.utils.DataSourcePooled;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import java.io.Serializable;
import java.sql.SQLException;
import java.util.List;
public class GoodsTypeDaoImpl implements GoodsTypeDao {
QueryRunner runner = new QueryRunner(DataSourcePooled.getDataSource());
@Override
public void insert(GoodsType goodsType) {
String sql = "insert into goodstype values(null,?)";
Object[]obj = new Object[]{goodsType.getName()};
try {
runner.update(sql,obj);
} catch (SQLException e) {
e.printStackTrace();
}
}
@Override
public void update(GoodsType goodsType) {
String sql = "update goodstype set name=? where id=?";
Object[]obj = new Object[]{goodsType.getName(),goodsType.getId()};
try {
runner.update(sql,obj);
} catch (SQLException e) {
e.printStackTrace();
}
}
@Override
public void delete(Serializable id) {
String sql = "delete from goodstype where id=?";
try {
runner.update(sql,id);
} catch (SQLException e) {
e.printStackTrace();
}
}
@Override
public List<GoodsType> findAll() {
String sql = "select * from goodstype";
try {
return runner.query(sql,new BeanListHandler<GoodsType>(GoodsType.class));
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
@Override
public GoodsType findById(Serializable id) {
String sql = "select * from goodstype where id=?";
try {
return runner.query(sql,new BeanHandler<GoodsType>(GoodsType.class),id);
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
/*两个表的查询*/
@Override
public List<Goods> GoodTypeAll() {
String sql = "select * from goods,goodstype where goods.`typeId`=goodstype.`id`";
try {
return runner.query(sql,new BeanListHandler<Goods>(Goods.class));
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
}
分页查询的运算逻辑
//分页查询 实现类代码
@Override
public List<Book_info> findPageAll(int curentPage, int pageSize) {
String sql = "select book_code,book_name,book_type," +
" book_author,pubish_press ,publish_date,is_borrow from book_info limit ?,?";
try {
return runner.query(sql,new BeanListHandler<Book_info>(Book_info.class),(curentPage-1)*pageSize,pageSize);
} catch (SQLException e) {
e.printStackTrace();
}
return null;
}
//工具类封装代码
/**
* 封装分页的数据
* */
public class PageBean {
private int pageSize=3;//定义每一页面显示的行数
private int totalPage;//总的页面数
private int currPage;//当前页面号
private int totalRows;//总行数
private List<?> list;//用于封装当前页面的数据
public int getPageSize() {
return pageSize;
}
public void setPageSize(int pageSize) {
this.pageSize = pageSize;
}
public int getTotalPage() {
return totalPage;
}
public void setTotalPage(int totalPage) {
this.totalPage = totalPage;
}
public int getCurrPage() {
return currPage;
}
//对要显示的当前页面作判断
public void setCurrPage(int currPage) {
if(currPage<1)
this.currPage=1;
else if(currPage>this.totalPage)
this.currPage=this.totalPage;
else
this.currPage = currPage;
}
public int getTotalRows() {
return totalRows;
}
//设置总行数,根据总行数计算出总页面数
public void setTotalRows(int totalRows) {
this.totalRows = totalRows;
if(totalRows % this.pageSize==0)
this.totalPage=totalRows/pageSize;
else
this.totalPage=totalRows/pageSize+1;
}
public List<?> getList() {
return list;
}
public void setList(List<?> list) {
this.list = list;
}
}
Service层
定义一个接口一个实现类==方法跟Controller类似,通过这一层直接访问Dao层,
Service层主要负责逻辑运算,让Controller层更简化,只负责取、调、转让代码更便于维护
01接口
public interface GoodsServic {
//增加
void insert(Goods goods);
//修改
void update(Goods goods);
//删除
void delete(Serializable id);
//查询
List<Goods> findAll();
//通过id查询
Goods findById(Serializable id);
//查询所有的类型
List<GoodsType>findAllType();
/*带查询条件的分页 通过serviet把获取的值传递过来在进行转换,简化serviet,把判断复杂的操作在此层执行*/
PageBean LikeGoodsAll(String page,String type, String price1, String price2);
}
02)实现类
public class GoodServic implements GoodsServic{
private GoodsDaoImpl goodsDao = new GoodsDaoImpl();
private GoodsTypeDaoImpl goodsTypeDao = new GoodsTypeDaoImpl();
@Override
public void insert(Goods goods) {
goodsDao.insert(goods);
}
@Override
public void update(Goods goods) {
goodsDao.update(goods);
}
@Override
public void delete(Serializable id) {
goodsDao.delete(id);
}
@Override
public List<Goods> findAll() {
List<Goods> all = goodsDao.findAll();
return all;
}
@Override
public Goods findById(Serializable id) {
Goods byId = goodsDao.findById(id);
return byId;
}
@Override
public List<GoodsType> findAllType() {
List<GoodsType> all = goodsTypeDao.findAll();
return all;
}
/*返回满足条件的分页查询集合*/
@Override
public PageBean LikeGoodsAll(String page,String type, String price1, String price2) {
//判断page是否为空===此方法EmptyUtils提供
if (EmptyUtils.isEmpty(page)){
page="1";
}
//当前默认页面号
int currentPage = Integer.parseInt(page);
PageBean pageBean = new PageBean();//封装分页的实体类
GoodLike goodLike = new GoodLike();//封装查询条件的实体类
//判断查询的id类型是否为空,如果不为空,则强转后放入对象实体
if (EmptyUtils.isNotEmpty(type)){
goodLike.setTypeId(Integer.parseInt(type));
}
if (EmptyUtils.isNotEmpty(price1) && EmptyUtils.isNotEmpty(price2)){
goodLike.setPriceBetween(Integer.parseInt(price1));
goodLike.setPriceAnd(Integer.parseInt(price2));
}
System.out.println("查询条件对象的值为"+goodLike);
//求总行数 pageBean 在service层放入 总行数 跟 当前页面号 求出其他的值
int rows= goodsDao.getRows(goodLike);
pageBean.setTotalRows(rows);
pageBean.setCurrPage(currentPage);
//把包含条件的数据查出来放入pageBean的集合当中,用于页面调用
List<Goods> list = goodsDao.LikeGoodsAll(goodLike, pageBean.getCurrPage(), pageBean.getPageSize());
pageBean.setList(list);
System.out.println(list);
return pageBean;
}
}
Controller层===控制器(Servlet)
doPost&doGet
@WebServlet(urlPatterns = "/GoodServlet")
public class GoodServlet extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
/*处理中乱码*/
//request.setCharacterEncoding("utf-8");
//response.setContentType("text/html;charset=utf-8");
/*获取的到的method值判断执行的命令*/
String method = request.getParameter("method");
System.out.println("method="+method);
if ("doList".equals(method))
this.doList(request,response);
else if ("doInsert".equals(method))
this.doList(request,response);//
else if ("doDelete".equals(method))
this.doDelete(request,response);
else if ("doUp".equals(method))
this.doUp(request,response);
else if ("doUpdate".equals(method))
this.doList(request,response);
else if ("doUpload".equals(method))
this.doUpload(request,response);
else if ("doUt".equals(method))
this.doUt(request,response);
else
this.doList(request,response);
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doPost(request,response);
}
分页查询
/*浏览查询*/
protected void doList(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//取数据
String page = request.getParameter("page");//当前浏览的页面号
String type = request.getParameter("type");//商品类型
String price1 = request.getParameter("price1");//价格区间
String price2 = request.getParameter("price2");//价格区间
//调
GoodServic goodServic = new GoodServic();
PageBean pageBean = goodServic.LikeGoodsAll(page, type, price1, price2);
//存
request.setAttribute("pb",pageBean);
/*回显的数据*/
request.setAttribute("types",type);
request.setAttribute("price1",price1);
request.setAttribute("price2",price2);
/*类型同时加载*/
List<GoodsType> allType = goodServic.findAllType();
HttpSession session = request.getSession();
session.setAttribute("allType",allType);
/*转发*/
request.getRequestDispatcher("pages/main.jsp").forward(request,response);
}
删除&加载回显
/*删除*/
protected void doDelete(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
/*取数据*/
String id = request.getParameter("goodid");
/*方法定义的Serializable类型,此类型包含String int 等8个常用数据类型,所以不需要强转*/
/*调用删除的方法*/
GoodServic goodServic = new GoodServic();
goodServic.delete(id);
/*内部直接调用查看的方法更新数据*/
doList(request,response);
}
/*辅助修改的方法做回显数据*/
protected void doUp(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String id = request.getParameter("id");
GoodServic goodServic = new GoodServic();
Goods byId = goodServic.findById(id);
request.setAttribute("byId",byId);
request.getRequestDispatcher("pages/UpdateGoods.jsp").forward(request,response);
}
增加==文件上传
/*增加===文件上传版*/
protected void doUpload(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//创建一个FileItemFactory
DiskFileItemFactory factory=new DiskFileItemFactory();
//设置缓冲区
factory.setSizeThreshold(1024*100);
//构造上传的组件
ServletFileUpload upload=new ServletFileUpload(factory);
upload.setHeaderEncoding("utf-8");
String path=getServletContext().getRealPath("upload").toString();
File dir=new File(path);
if(!dir.exists()){
dir.mkdir();
}
String name="";//商品名称
String price="";//商品价格
String typeId="";//商品类型
String createTime="";//商品生产日期
String fileName="";//商品图片
boolean isMultipart = ServletFileUpload.isMultipartContent(request);
if (isMultipart) {
try {
//解析请求,将表单中每个输入项封装成一个FileItem对象 5
List<FileItem> fileItems = upload.parseRequest(request);
// 迭代表单数据
for (FileItem fileItem : fileItems) {
//判断输入的类型是 普通输入项 还是文件
if (fileItem.isFormField()) {
if("name".equals(fileItem.getFieldName())){
name=fileItem.getString("UTF-8");
}
if("price".equals(fileItem.getFieldName())){
price=fileItem.getString("UTF-8");
}
if("typeId".equals(fileItem.getFieldName())){
typeId=fileItem.getString("UTF-8");
}
if("createTime".equals(fileItem.getFieldName())){
createTime=fileItem.getString("UTF-8");
}
} else {
fileName=fileItem.getName();
String ext = fileName.substring(fileName.lastIndexOf("."));
fileName = StringUtils.randomUUID()+ext;
//在指的目录下构造一个空文件
File file = new File(path+"\\"+fileName);
fileItem.write(file);
}
}
} catch (FileUploadException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
}else{
System.out.println("普通表单");
}
//用户增加的数据存储到数据库中
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
Date parse = null;
try {
parse = sdf.parse(createTime);
} catch (ParseException e) {
e.printStackTrace();
}
Goods goods=new Goods(name,Integer.parseInt(typeId),Integer.parseInt(price),parse,fileName);
GoodServic goodServic = new GoodServic();
goodServic.insert(goods);
response.sendRedirect("GoodServlet");
}
修改==文件上传
/*修改===文件上传版*/
protected void doUt(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//创建一个FileItemFactory
DiskFileItemFactory factory=new DiskFileItemFactory();
//设置缓冲区
factory.setSizeThreshold(1024*100);
//构造上传的组件
ServletFileUpload upload=new ServletFileUpload(factory);
upload.setHeaderEncoding("utf-8");
String path=getServletContext().getRealPath("upload").toString();
File dir=new File(path);
if(!dir.exists()){
dir.mkdir();
}
String id ="";
String name="";//商品名称
String price="";//商品价格
String typeId="";//商品类型
String createTime="";//商品生产日期
String fileName="";//商品图片
boolean isMultipart = ServletFileUpload.isMultipartContent(request);
if (isMultipart) {
try {
//解析请求,将表单中每个输入项封装成一个FileItem对象 5
List<FileItem> fileItems = upload.parseRequest(request);
// 迭代表单数据
for (FileItem fileItem : fileItems) {
//判断输入的类型是 普通输入项 还是文件
if (fileItem.isFormField()) {
if("id".equals(fileItem.getFieldName())){
id=fileItem.getString("UTF-8");
}
if("name".equals(fileItem.getFieldName())){
name=fileItem.getString("UTF-8");
}
if("price".equals(fileItem.getFieldName())){
price=fileItem.getString("UTF-8");
}
if("typeId".equals(fileItem.getFieldName())){
typeId=fileItem.getString("UTF-8");
}
if("createTime".equals(fileItem.getFieldName())){
createTime=fileItem.getString("UTF-8");
}
} else {
fileName=fileItem.getName();
String ext = fileName.substring(fileName.lastIndexOf("."));
fileName = StringUtils.randomUUID()+ext;
System.out.println("fileName"+fileName);
//在指的目录下构造一个空文件
File file = new File(path+"\\"+fileName);
fileItem.write(file);
}
}
} catch (FileUploadException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
}else{
System.out.println("普通表单");
}
//用户增加的数据存储到数据库中
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
Date prase = null;
try {
prase = sdf.parse(createTime);
} catch (ParseException e) {
e.printStackTrace();
}
Goods goods=new Goods(Integer.parseInt(id),name,Integer.parseInt(typeId),Integer.parseInt(price),prase,fileName);
System.out.println(goods);
GoodServic goodServic = new GoodServic();
goodServic.update(goods);
response.sendRedirect("GoodServlet");
}
模板==只需要改三处,其余套用即可
增加
代码处标记1/2/3/4
//完成文件上传 完成增加的功能 带上传
protected void doUpload(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//创建一个FileItemFactory
DiskFileItemFactory factory=new DiskFileItemFactory();
//设置缓冲区
factory.setSizeThreshold(1024*100);
//构造上传的组件
ServletFileUpload upload=new ServletFileUpload(factory);
upload.setHeaderEncoding("utf-8");
String path=getServletContext().getRealPath("upload").toString();
File dir=new File(path);
if(!dir.exists()){
dir.mkdir();
}
/*1.第一处*/
String name="";
String price="";
String typeId="";
String createTime="";
String fileName="";
boolean isMultipart = ServletFileUpload.isMultipartContent(request);
if (isMultipart) {
try {
//解析请求,将表单中每个输入项封装成一个FileItem对象 5
List<FileItem> fileItems = upload.parseRequest(request);
// 迭代表单数据
for (FileItem fileItem : fileItems) {
//判断输入的类型是 普通输入项 还是文件
if (fileItem.isFormField()) {
/*2.第二处*/
if("name".equals(fileItem.getFieldName())){
name=fileItem.getString("UTF-8");
}
if("price".equals(fileItem.getFieldName())){
price=fileItem.getString("UTF-8");
}
if("typeId".equals(fileItem.getFieldName())){
typeId=fileItem.getString("UTF-8");
}
if("createTime".equals(fileItem.getFieldName())){
createTime=fileItem.getString("UTF-8");
}
} else {
fileName=fileItem.getName();
String ext = fileName.substring(fileName.lastIndexOf("."));
fileName = StringUtils.randomUUID()+ext;
//在指的目录下构造一个空文件
File file = new File(path+"\\"+fileName);
fileItem.write(file);
}
}
} catch (FileUploadException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
}else{
System.out.println("普通表单");
}
//用户增加的数据存储到数据库中
/*3.第三处*/
Goods goods=new Goods(name,Integer.parseInt(price),createTime,fileName,Integer.parseInt(typeId));
/*4.第四处*/
goodsService.insertGooods(goods);
response.sendRedirect("GoodsServlet");
}
修改
加上id、更改dom层方法即可
//完成修改
protected void doUpdate(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//创建一个FileItemFactory
DiskFileItemFactory factory=new DiskFileItemFactory();
//设置缓冲区
factory.setSizeThreshold(1024*100);
//构造上传的组件
ServletFileUpload upload=new ServletFileUpload(factory);
upload.setHeaderEncoding("utf-8");
String path=getServletContext().getRealPath("upload").toString();
File dir=new File(path);
if(!dir.exists()){
dir.mkdir();
}
String id="";
String name="";
String price="";
String typeId="";
String createTime="";
String fileName="";
boolean isMultipart = ServletFileUpload.isMultipartContent(request);
if (isMultipart) {
try {
//解析请求,将表单中每个输入项封装成一个FileItem对象 5
List<FileItem> fileItems = upload.parseRequest(request);
// 迭代表单数据
for (FileItem fileItem : fileItems) {
//判断输入的类型是 普通输入项 还是文件
if (fileItem.isFormField()) {
if("id".equals(fileItem.getFieldName())){
id=fileItem.getString("UTF-8");
}
if("name".equals(fileItem.getFieldName())){
name=fileItem.getString("UTF-8");
}
if("price".equals(fileItem.getFieldName())){
price=fileItem.getString("UTF-8");
}
if("typeId".equals(fileItem.getFieldName())){
typeId=fileItem.getString("UTF-8");
}
if("createTime".equals(fileItem.getFieldName())){
createTime=fileItem.getString("UTF-8");
}
} else {
fileName=fileItem.getName();
String ext = fileName.substring(fileName.lastIndexOf("."));
fileName = StringUtils.randomUUID()+ext;
//在指的目录下构造一个空文件
File file = new File(path+"\\"+fileName);
fileItem.write(file);
}
}
} catch (FileUploadException e) {
e.printStackTrace();
} catch (Exception e) {
e.printStackTrace();
}
}else{
System.out.println("普通表单");
}
//用户增加的数据存储到数据库中
Goods goods=new Goods(name,Integer.parseInt(price),createTime,fileName,Integer.parseInt(typeId));
goods.setId(Integer.parseInt(id));
goodsService.udpateBook(goods);
response.sendRedirect("GoodsServlet");
}
pages===视图
01)浏览首页
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<html>
<head>
<title>首页</title>
</head>
<body>
<center>
<h2>商品信息列表</h2>
<a href="pages/InsertGoods.jsp">添加商品</a>
<form action="GoodServlet" method="post">
<input hidden name="method" value="doList">
商品类型:
<select name="type">
<option value="-1">全部类型</option>
<c:forEach items="${sessionScope.allType}" var="ty">
<option value="${ty.id}"
<c:if test="${requestScope.types == ty.id}">
selected="selected"
</c:if>
>${ty.name}</option>
</c:forEach>
</select>
价格:
<input type="text" name="price1" value="${requestScope.price1}">
到
<input type="text" name="price2" value="${requestScope.price2}">
<input type="submit" value="查询">
</form>
<table border="1" width="800">
<tr>
<td>商品编号</td>
<td>商品名称</td>
<td>商品类型</td>
<td>价格</td>
<td>生产日期</td>
<td>删除</td>
<td>修改</td>
<td>详情</td>
</tr>
<c:forEach items="${requestScope.pb.list}" var="list">
<tr>
<td>${list.id}</td>
<td>${list.name}</td>
<td>${list.typename}</td>
<td>${list.price}</td>
<td>${list.createTime}</td>
<td><a href="javascript:deleteGood(${list.id})">删除</a></td>
<td><a href="GoodServlet?method=doUp&id=${list.id}">修改</a></td>
<td><a href="#">详情</a></td>
</tr>
</c:forEach>
<tr>
<td colspan="2"><a href="GoodServlet?method=doList&page=1">首页</a></td>
<td><a href="GoodServlet?method=doList&page=${requestScope.pb.currPage-1}">上一页</a></td>
<td><a href="GoodServlet?method=doList&page=${requestScope.pb.currPage+1}">下一页</a></td>
<td><a href="GoodServlet?method=doList&page=${requestScope.pb.totalPage}">尾页</a></td>
<td><a href="#">总行数${requestScope.pb.totalRows}</a></td>
<td><a href="#">总页面数${requestScope.pb.totalPage}</a></td>
<td><a href="#">当前第${requestScope.pb.currPage}页</a></td>
</tr>
</table>
</center>
</body>
<script>
function deleteGood(id) {
if(confirm("是否要删除?")){
window.location.href="GoodServlet?method=doDelete&goodid="+id;
}
}
</script>
</html>
02)修改页面
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<html>
<head>
<title>修改页面</title>
</head>
<body>
<center>
<form action="GoodServlet?method=doUt" method="post" enctype="multipart/form-data">
<input type="hidden" name="id" value="${byId.id}">
<h2>修改商品</h2>
<table border="1" width="300">
<tr>
<td>商品名称</td>
<td><input type="text" name="name" value="${byId.name}"></td>
</tr>
<tr>
<td>商品类型</td>
<%--动态数据--%>
<td>
<select name="type">
<c:forEach items="${sessionScope.allType}" var="ty">
<option value="${ty.id}"
<c:if test="${ty.id==byId.id}">
selected="selected"
</c:if>
>${ty.name}
</option>
</c:forEach>
</select>
</td>
</tr>
<tr>
<td>价格</td>
<td><input type="text" name="price" value="${byId.price}"></td>
</tr>
<tr>
<td>生产时间</td>
<td><input type="text" name="createTime" value="${byId.createTime}"></td>
</tr>
<tr>
<td colspan="2">
<input type="submit" value="添加">
<input type="reset" value="重置">
</td>
</tr>
</table>
</form>
</center>
</body>
</html>
03)添加页码
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>添加商品</title>
</head>
<body>
<form method="post" action="/GoodServlet">
<input type="hidden" name="method" value="doInsert">
<h2>添加商品</h2>
<table border="1" width="300">
<tr>
<td>商品名称</td>
<td><input type="text" name="name"></td>
</tr>
<tr>
<td>商品类型</td>
<%--动态数据--%>
<td>
<select name="type">
<c:forEach items="${sessionScope.allType}" var="ty">
<option value="${ty.id}">${ty.name}</option>
</c:forEach>
</select>
</td>
</tr>
<tr>
<td>价格</td>
<td><input type="text" name="price"></td>
</tr>
<tr>
<td>生产时间</td>
<td><input type="text" name="createTime"></td>
</tr>
<tr>
<td colspan="2">
<input type="submit" value="添加">
<input type="reset" value="重置">
</td>
</tr>
</table>
</form>
</body>
</html>
常见问题
1.sql语句如果确定没错的话就检查一下空格,此类问题容易解决
2.单引号问题,一般不需要加单引号。如果加的话要成对加,sql语句报错的话如果报错行检查没问题,就顺延往上检查
3.选择器一定要用if-else,常量放在前面,不然重定向必须带参数,不然空指针,或者出现重复转发现象
4.文件上传如果传递值是空的话检查一下构造方法,打印出来看下有没有在赋值的过程出现错误,导致传参失败!
5.sql语句的判断每一层都要检查,分页查询的返回记录数方法跟dao层的方法判断要一致并且要经过测试排除问题
6.如果是带文件上传一定要在form表单加上传的代码,否则报错
7.报错行不一定是问题出现的行,排查问题要从实体类的构造方法→dao层→service层→servlet层→页面显示层,逐一判断
8.条件分页查询的判断要注意跟查询记录数的方法一致
Filter过滤器
概念
- 是一个特殊的Servlet[特殊Java类,受容器管理,容器负责创建调用销毁,取调转]
- 过滤功能,接受用户所有请求,对每一个请求进行过滤[权限]
- filter工作在浏览器与服务器之间,来过滤所有请求/*,过滤指定的请求/login
任务
-
字符编码的转换
-
权限控制[没有登录不能访问[页面]
实现一个过滤器
实现一个Filter的接口
public class MyFilter implements Filter {
public void destroy() {
}
// 过滤器链
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws ServletException, IOException {
//保证请求经过这个过滤器后正常向下执行
chain.doFilter(req, resp);
}
public void init(FilterConfig config) throws ServletException {
}
}
配置Filter
web.xml配置这个过滤器
<filter>
<filter-name>myFilter</filter-name>
<filter-class>com.kgc.filter.MyFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>myFilter</filter-name>
<!--向服务器发出所有请求,先要经过这个filter 执行doFilter方法-->
<url-pattern>/*</url-pattern>
</filter-mapping>
@WebFilter(urlPatterns = {"/login","/LoginServlet"})
接受所有请求,用户向服务发出来的每一个请求都要先经过过滤器
@WebFilter(urlPatterns = {"/*"})
权限控制
1.登录成功将User存放到session
2.sesion中是否有user就一个判断用户是否登录过的一个条件
3.一个资源一个组件,需要先登录才能访问
4.实现只有登录过的用户才能访问BookInfoServlet
Filter过滤重定向,转发不经过滤器
package com.kgc.filter;
import com.kgc.entity.User;
import javax.servlet.*;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
//login.jsp LoginServlet
@WebFilter(urlPatterns = "/*")
public class PermissionFilter implements Filter {
public void destroy() {
}
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws ServletException, IOException {
//当前发请求的用户是否登录过
HttpServletRequest request=(HttpServletRequest)req;
HttpServletResponse response=(HttpServletResponse)resp;
HttpSession session=request.getSession();
//当前用户发请求的,请求字符串 http://localhost:8080/index.jsp
String uri=request.getRequestURI();///index.jsp
//String url=request.getRequestURL().toString();// http://localhost:8080/index.jsp
if(uri.indexOf("login.jsp")>0){
chain.doFilter(req, resp);
return;
}
if(uri.indexOf("LoginServlet")>0){
chain.doFilter(req, resp);
return;
}
if(request.getRequestURI().indexOf("BookInfoServlet")>0) {
User user = (User) session.getAttribute("user");
if (user != null) {//当前发请求的用户登录过了
chain.doFilter(req, resp);
return;
} else {
response.sendRedirect("login.jsp");
return;
}
}else{
chain.doFilter(req, resp);
}
}
public void init(FilterConfig config) throws ServletException {
}
}
Listener监听器
HttpSessionListener 监听session 的创建与销毁
HttpSessionAttributeListener setAttribute(key,value)
当服务创建一个session,HttpSessionListener 就会触发一个事件sessionCreated,这个方法就被调用
服务器销毁一个session对象,HttpSessionListener中的sessionDestroyed,会被 调用
jQuery
01)html标签内写js方法
可通过a标签href调用传值事件触发js效果
html代码
<td><a href="javascript:deleteGood(${list.id})">删除</a></td>
<script>
function deleteGood(id) {
if(confirm("是否要删除?")){
window.location.href="GoodServlet?method=doDelete&goodid="+id;
}
}
</script>
02)jQuery使用步骤
01)导入文件
<script type="text/javascript" src="js/jquery-3.2.1.js"></script>
02)声明js文件或导入js文件路径
<script type="text/javascript" >
$(function(){
$("td").click(function(){
alert($(this).text());
});
});
</script>
03)声明jquery部分
声明==将dom对象包装成jQuery对象
$(function(){
内容
$("td").click(function(){
alert($(this).text());
});
03)获得一个标签对象
js语法:
得到一个dom类型的对象,通过el就可以调用dom所提供的api
val el=document.getElementById("a1");
el.value="张三"
jquery语法:
$("#a1");
$("#a1").val("张三");
代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>jQuery</title>
<style>
.c1{
color: red;
font-size: 66px;
}
</style>
</head>
<body>
<form action="#" method="POST">
<h1>学生系统</h1>
姓名:<input type="text" id="">
性别:<input type="text" id="">
<hr/>
<table border="1" width="800">
<tr>
<th>姓名</th><th>年龄</th><th>性别</th>
</tr>
<tr>
<td>张三</td><td>26</td><td>男</td>
</tr>
<tr>
<td>李四</td><td>27</td><td>男</td>
</tr>
<tr>
<td>王五</td><td>28</td><td>男</td>
</tr>
<tr>
<td>赵六</td><td>29</td><td>男</td>
</tr>
</table>
<img id="image1" src="img/bdlogo.gif">
</form>
</body>
<script type="text/javascript" src="js/jquery-3.2.1.js"></script>
<script type="text/javascript" >
$(function(){
$("td").click(function(){
// 获取对象的值
alert($(this).text());
// 给对象赋值
$(this).text("小李")
// 给当前对象增加css属性
$(this).css("color","red")
// 链式选择器==结合多种功能的语法
$(this).css("color","red").text("abc")
// 语法2
$(this).css({"color":"red","font-size":"30px"})
// 在当前对象中增加class="c1" 使其对象增加c1中css样式
$("td").addClass("c1")
$(this).addClass("c1")
// 删除c1中属性
$(this).removeClass("c1");
// 触发事件写一个html标签
$(this).html("<h1>孙悟空</h1>");
});
// 给标签增加属性
// attr操作可使用的属性
// prop操作这个对象本身就有的属性
$("#image1").click(function(){
// 点击这个对象替换src的属性
// $(this).attr("src","img/相机.png");
$(this).prop("src","img/相机.png");
});
});
</script>
</html>
04)选择器
id选择器
语法
得到jquery类型的对象
$("#id名");
取这个表单元素的value属性值,表单元素的值
$("#t1").val()
为表单元素赋值
$("#t1").val("新值")
非表单元素的取文本
类选择器
语法同上,但获得的是一个数组
标签选择器
同类选择器
05)常用API
函数 | 作用 |
---|---|
text() | 操作标签文本 |
html() | 操作标签 |
css() | 操作样式 |
addClass() | 在标签中增加class属性 |
removeClass() | 删除标签中的class属性 |
attr(k,v) | 修改标签属性值==任何属性值 |
prop(k,v) | 修改标签属性值==标签内存在的属性值 |
val() | 获取属性值或赋值 |
push() | 数组中添加元素 |
父元素.append(子元素) | 给当前元素增加子元素 |
子元素.appendTo(父元素) | 给当前元素增加父级元素 |
parent() | 得到当前元素的父节点 |
parents() | 得到当前元素的父节点的父节点 |
remove() | 删除元素 |
06)循环遍历
$("#revm").click(function(){
// 定义一个数组
var ids=[];
// 循环遍历方式一:index表示索引,data表示对象
$("td :checked").each(function(index,data){
console.log($(data).val())
//把值存入数组
ids.push($(data).val())
});
// 循环遍历方式二:
$.each( $("td :checked"),function(index,data){
console.log($(data).val())
ids.push($(data).val())
});
});
07)隔行变色
$(function(){
// 隔行换色 :odd奇数行,:even匹配所有索引值为偶数的元素,从 0 开始计数
$("tr:odd").css("background-color","mediumturquoise");
console.info($("td[style]").text());
});
08)删除选中的项
<h1>学生系统</h1>
姓名:<input type="text" id="">
性别:<input type="text" id="">
<hr/>
<table border="1" width="600">
<tr>
<th><input type="checkbox" id="all">全选</th><th>姓名</th><th>年龄</th><th>性别</th><td>操作</td>
</tr>
<tr>
<td><input type="checkbox" name="ids" value="1"></td><td>张三</td><td>26</td><td>男</td>
<td><button class="rem">删除</button></td>
</tr>
<tr>
<td><input type="checkbox" name="ids" value="2"></td><td>李四</td><td>27</td><td>男</td>
<td><button class="rem">删除</button></td>
</tr>
<tr>
<td><input type="checkbox" name="ids" value="3"></td><td>王五</td><td>28</td><td>男</td>
<td><button class="rem">删除</button></td>
</tr>
<tr>
<td><input type="checkbox" name="ids" value="4"></td><td>赵六</td><td>29</td><td>男</td>
<td><button class="rem">删除</button></td>
</tr>
</table>
<button id="revm">删除</button>
<br/>
<img id="image1" src="img/bdlogo.gif">
$(function(){
// 全选
$("#all").click(function(){
$("#all").prop("checked")
$("td :checkbox[name='ids']").prop("checked",$("#all").prop("checked"))
});
// 获取勾选对象值
$("#revm").click(function(){
//判断当前是否有选中值
if($("td :checked").length == 0){
alert("请先选择要删除的项!")
return;
}
// 循环遍历方式一:删除勾选中项
// 定义一个数组
var ids=[];
$("td :checked").each(function(index,data){
//把值存入数组
//ids.push($(data).val())
$(data).parents("tr").remove();
});
});
//删除当前点击的
$(".rem").click(function(e){
$(this).parents("tr").remove();
});
});
Ajax
jQuery发送Ajax请求
$.post(url,{key:value,key:value},function(result){});
$.get(url,{key:value,key:value},function(result){});
$.ajax();// $.get $.post都是$.ajax简化版
$.ajax({
type: "GET",//请求的类型get /post
url: "test.js",//向服务器那个controller发请求
dataType: "json",//返回结果的类型
data:key=value&key=value,
success:function(reslt0{}),服务器返回成功,就执行success方法
error:function(){}
});
代码示例
/*输一个id 在前台显示这个用户信息*/
/*不输入,在前参显示所有信息*/
$("#all").click(function () {
var userIdValue = $("#userId").val();
$.ajax({
type:"post",
url:"../AjaxServlet?op=doAll",
data:"userId="+userIdValue,
dataType:"json",
success:function (resule) {
$("#ids").text(resule.userId);
$("#names").text(resule.userName);
$("#pwds").text(resule.userPwd);
}
})
});
常用API
方法 | 说明 |
---|---|
open(String method,String url,boolean async,String user ,String password) | |
Ajax交互数据库
js方式
<html>
<head>
<title>用户登录</title>
</head>
<body>
<form action="#" method="post">
<table border="0" width="500">
<tr>
<th colspan="2"><h1>论坛注册</h1></th>
</tr>
<tr>
<td>用户名:</td>
<td><input type="text" name="userName" id="userName" onblur="chank()"><span id="info"></span></td>
</tr>
<tr>
<td>密码:</td>
<td><input type="text" name="userPwd"></td>
</tr>
<tr>
<td>确认密码:</td>
<td><input type="text" name="userPwd"></td>
</tr>
<tr>
<td colspan="2"><input type="button" value="提交"></td>
</tr>
</table>
</form>
<script type="text/javascript">
var xmlHttpRequest;
function chank() {
//得到要发给服务器的值
var userName = document.getElementById("userName").value;
//得到xmlHttpRequest这个对象,这个对象可以发ajxk请求 createXmlRequse 自定义的函数
xmlHttpRequest = createXmlRequse();
//调回调函数 这个callback函数处理服务器返回的结果 callback 自定义的函数
xmlHttpRequest.onreadystatechange= callback;
//初始化
xmlHttpRequest.open("post","../AjaxServlet?op=doBoor&userName="+userName,true);
//发请求
xmlHttpRequest.send(null)
}
function callback() {
if(xmlHttpRequest.readyState == 4){ //判断交互是否成功
if(xmlHttpRequest.status == 200){ //获取服务器返回的数据
//获取纯文本数据
//得到服务器返回的结果
var responseText =xmlHttpRequest.responseText;
document.getElementById("info").innerHTML = responseText;
}
}
}
function createXmlRequse(){
var xmlHttp;
if(window.XMLHttpRequest) {//非IE
xmlHttp = new XMLHttpRequest();
if(xmlHttp.overrideMimeType) {
xmlHttp.overrideMimeType("text/xml");
}
} else if(window.ActiveXobject) {//
var activeName = ["MSXML2.XMLHTTP", "Microsoft.XMLHTTP"];
for (var i = 0; i < activeName.length; i++) {
try {
xmlHttp = new ActiveXobject(activeName[i]);
break;
} catch (e) {
}
}
}
return xmlHttp;
}
</script>
</body>
</html>
jquery方式
<html>
<head>
<title>用户登录</title>
</head>
<body>
<table border="1" width="500">
<tr>
<th colspan="2"><h1>论坛注册</h1></th>
</tr>
<tr>
<td>用户名:</td>
<td><input type="text" name="userName" id="userName" ><span id="info"></span></td>
</tr>
<tr>
<td>密码:</td>
<td><input type="text" name="userPwd"></td>
</tr>
<tr>
<td>确认密码:</td>
<td><input type="text" name="userPwd"></td>
</tr>
<tr>
<td colspan="2"><input type="button" value="提交"></td>
</tr>
</table>
<div id="allText">
<table border="1" width="500">
<tr>
<td>用户查询:</td>
<td><input type="text" id="userId"></td>
<td><button id="all">查询</button></td>
</tr>
<tr>
<th>用户编号</th>
<th>用户账号</th>
<th>用户密码</th>
</tr>
<tr>
<td ><span id="ids"></span></td>
<td id="names"></td>
<td id="pwds"></td>
</tr>
</table>
</div>
<script type="text/javascript" src="../js/jquery-3.2.1.js" ></script>
<script type="text/javascript">
$(function () {
/*查询用户名是否存在数据库*/
$("#userName").blur(function () {
var userNameValue = $("#userName").val();
$.ajax({
type:"post",
url:"../AjaxServlet?op=doBoor",
data:"userName="+userNameValue,
success:function (resule) {
$("#info").text(resule);
}
})
})
/*输一个id 在前台显示这个用户信息*/
/*不输入,在前参显示所有信息*/
$("#all").click(function () {
var userIdValue = $("#userId").val();
$.ajax({
type:"post",
url:"../AjaxServlet?op=doAll",
data:"userId="+userIdValue,
dataType:"json",
success:function (resule) {
//$("#ids").html(resule.userId);
$("#ids").text(resule.userId);
$("#names").text(resule.userName);
$("#pwds").text(resule.userPwd);
}
})
});
//失去焦点显示所有对象
$("#userId").blur(function () {
$.ajax({
type:"post",
url:"../AjaxServlet?op=doAllSum",
success:function (resule) {
$("#ids").text(resule);
}
})
});
});
</script>
</body>
</html>
Servlet后台代码
@WebServlet(urlPatterns = "/AjaxServlet")
public class AjaxServlet extends HttpServlet {
private UserDaoImpl userDao = new UserDaoImpl();
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
response.setContentType("text/html;charset=UTF-8");
String op = request.getParameter("op");
System.out.println(op);
if ("doAll".equals(op))
this.doAll(request,response);
else if ("doBoor".equals(op))
this.doBoor(request,response);
else if ("doAllSum".equals(op))
this.doAllSum(request,response);
else
this.doAllSum(request,response);
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
this.doPost(request,response);
}
protected void doAllSum(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//获得打印对象
PrintWriter out = response.getWriter();
//查询结果集
List<User> all = userDao.findAll();
//通过gson转换格式
Gson gson = new Gson();
String s = gson.toJson(all);
out.print(s);
}
//查询单条数据
protected void doAll(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
PrintWriter out = response.getWriter();
String userId = request.getParameter("userId");
User byId = userDao.findById(userId);
Gson gson = new Gson();
String s = gson.toJson(byId);
out.print(s);
}
//向后台发送账号,检查是否存在
protected void doBoor(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
PrintWriter out = response.getWriter();
String userName = request.getParameter("userName");
//向后台发送账号,检查是否存在
if (userDao.isName(new User(userName))){
out.print("该账户已被占用,请更换!");
}else {
out.print("该账户可以正常注册!");
}
}
}
参数说明
参数 | 类型 | 说明 |
---|---|---|
url | String | 必选,发送请求的地址 |
data | Plainobject或 String | 发送到服务器的数据 |
success | Function( PlainObject result , String textStatus,jqXHR jqxhr ) | 请求成功后调用的函数, 参数result:可选,由服务器返回的数据 |
dataType | String | 预期服务器返回的数据类型, 包括:XML、HTML.Script |
$.get()方法的使用
$.get(url,data,function(result){
//省略服务器返回的数据显示到页面的代码
});
Maven
云仓配置
<mirrors>
<!--复制以下代码放入mirrors中后,项目需要的jar包如果没有将会在阿里云自动下载-->
<mirror>
<!--This sends everything else to /public -->
<id>nexus</id>
<mirrorOf>*</mirrorOf>
<url>http://maven.aliyun.com/nexus/content/groups/public/</url>
</mirror>
<mirror>
<id>nexus-public-snapshots</id>
<mirrorOf>public-snapshots</mirrorOf>
<url>http://maven.aliyun.com/nexus/content/repositories/snapshots/</url>
</mirror>
<mirror>
<id>Central</id>
<url>http://repo1.maven.org/maven2</url>
<mirrorOf>central</mirrorOf>
</mirror>
</mirrors>
th>
Servlet后台代码
@WebServlet(urlPatterns = "/AjaxServlet")
public class AjaxServlet extends HttpServlet {
private UserDaoImpl userDao = new UserDaoImpl();
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
response.setContentType("text/html;charset=UTF-8");
String op = request.getParameter("op");
System.out.println(op);
if ("doAll".equals(op))
this.doAll(request,response);
else if ("doBoor".equals(op))
this.doBoor(request,response);
else if ("doAllSum".equals(op))
this.doAllSum(request,response);
else
this.doAllSum(request,response);
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
this.doPost(request,response);
}
protected void doAllSum(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//获得打印对象
PrintWriter out = response.getWriter();
//查询结果集
List<User> all = userDao.findAll();
//通过gson转换格式
Gson gson = new Gson();
String s = gson.toJson(all);
out.print(s);
}
//查询单条数据
protected void doAll(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
PrintWriter out = response.getWriter();
String userId = request.getParameter("userId");
User byId = userDao.findById(userId);
Gson gson = new Gson();
String s = gson.toJson(byId);
out.print(s);
}
//向后台发送账号,检查是否存在
protected void doBoor(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
PrintWriter out = response.getWriter();
String userName = request.getParameter("userName");
//向后台发送账号,检查是否存在
if (userDao.isName(new User(userName))){
out.print("该账户已被占用,请更换!");
}else {
out.print("该账户可以正常注册!");
}
}
}
参数说明
参数 | 类型 | 说明 |
---|---|---|
url | String | 必选,发送请求的地址 |
data | Plainobject或 String | 发送到服务器的数据 |
success | Function( PlainObject result , String textStatus,jqXHR jqxhr ) | 请求成功后调用的函数, 参数result:可选,由服务器返回的数据 |
dataType | String | 预期服务器返回的数据类型, 包括:XML、HTML.Script |
$.get()方法的使用
$.get(url,data,function(result){
//省略服务器返回的数据显示到页面的代码
});
Maven
云仓配置
<mirrors>
<!--复制以下代码放入mirrors中后,项目需要的jar包如果没有将会在阿里云自动下载-->
<mirror>
<!--This sends everything else to /public -->
<id>nexus</id>
<mirrorOf>*</mirrorOf>
<url>http://maven.aliyun.com/nexus/content/groups/public/</url>
</mirror>
<mirror>
<id>nexus-public-snapshots</id>
<mirrorOf>public-snapshots</mirrorOf>
<url>http://maven.aliyun.com/nexus/content/repositories/snapshots/</url>
</mirror>
<mirror>
<id>Central</id>
<url>http://repo1.maven.org/maven2</url>
<mirrorOf>central</mirrorOf>
</mirror>
</mirrors>
maven用骨架创建web.xml文件需要改