【database1】mysql:DDL/DML/DQL,外键约束/多表/子查询,事务/连接池
文章目录
- 1.mysql安装:存储:集合(内存:临时),IO流(硬盘:持久化)
- 1.1 服务端:双击mysql-installer-community-5.6.22.0.msi
- 1.2 客户端:命令行输入mysql -u...实际是如下安装路径的bin文件夹的mysql.exe
- 2.DDL/DML:char不用动态变化,效率高
- 3.DQL:select(相当于System.out)第一个但在倒数第二执行
- 4.约束和自增长:字段约束(字段的赋值规范)/主键约束(唯一非空且一张表只有一个主键)
- 5.单表缺点和外键约束:多从外 引出
- 6.三种多表关系:中间表两外键:一对一(简历),一对多(员工,部门),多对多(学生,课表)
- 7.多表查询:表..join表on
- 7.1 外连接:左外=左表+内连接
- 8.子查询:优先于主查询产生结果
- 9.事务:一组操作,要么同时成功,要么同时失败
- 10.四个接口:左java.sql包下的DCSR,右com.mysql.jdbc.Driver
- 11.释放资源:finally,工具类封装
- 12.JDBC事务操作:conn.setAutoCommit(false)
- 13.登陆案例预编译改造:PreparedStatement,setString,executeQuery
- 14.c3p0连接池:jdbc2.0才引进连接池,不是线程池(连接池的技术标准就是DataSource替代DriverManager)
- 15.druid连接池:自动ds.set
- 16.execute/update方法:template =
- 17.queryForXX/query方法:Map.Entry < String, Object > ,Map < String, Object > 两个数据类型
1.mysql安装:存储:集合(内存:临时),IO流(硬盘:持久化)
1.1 服务端:双击mysql-installer-community-5.6.22.0.msi
mysql安装包:链接:https://pan.baidu.com/s/18Ctus6BLVrECZP0W-QKtfw 提取码:94s9。
上面next,execute安装后,下面开始配置。
1.2 客户端:命令行输入mysql -u…实际是如下安装路径的bin文件夹的mysql.exe
命令行java -version要配环境变量,看mysql有没有运行,只能从任务管理器看有没有mysql的进程。
win下cmd输入:完整版没有括号:mysql -h(host)
127.0.0.1 -P(port)
3306 -u(username)
root -p(password)
。简略版:mysql -u root -p。
可视化工具navicat链接:https://pan.baidu.com/s/11qAEA7yEGSIz6J9GIC_S6A 提取码:1w9n。navicat免安装链接:https://pan.baidu.com/s/1zanhYyyNsUXajI-czfW7KA 提取码:om5g。
2.DDL/DML:char不用动态变化,效率高
如下中间蓝框里一个数据库相当于一个excel表
,紫色框里一个table相当于excel表里的一个sheet
。use数据库相当于双击打开excel表格,select查看函数返回值,desc全称description,like复制表结构,change 旧字段 新字段 新类型
。
数据库名字不建议修改,用数据库备份改名(新建一个数据库,把原数据库数据复制过来)。mysql中utf-8中-无法识别,用utf8。ISO-8859-1用latin1。
注意(),逗号,分号。
如下数(整小)日字
,oracle两个不同:number包含整小,varchar2。
选用timestamp而不用datetime,因为datetime不会自动设置时间。
int(11)默认11位不用写出来,2147483647即21亿10位
,如果有负数还有最前面一位是符号位,所以一共11位
。
如下是表记录,select非常多,删除只是记录,表结构还在。
DDL后面不需要加from等词。
如下单引号可加可不加。
如下要写两个add。
3.DQL:select(相当于System.out)第一个但在倒数第二执行
如下3中第一排序字段相同的里面再进行第二排序。
如下查询id是1或3或5的学生。
d低下降,只要有数字都比null大。
如下有英语成绩有6个,不能代表总人数,缺考没算入。
select后的第一个字段要和group by后同。
如下是select语句执行顺序,红字书写顺序必须这样。
sql只有一种情况报错:语法写错。如下索引越界不会报错。
page和count是前端传来的两个参数,count不用变。
数量(count(*))降序只要一个(limit 1)。
如下将db3数据库整个连数据备份,本质create,insert。记住mysqldump和source。
4.约束和自增长:字段约束(字段的赋值规范)/主键约束(唯一非空且一张表只有一个主键)
如下验证主键唯一和非空
,如下两个框都报错。
如下的Null列表示是否允许为空。
5.单表缺点和外键约束:多从外 引出
多表是外键约束的前提,外键约束解决下面多表的2个问题,add…多了一条线。alter table emploee drop foreign key
fk_001。
如上是在已有表添加外键,如下建表就添加(开发中常用)。
如果要删除department表的id为001即整个研发部门,需要先在employee表中删除id=001的很多记录,很麻烦。现在想要删除department的001部门时employee为001的行也一起删了,所以用外键级联操作
,如下create table …中省略同上。
6.三种多表关系:中间表两外键:一对一(简历),一对多(员工,部门),多对多(学生,课表)
7.多表查询:表…join表on
CREATE DATABASE day03;
USE day03;
-- 创建部门表
CREATE TABLE dept (id INT PRIMARY KEY AUTO_INCREMENT,NAME VARCHAR(20)
);
INSERT INTO dept (NAME) VALUES ('开发部'),('市场部'),('财务部');
-- 创建员工表
CREATE TABLE emp ( id INT PRIMARY KEY AUTO_INCREMENT,NAME VARCHAR(10),gender CHAR(1), -- 性别salary DOUBLE, -- 工资join_date DATE, -- 入职日期dept_id INT
);
INSERT INTO emp(NAME,gender,salary,join_date,dept_id) VALUES('孙悟空','男',7200,'2013-02-24',1);
INSERT INTO emp(NAME,gender,salary,join_date,dept_id) VALUES('猪八戒','男',3600,'2010-12-02',2);
INSERT INTO emp(NAME,gender,salary,join_date,dept_id) VALUES('唐僧','男',9000,'2008-08-08',2);
INSERT INTO emp(NAME,gender,salary,join_date,dept_id) VALUES('白骨精','女',5000,'2015-10-07',3);
INSERT INTO emp(NAME,gender,salary,join_date,dept_id) VALUES('蜘蛛精','女',4500,'2011-03-14',1);
如下要查出有用的记录需要emp.dept_id(emp外键)=dept.id(dept主键)。
因为select * ,所以将两个橙色横框拼接起来,棕色框。
7.1 外连接:左外=左表+内连接
如下注意记住左表不动。
如下第一个内连接没有销售部(销售部没有和员工表任何数据相交),第二个有销售部。
union all不去重,左外连接+右外连接。
8.子查询:优先于主查询产生结果
如下执行两句sql,要连接两次数据库,子查询一般要写在()里。
如下1,2是dept_id,可以把in换成 = any
。
如下第一行和第二行效果相同。
如下两个select等价。
如下还是写上面的题目,如果用内连接,沙僧会没有,左外或右外连接都可以。
如下将上面的id1列去除(即将dept表的id列去除不显示)。
on比where先执行。
-- 11111111111111111111111111111111111111111111111111111111111111111部门表
CREATE TABLE dept (id INT PRIMARY KEY PRIMARY KEY, -- 部门iddname VARCHAR(50), -- 部门名称loc VARCHAR(50) -- 部门位置
);
-- 添加4个部门
INSERT INTO dept(id,dname,loc) VALUES
(10,'教研部','北京'),
(20,'学工部','上海'),
(30,'销售部','广州'),
(40,'财务部','深圳');-- 1111111111111111111111111111111111111111111111111111111职务表,职务名称,职务描述
CREATE TABLE job (id INT PRIMARY KEY,jname VARCHAR(20),description VARCHAR(50)
);
-- 添加4个职务
INSERT INTO job (id, jname, description) VALUES
(1, '董事长', '管理整个公司,接单'),
(2, '经理', '管理部门员工'),
(3, '销售员', '向客人推销产品'),
(4, '文员', '使用办公软件');-- 11111111111111111111111111111111111111111111111111111111111111111111员工表
CREATE TABLE emp (id INT PRIMARY KEY, -- 员工idename VARCHAR(50), -- 员工姓名job_id INT, -- 职务idmgr INT , -- 上级领导joindate DATE, -- 入职日期salary DECIMAL(7,2), -- 工资bonus DECIMAL(7,2), -- 奖金dept_id INT, -- 所在部门编号CONSTRAINT emp_jobid_ref_job_id_fk FOREIGN KEY (job_id) REFERENCES job (id),CONSTRAINT emp_deptid_ref_dept_id_fk FOREIGN KEY (dept_id) REFERENCES dept (id)
);
-- 添加员工
INSERT INTO emp(id,ename,job_id,mgr,joindate,salary,bonus,dept_id) VALUES
(1001,'孙悟空',4,1004,'2000-12-17','8000.00',NULL,20),
(1002,'卢俊义',3,1006,'2001-02-20','16000.00','3000.00',30),
(1003,'林冲',3,1006,'2001-02-22','12500.00','5000.00',30),
(1004,'唐僧',2,1009,'2001-04-02','29750.00',NULL,20),
(1005,'李逵',4,1006,'2001-09-28','12500.00','14000.00',30),
(1006,'宋江',2,1009,'2001-05-01','28500.00',NULL,30),
(1007,'刘备',2,1009,'2001-09-01','24500.00',NULL,10),
(1008,'猪八戒',4,1004,'2007-04-19','30000.00',NULL,20),
(1009,'罗贯中',1,NULL,'2001-11-17','50000.00',NULL,10),
(1010,'吴用',3,1006,'2001-09-08','15000.00','0.00',30),
(1011,'沙僧',4,1004,'2007-05-23','11000.00',NULL,20),
(1012,'李逵',4,1006,'2001-12-03','9500.00',NULL,30),
(1013,'小白龙',4,1004,'2001-12-03','30000.00',NULL,20),
(1014,'关羽',4,1007,'2002-01-23','13000.00',NULL,10);-- 1111111111111111111111111111111111111111111111111111111111111111工资等级表
CREATE TABLE salarygrade (grade INT PRIMARY KEY,losalary INT,hisalary INT
);
-- 添加5个工资等级
INSERT INTO salarygrade(grade,losalary,hisalary) VALUES
(1,7000,12000),
(2,12010,14000),
(3,14010,20000),
(4,20010,30000),
(5,30010,99990);
9.事务:一组操作,要么同时成功,要么同时失败
如下若在执行一次sql前执行一次start transaction,若不commit,刷新数据库不显示。
10.四个接口:左java.sql包下的DCSR,右com.mysql.jdbc.Driver
如下mchange. .和c3p0. .一起。第一个导入的是mysql-connector…。
如下代码第一行new Driver()是导入com.mysql.jdbc(用mysql实现好的,就是上面导入的mysql-connector..jar包)
而不是java.sql(自己不会重写抽象方法)下,参数是接口类型需要传入接口的实现类对象即new Driver()。registerDriver相当于set方法,get获取的是mysql.Driver.connect方法返回的Connection类即com.mysql.jdbc.JDBC4Connection(有mysql.的都是导入的jar包)。
加载DriverManager这个类用到打破双亲类加载:DriverManager是jdk自带的类,DriverManager类使用的是bootstrap引用类加载器。数据库是用户类用bootstrap加载不合适,所以DriverManager去加载h2的Driver需要把当前引用类加载器替
换为当前系统或当前线程的应用app类加载器
。
package com.itheima01.jdbc;
import com.mysql.jdbc.Driver;
import java.sql.*;public class JdbcDemo { public static void main(String[] args) throws SQLException, ClassNotFoundException, IllegalAccessException, InstantiationException {//1. 注册驱动 (注意: 导入的mysql的驱动)/** A. 查看mysql.Driver源码: 点new Driver()中Driver看源码* 发现static 代码块里 已经注册了驱动 -> 驱动自注册 相当于set一次就行* 带来问题: 外部的注册没有意义(重复注册)* * 解决: 保证mysql.Driver类被加载(静态代码块就会执行),如下两种方案:* 1. 创建对象* 2. 反射:a. 节省内存* b. 跟驱动包的关联只剩一个字符串:"com.mysql.jdbc.Driver"* 待会将字符串写入配置文件,只要改配置文件就行 就会跟 mysql驱动包的彻底解耦 *///111111111111111111111111111111111111111111111111111111111111111111111111111111111111
// DriverManager.registerDriver(new Driver()); //这行重复注册,下行new了就会加载 源码里的静态代码块,所以这行=下行//new Driver(); // Class对象 + 普通实例 //只要用了这个类,这个类就会被加载内存中方法区 //自动导包// new Driver()的内存消耗等价于下面两行: 其实只需要calss对象,不需要实例 // Class<?> clazz = Class.forName("com.mysql.jdbc.Driver"); //获取这个类的class对象// Object obj = clazz.newInstance(); //利用class对象调用其空参构造来创建一个实例Class.forName("com.mysql.jdbc.Driver"); //获取Class对象,没有普通实例,因为普通实例没有意义 //用反射,com.mysql.jdbc.Driver这个类也会被加载//111111111111111111111111111111111111111111111111111111111111111111111111111111111111//2. 获取连接/** 只要涉及两个软件通信 : 网络三要素(必要非充分:一定要,但是有它们三不一定够如多了资源位置)* 1. 协议 : jdbc:mysql (主协议:子协议)* 2. ip : 数据库所在的计算机(自己:localhost或127.0.0.1)* 3. port : mysql数据库3306* 资源位置: 数据仓库的名称* * 协议://ip:port/资源位置* https://www.baidu.com:443*/
// String url = "jdbc:mysql://localhost:3306/day03"; //day03是数据库String url = "jdbc:mysql:///day03"; //ip:localhost port:3306 可以省略String user = "root";String pwd = "1234";Connection conn = DriverManager.getConnection(url, user, pwd);System.out.println("conn:" + conn); //引用类型打印地址//1111111111111111111111111111111111111111111111111111111111111111111111111111111111//3. 创建执行sql的语句对象/** Connection 接口的一些方法* <1>. Statement createStatement(); 创建执行sql的语句对象,相当于创建一个流* <2>. PreparedStatement prepareStatement(sql); 创建一个预编译sql的语句对象* <3>. 事务操作相关*/Statement statement = conn.createStatement();System.out.println("statement:" + statement);//11111111111111111111111111111111111111111111111111111111111111111111111111111111111//4. 执行sql,返回结果/** Statetment 接口的api* 1. ResultSet statement.executeQuery(sql);* 执行的查询语句 : DQL* 返回的查询结果: 结果集* * 2. int executeUpdate(sql) :* 执行的增删改语句: DML* 返回的结果: 被影响的行数* * 3. boolean execute(sql); -> 不需要掌握,知道即可* 万能 : DDL等 如create成功或失败是和异常相关,和返回值无关* 返回值: 非查询语句返回false,查询语句返回true*/String sql = "select * from emp";ResultSet resultSet = statement.executeQuery(sql);//11111111111111111111111111111111111111111111111111111111111111111111111111111111111 //5. 处理结果while(resultSet.next()){String name = resultSet.getString("name");
// String id = resultSet.getString("id"); //也可以,java程序以外的所有数据对java来说都是字符串int id = resultSet.getInt("id"); //底层先调用getString再parse intSystem.out.println(id+ ":" + name);}//11111111111111111111111111111111111111111111111111111111111111111111111111111111111//6. 释放资源resultSet.close();statement.close();conn.close();}
}
resultset不是返回一行数据,而是带有id=…。因为返回一行数据如 11孙悟空男,不知道怎么解析。
如下hasNext和next区别。
11.释放资源:finally,工具类封装
package com.itheima04.release;
import com.itheima05.utils.JdbcUtil;
import java.io.Closeable;
import java.io.IOException;
import java.sql.*;public class ReleaseDemo {public static void main(String[] args) {ResultSet resultSet = null;Statement statement = null;Connection conn = null;try {/*Class.forName("com.mysql.jdbc.Driver");String url = "jdbc:mysql://localhost:3306/day03";String user = "root";String pwd = "1234";conn = DriverManager.getConnection(url, user, pwd);*/conn = JdbcUtil.getConnection(); //查询要获取连接,getConnection方法调用多遍,所以getConnection方法不写try catch,查询提示 查询失败,删除提示 删除失败,封装时不知道是查询还是删除,不好提示,所以往外抛。conn = JdbcUtil.getConnection(); //增删改也要获取连接//1111111111111111111111111111111111111111111111111111111111111111111111111 statement = conn.createStatement();String sql = "select * from emp"; resultSet = statement.executeQuery(sql); while(resultSet.next()){String name = resultSet.getString("name");System.out.println(name);}} catch (Exception e) {e.printStackTrace();} finally{/* if(resultSet != null){try {resultSet.close();} catch (SQLException e) {e.printStackTrace();}}if(statement != null){try {statement.close();} catch (SQLException e) {e.printStackTrace();}}if(conn != null){try {conn.close();} catch (SQLException e) {e.printStackTrace();}}*/// closeIo(resultSet,statement,conn);JdbcUtil.release(conn,statement,resultSet);}}//1111111111111111111111111111111111111111111111111111111111111111111111private static void closeIo(AutoCloseable... ios) { //AutoCloseable接口位于java.lang包下,不用导包for (AutoCloseable io : ios) {if(io != null){try {io.close();} catch (Exception e) {e.printStackTrace();}}}}
}
package com.itheima05.utils;
import java.sql.*;
/**
* 工具类: 0. 拥有很多 工具方法(重复的代码封装) 的类
* 命名规范: utils 包 -> xxUtil 类 (xx : 某个模块的名称)
* Objects,Arrays,Collections...(JDK提供的)
*
* 1. 一般工具类中方法是静态的,不用实例化,节省内存
*
* 2. 封装方法的步骤
* 1. 先把要把封装的代码写出来
* 2. 观察不断重复的部分
* 3. 定义方法,然后直接复制过来
* 4. 设置参数和返回值
*
* 注意点: 1. 扩展性 : 不要导入mysql包中的类, 要导入java包中的类(这样换成oracle也可用)
* 2. 工具类中的异常一般是往外抛 : 一般异常是要在业务中处理
*/
public class JdbcUtil {static{try {Class.forName("com.mysql.jdbc.Driver");} catch (ClassNotFoundException e) {e.printStackTrace();}}//1111111111111111111111111111111111111111111111111111111111111111111111111111111public static Connection getConnection() throws SQLException {//此方法会被多次调用,注册驱动只需要一次 -> 所以用静态代码块 如上
// Class.forName("com.mysql.jdbc.Driver");String url = "jdbc:mysql://localhost:3306/day03";String user = "root";String pwd = "1234";Connection conn = DriverManager.getConnection(url, user, pwd);return conn;}//1111111111111111111111111111111111111111111111111111111111111111111111111111111/*** 文档注释: a. 写在类上面 : 描述类的用途* b. 写在方法上面 : 描述方法的用途 (返回值,参数)*/public static void release(Connection conn, Statement statement, ResultSet resultSet){//java.sql.Connectionif(resultSet != null){try {resultSet.close();} catch (SQLException e) {e.printStackTrace();}}if(statement != null){try {statement.close();} catch (SQLException e) {e.printStackTrace();}}if(conn != null){try {conn.close();} catch (SQLException e) {e.printStackTrace();}}}
}
如下改进上面工具类。
/*
* 问题: 驱动,url,用户名和密码等信息 是有可能会变的, 变动频率比较低
* 1. 如果不变,直接写死在代码中
* 2. 变,但是频率高 : 一般设置成参数
* 3. 变,但是频率不高: 放在配置文件
* 1. 解耦 : 信息要改变的话,只要改配置文件,代码不用改,程序不需要重新编译和部署
* 2. 代码简化 : 无需调用的时候传参了
*/
//jdbc.properties文件,每个月改一次 //文件里没有关键字,也没有双引号,本来就是字符串
driverName = com.mysql.jdbc.Driver
url = jdbc:mysql://localhost:3306/day03
user = root
pwd = 1234
package com.itheima05.utils;
import java.io.FileInputStream;
import java.sql.*;
import java.util.Properties;public class JdbcUtil02 {static String driverName;static String url;static String user;static String pwd;static{try {Properties p = new Properties();p.load(new FileInputStream("src/jdbc.properties"));driverName = p.getProperty("driverName");url = p.getProperty("url");user = p.getProperty("user");pwd = p.getProperty("pwd");Class.forName(driverName);} catch (Exception e) {e.printStackTrace();}} //1111111111111111111111111111111111111111111111111111111111111111111111111111111111public static Connection getConnection() throws SQLException {Connection conn = DriverManager.getConnection(url, user, pwd);return conn;}//11111111111111111111111111111111111111111111111111111111111111111111111111111111111 public static void release(Connection conn, Statement statement, ResultSet resultSet){if(resultSet != null){try {resultSet.close();} catch (SQLException e) {e.printStackTrace();}}if(statement != null){try {statement.close();} catch (SQLException e) {e.printStackTrace();}}if(conn != null){try {conn.close();} catch (SQLException e) {e.printStackTrace();}}}
}
12.JDBC事务操作:conn.setAutoCommit(false)
package com.itheima01.transaction;
import com.itheima.utils.JdbcUtil;
import java.sql.Connection;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Scanner;
// JDBC : 写一个转账案例
public class Demo {public static void main(String[] args) { System.out.println("请输入转出的账户:"); Scanner sc = new Scanner(System.in); // 控制台: 模拟页面String outUser = sc.nextLine();System.out.println("请输入转入的账户:");String inUser = sc.nextLine(); System.out.println("请输入转账的金额:");double money = sc.nextDouble();//sql里面最好写单引号 , 1000和jack改为 两个双引和两个+号//String sql1 = "update account set money = money-1000 where name = 'jack'";String sql1 = "update account set money = money-"+money+" where name = '"+outUser+"'";String sql2 = "update account set money = money+"+money+" where name = '"+inUser+"'";//11111111111111111111111111111111111111111111111111111111111111111111111111111111111111Connection conn = null;try {/** 事务操作: Connection* 1. setAutoCommit(false); 开启事务* 2. commit(); 提交事务* 3. rollback(); 事务回滚* 注意点: 在事务中, 开启事务的连接才具有手动提交事务的功能* 一组操作都必须要同一个 连接conn 要执行*/ conn = JdbcUtil.getConnection(); //访问数据库,try外面定义conn// Connection conn2 = JdbcUtil.getConnection(); conn.setAutoCommit(false); //开启事务,禁止自动提交 Statement statement = conn.createStatement(); statement.executeUpdate(sql1); //转出 // int i = 1/0; // ArithmeticException 算术异常 模拟银行爆炸 Statement statement2 = conn.createStatement(); statement2.executeUpdate(sql2); //转入//1111111111111111111111111111111111111111111111111111111111111111111111111111111111111 conn.commit(); //提交事务(和事务回滚只有其一执行) System.out.println("转账成功~~");} catch (Exception e) { // 注意: 提升异常级别(用于捕获算术异常)e.printStackTrace();if(conn != null){ //Connection conn放外面,这边访问的到try {conn.rollback(); //事务回滚} catch (SQLException e1) {e1.printStackTrace();}}System.out.println("转账失败");}}
}
13.登陆案例预编译改造:PreparedStatement,setString,executeQuery
package com.itheima02.login;
import com.itheima.utils.JdbcUtil;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Scanner;
/*前提: 用户能够登录,说明已经注册过了注册成功的时候, 程序会把用户的信息保存到数据库* 登录案例: 逻辑: 请输入用户名和密码(用户)
* 我们: 校验数据库
* sql : select * from account where name = ? and pwd = ?; (name用户名唯一)
* 预测结果: 1. 0条 : 用户名不存在或密码错误
* 2. 1条 : 登录成功
*/
public class LoginDemo {public static void main(String[] args) throws SQLException {System.out.println("请输入用户名:");Scanner sc = new Scanner(System.in);String name = sc.nextLine(); System.out.println("请输入密码:");String pwd = sc.nextLine();String sql = "select * from account where name = '"+name+"' and pwd = '"+pwd+"'";System.out.println(sql); //将参数(上面键盘输入)直接拼接进sql//1111111111111111111111111111111111111111111111111111111111111111111111111111111111111111Connection conn = JdbcUtil.getConnection();Statement statement = conn.createStatement(); ResultSet resultSet = statement.executeQuery(sql); //将sql发送给数据库去处理if(resultSet.next()){ //有一条则为trueSystem.out.println("登录成功~~");}else{System.out.println("用户名不存在或密码错误");}}
}
根据(用户名和密码)或(1=1永真)为条件查询数据库,what可以随便写。
预编译知道了sql的语法结构了,已经把关键字认全了,后面再包含关键字or
就不认了(当成字符串处理),可以防止sql注入
。
package com.itheima02.login;
import com.itheima.utils.JdbcUtil;
import java.sql.*;
import java.util.Scanner;public class LoginDemo02 {public static void main(String[] args) throws SQLException {System.out.println("请输入用户名:");Scanner sc = new Scanner(System.in);String name = sc.nextLine(); System.out.println("请输入密码:");String pwd = sc.nextLine();// 1. 改造sql String sql = "select * from account where name = ? and pwd = ?";System.out.println(sql);Connection conn = JdbcUtil.getConnection();// 2. 预编译sql // PreparedStatement 是 Statement的子接口PreparedStatement statement = conn.prepareStatement(sql);// 3. 设置参数// setString(int parameterIndex, String x)// parameterIndex : sql中的?的索引(从1开始,从左开始) // String x: 参数statement.setString(1,name);statement.setString(2,pwd);// 4. 传参执行ResultSet resultSet = statement.executeQuery();if(resultSet.next()){System.out.println("登录成功~~");}else{System.out.println("用户名不存在或密码错误");}}
}
如下手动在数据库中增加一行。
package com.itheima03.prepare;
import com.itheima.utils.JdbcUtil;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.sql.Statement;
/*
* 预编译的好处: 1. 防止sql注入
* 2. 阅读性强(sql)
* 3. 批量处理sql,效率高 (节省了sql重复编译过程)
*/
public class PrepareDemo {public static void main(String[] args) throws SQLException {
// method01(); //用预编译,如下不用预编译String name = "ww";int money = 200;String sql1 = "insert into account values(null,'"+name+"',"+money+",null)";String name2 = "www";int money2 = 2002;String sql2 = "insert into account values(null,'"+name2+"',"+money2+",null)"; Connection conn = JdbcUtil.getConnection();Statement statement = conn.createStatement(); //不用预编译statement.executeUpdate(sql1);// 编译+运行statement.executeUpdate(sql2);//编译+运行,和上行一共两次编译 statement.close();conn.close();}//1111111111111111111111111111111111111111111111111111111111111111111111111private static void method01() throws SQLException {String sql = "insert into account values(null,?,?,null)"; Connection conn = JdbcUtil.getConnection();PreparedStatement pstm = conn.prepareStatement(sql); pstm.setString(1,"zs");pstm.setDouble(2,1000);pstm.executeUpdate();//运行pstm.setString(1,"ls");pstm.setDouble(2,2000);pstm.executeUpdate();//运行 pstm.close();conn.close();}
}
14.c3p0连接池:jdbc2.0才引进连接池,不是线程池(连接池的技术标准就是DataSource替代DriverManager)
package com.itheima04.c3p0;
import com.mchange.v2.c3p0.ComboPooledDataSource;
import java.beans.PropertyVetoException;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;public class C3p0Demo { public static void main(String[] args) throws PropertyVetoException, SQLException {
// method01(); //这行方法和下面xml文件无关/** 配置文件方式 : 默认情况下, c3p0将会在 类加载器路径(在当前的工程下, src路径)下* 寻找一个名为c3p0-config.xml 配置文件(xml文件是复杂的Properties文件,也是key-value)* * 套路: 1. 在src下创建名为c3p0-config.xml配置文件(内容直接复制)* 2. 创建ComboPooledDataSource核心类 */ComboPooledDataSource cpds = new ComboPooledDataSource(); //1. 底层自动会去类加载器路径(写代码:src下) 去寻找一个名为c3p0-config.xml 配置文件// 2. 自动解析: 读取xml中配置信息 , 设置给c3p0即cpds String sql = "select * from account"; // 同下面 Connection conn = cpds.getConnection(); PreparedStatement pstm = conn.prepareStatement(sql);ResultSet resultSet = pstm.executeQuery();while(resultSet.next()){String name = resultSet.getString("name");System.out.println(name + "--");}conn.close();// 将连接还给连接池cpds.close(); // 销毁}//111111111111111111111111111111111111111111111111111111111111111111111111111111111111111private static void method01() throws PropertyVetoException, SQLException {// 如下硬编码: 用代码来实现参数的设置。一般不用硬编码,用配置文件ComboPooledDataSource cpds = new ComboPooledDataSource();//ComboPooledDataSource是DataSource实现类cpds.setDriverClass( "com.mysql.jdbc.Driver"); //需要mysql-connector-java-x.x.x-bin.jarcpds.setJdbcUrl( "jdbc:mysql://localhost:3306/day05" );cpds.setUser("root");cpds.setPassword("1234");String sql = "select * from account"; Connection conn = cpds.getConnection(); PreparedStatement pstm = conn.prepareStatement(sql);ResultSet resultSet = pstm.executeQuery();while(resultSet.next()){String name = resultSet.getString("name");System.out.println(name); //System.err.println(name);//红色}conn.close();// 将连接还给连接池cpds.close(); // 销毁}
}
//c3p0-config.xml
<c3p0-config> <default-config> <!-- 使用默认的配置读取连接池对象 --><!-- 如下连接参数 --> <property name="driverClass">com.mysql.jdbc.Driver</property><property name="jdbcUrl">jdbc:mysql://localhost:3306/day05</property><property name="user">root</property><property name="password">1234</property><!-- 如下连接池参数 --><!--initialPoolSize : 初始化连接数 3maxPoolSize: 最大连接数 5checkoutTimeout : 连接超时时间 2000ms(默认10s,访问数超过最大连接数, 有人必须要等,2秒连不上给个提示或报错) maxIdleTime :最大的闲置时间,连接超过maxIdleTime没人使用闲置就销毁maxPoolSize中连接,留到minPoolSize中数量,因为费内存--><property name="initialPoolSize">3</property><property name="maxPoolSize">5</property><property name="minPoolSize">2</property><property name="checkoutTimeout">2000</property><property name="maxIdleTime">1000</property></default-config><!--111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111--><named-config name="xx"><!-- 连接参数 --><property name="driverClass">com.mysql.jdbc.Driver</property><property name="jdbcUrl">jdbc:mysql://localhost:3306/beitai</property><property name="user">root</property><property name="password">root</property><!-- 连接池参数 --><property name="initialPoolSize">5</property><property name="maxPoolSize">15</property><property name="checkoutTimeout">2000</property><property name="maxIdleTime">1000</property></named-config>
</c3p0-config>
package com.itheima04.c3p0;
import org.junit.Test;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.util.Properties;public class ParseDemo {@Testpublic void method01() throws IOException {Properties p = new Properties(); //Properties就是一个map p.load(new FileInputStream("src/jdbc.properties")); //相对路径:当前工程src下String url = p.getProperty("url"); //.properties文件中有url=...System.out.println(url);} @Testpublic void method02() throws IOException {/** 1. 类加载器 classloader 【底层: 输入流】* 作用: 将 .class文件(硬盘) 加载进内存(兼职把jdbc.properties加载进来)。* * 2. classloader怎么知道.class文件在哪里?* classloader有个默认加载路径:out路径下项目名路径(src和out/production/项目名路径里文件全一样)。* * 相比method01,一般用method02更通用,因为每个工程都会有类加载器路径,但是每个工程的相对路径不一定是当前工程src下。* 如web阶段main方法不在项目里,每个项目的入口是main方法,main方法在tomcat里,* 所以工程的相对路径会变,但是类加载器的路径不变,一直指向.class文件路径。*/ClassLoader classLoader = ParseDemo.class.getClassLoader(); //利用当前类获取类加载器路径InputStream is = classLoader.getResourceAsStream("jdbc.properties"); //获取资源转成流 Properties p = new Properties();p.load(is);String url = p.getProperty("url");System.out.println(url + "-2");}
}
package com.itheima04.c3p0;
import com.mchange.v2.c3p0.ComboPooledDataSource;
import java.sql.Connection;
import java.sql.SQLException;
//c3p0-config.xml验证
public class C3p0Demo02 { public static void main(String[] args) throws SQLException { ComboPooledDataSource ds = new ComboPooledDataSource(); //使用默认配置即c3p0-config.xml中<default-config> // ComboPooledDataSource ds = new ComboPooledDataSource("xx"); //使用命名配置即c3p0-config.xml中<named-config name="xx"> //备胎项目用。 for (int i = 0; i < 6; i++) { //循环模拟: 有几多个用户Connection conn = ds.getConnection();System.out.println(conn); //没有下面close的话,5个连接6个人拿超过2s,会发生timed out报错if(i == 3){ //i=3打印了下又还给连接池,所以i=3打印了两次。 conn.close(); //验证了确实连接还给连接池}}}
}
5个连接6个人拿是不够的。如下最后@2d…打印了2次并且没有发生timed out连接超时错误。
15.druid连接池:自动ds.set
package com.itheima05.druid;
import com.alibaba.druid.pool.DruidDataSource;
import com.alibaba.druid.pool.DruidDataSourceFactory;
import javax.sql.DataSource;
import java.io.IOException;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Properties;public class DruidDemo {public static void main(String[] args) throws Exception {
// method01(); //如下配置文件的方式InputStream is = DruidDemo.class.getClassLoader().getResourceAsStream("druid.properties");Properties p = new Properties();p.load(is); DataSource ds = DruidDataSourceFactory.createDataSource(p); //自动解析.properties文件String sql = "select * from account"; Connection conn = ds.getConnection(); //获取连接PreparedStatement pstm = conn.prepareStatement(sql);ResultSet resultSet = pstm.executeQuery();while(resultSet.next()){String name = resultSet.getString("name");System.out.println(name + "-++");}conn.close(); //将连接还给连接池}//111111111111111111111111111111111111111111111111111111111111111111111111private static void method01() throws SQLException {DruidDataSource ds = new DruidDataSource();ds.setDriverClassName("com.mysql.jdbc.Driver");ds.setUrl("jdbc:mysql:///day05");ds.setUsername("root");ds.setPassword("1234");String sql = "select * from account"; Connection conn = ds.getConnection(); PreparedStatement pstm = conn.prepareStatement(sql);ResultSet resultSet = pstm.executeQuery();while(resultSet.next()){String name = resultSet.getString("name");System.out.println(name + "--");}conn.close();// 将连接还给连接池
// ds.close(); // 销毁 //实际开发服务器不关,连接池不会销毁}
}
//druid.properties文件,如下key固定写法
driverClassName=com.mysql.jdbc.Driver
url=jdbc:mysql:///day05
username=root
password=1234
封装druid连接池工具类:ds = DruidDataSourceFactory。File-New-Project-Java。
package com.itheima.utils;
import com.alibaba.druid.pool.DruidDataSourceFactory;
import javax.sql.DataSource;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.Properties;public class JdbcUtil {private static DataSource ds; //下面getConn()也能访问到static{ //静态代码块只运行一次try {Properties p = new Properties();InputStream is = JdbcUtil.class.getClassLoader().getResourceAsStream("druid.properties"); p.load(is); ds = DruidDataSourceFactory.createDataSource(p); //DataSource ds = 移到最上面了} catch (Exception e) {e.printStackTrace();}}public static DataSource getDs() { //属性私有化后提供对外公开的方法return ds;}public static Connection getConn() throws SQLException {
// Connection connection = ds.getConnection();
// return connection;return ds.getConnection(); //等同上面两行}public static void release(AutoCloseable... ios){for (AutoCloseable io : ios) {if(io != null){try {io.close();} catch (Exception e) {e.printStackTrace();}}}}
}
package com.itheima.utils;
import org.junit.Test;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
//测试上面JdbcUtil类
public class TestDemo {@Testpublic void method01() throws SQLException {String sql = "select * from account"; Connection conn = JdbcUtil.getConn();PreparedStatement pstm = conn.prepareStatement(sql);ResultSet resultSet = pstm.executeQuery();while(resultSet.next()){String name = resultSet.getString("name");System.out.println(name);}JdbcUtil.release(resultSet,pstm,conn); //注意: conn的close是将连接还给连接池}
}
如下是数据库中name这一列,不是.properties文件的key。
16.execute/update方法:template =
package com.itheima01.template;
import com.itheima.utils.JdbcUtil;
import org.junit.Test;
import org.springframework.jdbc.core.JdbcTemplate;
import javax.sql.DataSource;
/*
* JdbcTemplate:是spring的框架的一部分,spring框架是工具箱。作用: 简化jdbc代码编写
* 使用:1. 数据库的操作:DCMQ
* 2. 核心类: JdbcTemplate。构造方法:JdbcTemplate(DataSource ds)
* 核心方法: A. void execute : 理论上可以执行任意sql,适合执行DDL,因为void无返回值
* B. int update : 适合执行DML
* C. 多种多样 query : 适合执行DQL,返回多种多样
*/
public class TemplateDemo01 {@Testpublic void execute(){String sql = "create table student(id int primary key auto_increment,name varchar(20),age int)";DataSource ds = JdbcUtil.getDs(); //拿到连接池JdbcTemplate template = new JdbcTemplate(ds); template.execute(sql); //无返回值System.out.println("执行结束");}@Testpublic void update01(){String sql = "insert into student values(null,?,?),(null,?,?)";JdbcTemplate template = new JdbcTemplate(JdbcUtil.getDs());/** int update(String sql, Object... args)* Object... args:* 1. Object原因是参数类型是不确定的 -> Object* 2. ... 原因是参数个数不确定* 返回值: 被影响的行数*/int count = template.update(sql, "zs", 18, "ls", 19);System.out.println(count); //2}@Testpublic void update02(){String sql = "update student set age = ? where id = ?";JdbcTemplate template = new JdbcTemplate(JdbcUtil.getDs()); Object[] args = {99,1}; //可变参数本质是数组int update = template.update(sql, args); System.out.println(update);}
}
17.queryForXX/query方法:Map.Entry < String, Object > ,Map < String, Object > 两个数据类型
一行map是一个对象,query方法用的是多个对象这个。
package com.itheima01.template;
import com.itheima.utils.JdbcUtil;
import org.junit.Test;
import org.springframework.dao.DataAccessException;
import org.springframework.jdbc.core.JdbcTemplate;
import java.util.List;
import java.util.Map;
import java.util.Set;
/*
* C. 多种多样 query : 适合执行DQL
* 1. queryForXX : XX表示返回值类型
* a. queryForObject
* b. queryForMap
* c. queryForList
* 2. query(RowMapper 行映射器)
*/
public class TemplateDemo02 {JdbcTemplate template = new JdbcTemplate(JdbcUtil.getDs());@Testpublic void queryForObject01(){String sql = "select count(*) from student";/** <T> T queryForObject(String sql, Class<T> requiredType)* requiredType : 返回值类型 -> Class对象** EmptyResultDataAccessException : 空结果异常* 查询不到任何数据,会报这个错*/Integer count = template.queryForObject(sql, Integer.class);System.out.println(count);}@Testpublic void queryForObject02(){String sql = "select name from student where id = ?";String s = null;try {s = template.queryForObject(sql, String.class,3); //3传入上面?} catch (DataAccessException e) {e.printStackTrace();System.out.println("查询不到任何结果");}System.out.println(s);}@Testpublic void queryForMap(){String sql = "select * from student where id = ?";Map<String, Object> map = template.queryForMap(sql, 1);
// System.out.println(map); //{id=1,name=zs,age=99}Set<Map.Entry<String, Object>> entrySet = map.entrySet();for (Map.Entry<String, Object> entry : entrySet) { //一条String key = entry.getKey();Object value = entry.getValue();System.out.println(key + "=" + value); //竖着打印id=1 name=zs age=99}}@Testpublic void queryForList(){String sql = "select * from student";List<Map<String, Object>> list = template.queryForList(sql); for (Map<String, Object> map : list) {System.out.println(map); //{id=1,name=zs,age=99} 换行 {id=2,name=ls,age=19}}}
}
package com.itheima01.template;
/*
* JavaBean三要素(必须要有):
* 1. private属性,属性名和表中字段名是一致的!!! 都是引用类型(因为数据库中空为null,不是0)
* 2. public get set方法
* 3. public 空参构造
*/
public class Student {private Integer id;private String name;private Integer age;@Overridepublic String toString() {return "Student{" +"id=" + id +", name='" + name + '\'' +", age=" + age +'}';}public Integer getId() {return id;}public void setId(Integer id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}public Integer getAge() {return age;}public void setAge(Integer age) {this.age = age;}
}
package com.itheima01.template;
import com.itheima.utils.JdbcUtil;
import org.junit.Test;
import org.springframework.jdbc.core.BeanPropertyRowMapper;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.RowMapper;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;public class TemplateDemo03 {JdbcTemplate template = new JdbcTemplate(JdbcUtil.getDs());@Testpublic void query01(){String sql = "select * from student"; /** List<T> query(String sql, RowMapper<T> rm)* RowMapper : 行映射器 (接口)。方法参数中有接口类型, 那么调用的时候必须传入接口的实现类对象*/RowMapper<Student> rowMapper = new RowMapper<Student>() {/** 如下Student mapRow(ResultSet resultSet, int i) 映射行: resultSet转换为Student * 1. resultSet: 结果集(每行)* 2. i: 当前的行索引(没什么用)*/@Overridepublic Student mapRow(ResultSet resultSet, int i) throws SQLException {String name = resultSet.getString("name");int id = resultSet.getInt("id");int age = resultSet.getInt("age");Student s = new Student();s.setId(id);s.setName(name);s.setAge(age);System.out.println(i);return s;}}; // RowMapper行映射器 像 动态代理中 InvocationHandler,mapRow方法像invoke方法List<Student> list = template.query(sql, rowMapper);System.out.println(list); //打印出,list里是student类// [Student{id=1,name='zs',age=99},Student{id=2,name='ls',age=19}] }@Testpublic void query02(){String sql = "select * from student";/*BeanPropertyRowMapper: 类1. RowMapper接口的实现类2. BeanPropertyRowMapper(xx.class); 返回值的泛型*//** BeanPropertyRowMapper (底层反射),思路如下:* 1. 实现RowMapper接口* 2. 重写mapRow方法 : 每行ResultSet -> javaBean* 1. 获取结果集中的数据* 知道结果集有哪些字段 -> 结果集元数据* 值 = resultSet.get(字段);* id值 = id* * 2. 设置到javabean中去 (需要传参: Student.class)* clazz = Student.class //获取类* Student s = clazz.newInstance(); // javabean规范: 默认调用空参构造 * // Student s = new Student(); //等同于上面两行* * //并不知道Student对象有哪些方法,通过反射如下* setIdMethod = clazz.getMethod("setId",int.class); * * //怎么知道Student对象中有setId方法呢?* //因为javabean规范 : 必有set方法。额外要求:set+名字(必须要和表中的字段名一致)* setIdMethod.invoke(s,id值);*/RowMapper<Student> rowMapper = new BeanPropertyRowMapper<>(Student.class);List<Student> list = template.query(sql, rowMapper);System.out.println(list); //打印出同query01()}
}
相关文章:

【database1】mysql:DDL/DML/DQL,外键约束/多表/子查询,事务/连接池
文章目录 1.mysql安装:存储:集合(内存:临时),IO流(硬盘:持久化)1.1 服务端:双击mysql-installer-community-5.6.22.0.msi1.2 客户端:命令行输入my…...

模拟木马程序自动运行:Linux下的隐蔽攻击技术
模拟木马程序自动运行:Linux下的隐蔽攻击技术 在网络安全领域,木马程序是一种常见的恶意软件,它能够悄无声息地在受害者的系统中建立后门,为攻击者提供远程访问权限。本文将探讨攻击者如何在Linux系统中模拟木马程序的自动运行&a…...

vuex的配置主要内容
1、state 作用:负责存储数据; 2、getters 作用:state计算属性(有缓存); 3、mutaions 作用:负责同步更新state数据 mutaions是唯一可以修改state数据的方式; 4、actions 作用:负责异步操作&a…...

VBA技术资料MF164:列出文件夹中的所有文件和创建日期
我给VBA的定义:VBA是个人小型自动化处理的有效工具。利用好了,可以大大提高自己的工作效率,而且可以提高数据的准确度。“VBA语言専攻”提供的教程一共九套,分为初级、中级、高级三大部分,教程是对VBA的系统讲解&#…...

linux 简单使用 sftp 和 lftp命令
目录 一. 环境准备二. sftp命令连接到SFTP服务器三. lftp命令3.1 连接FTP和SFTP服务器3.2 将文件从sftp服务器下载到本地指定目录 四. 通过WinSCP命令行从SFTP服务器获取文件到Windows 一. 环境准备 ⏹在安卓手机上下载个MiXplorer,用作SFTP和FTP服务器 官网: htt…...

2.超声波测距模块
1.简介 2.超声波的时序图 3.基于51单片机实现的代码 #include "reg52.h" #include "intrins.h" sbit led1P3^7;//小于10,led1亮,led2灭 sbit led2P3^6;//否则,led1灭,led2亮 sbit trigP1^5; sbit echo…...

C语言之常用标准库介绍
文章目录 1 标准库1.1 诊断assert.h1.2 字符类别测试ctype.h1.3 错误处理errno.h1.4 整型常量limits.h1.5 地域环境locale.h1.6 数学函数math.h1.7 非局部跳转setjmp.h1.8 可变参数表stdarg.h1.9 公共定义stddef.h1.10 输入输出stdio.h1.11 实用函数stdlib.h1.12 日期与时间函数…...

Spring响应式编程之Reactor核心接口
响应式流的核心接口 核心接口包括:Publisher<T>、Subscriber<T>、Subscription 和 Processo<T,R> (1)Publisher<T> Publisher接口代表数据流的生产者,根据收到的请求向Subscriber发布数据。接口定义如…...

【HTTPS云证书部署】SpingBoot部署证书
这里以华为云证书为例。 1. 下载证书 2. 解压 3. 选择.top_Tomcat复制到SpringBoot的Resource/source下 4. 在.properties文件中进行配置 修改key-store和key-store-password...

React的状态提升和组合
React的状态提升 通常,多个组件需要反映相同的变化数据,这时我们建议将共享状态提升到最近的共同父组件中去 示例: 我们写一个关于热水沸腾的组件,当我们在输入框输入的温度大于100度时,文字会显示热水沸腾。这样有…...

示例:推荐一个基于第三方开源控件库DataGridFilter封装的FilterColumnDataGrid,可以像Excel拥有列头筛选器
一、目的:基于第三方开源控件库DataGridFilter封装的FilterColumnDataGrid,可以像Excel拥有列头筛选器,感兴趣的可以去下方链接地址查看开源控件库地址。本控件封装的目的在于将第三方库的皮肤和样式封装到皮肤库中可统一设置样式,…...

Python: create object
# encoding: utf-8 # 版权所有 2024 涂聚文有限公司 # 许可信息查看: # 描述: # Author : geovindu,Geovin Du 涂聚文. # IDE : PyCharm 2023.1 python 3.11 # Datetime : 2024/6/15 18:59 # User : geovindu # Product : PyCharm # Pr…...

OpenSSL命令手册
正文共:999 字 10 图,预估阅读时间:1 分钟 我们前面编译安装了OpenSSL命令工具(CentOS编译安装OpenSSL 3.3.1),这是一个强大的安全套接字层密码库,可以用于实现各种加密和认证协议,如…...

[面试题]MongoDB
[面试题]Java【基础】[面试题]Java【虚拟机】[面试题]Java【并发】[面试题]Java【集合】[面试题]MySQL[面试题]Maven[面试题]Spring Boot[面试题]Spring Cloud[面试题]Spring MVC[面试题]Spring[面试题]MyBatis[面试题]Nginx[面试题]缓存[面试题]Redis[面试题]消息队列[面试题]…...

【Qt笔记①】帮助文档、窗口、按钮、信号和槽、lambda表达式
学习第一天:2024-3-9 文章目录 Qt creator 快捷键帮助文档默认生成的main.cpp逐行解释核心类帮助文档的查阅方法-①代码创建按钮第一个第二个对窗口的其他设置 对象树窗口坐标系信号和槽(优点:松散耦合)帮助文档的查阅方法-②找信…...

【pytorch05】索引与切片
索引 a[0,0]第0张图片的第0个通道 a[0,0,2,4]第0张图片,第0个通道,第2行,第4列的像素点,dimension为0的标量 选择前/后N张图片 a[:2,:1,:,:].shape前两张图片,第1个通道上的所有图片的数据 a[:2,1:,:,:].shape前两张…...

ECharts 蓝色系-荧光图标折线图01案例
ECharts 蓝色系-荧光图标折线图01案例 图表意义 本折线图案例展示了一周内不同路线的使用情况或数据统计。通过折线的上升和下降,可以直观地观察到每条路线的流量或数据变化趋势,从而进行分析和决策。 效果预览 效果图展示不同路线的数据统计和个性化…...

使用消息中间件实现系统间的异步通信和解耦
✨✨谢谢大家捧场,祝屏幕前的小伙伴们每天都有好运相伴左右,一定要天天开心哦!✨✨ 🎈🎈作者主页: 喔的嘛呀🎈🎈 ✨✨ 帅哥美女们,我们共同加油!一起进步&am…...

【QML】用 Image(QQuickPaintedItem) 显示图片
大体功能: 频繁地往界面推送图片,帧率达到视频效果。捕获画布上的鼠标事件和键盘事件。 代码如下: // DrawImageInQQuickPaintedItem.pro 代码如下: QT quick# You can make your code fail to compile if it uses deprecated…...

C++抽象类
C中抽象类 1.抽象类概念1.1、抽象类如何使用1.2、抽象类规定 2.抽象类代码示例2.1、抽象类2.2、子类12.3、子类22.4、程序入口 1.抽象类概念 C是一门面向对象的编程语言,而所有的对象都是通过类来描述的,如果一个类没有足够的信息来描述一个具体的对象&…...

计算机网络 —— 应用层(DHCP)
计算机网络 —— 应用层(DHCP) 什么是DHCPDHCP工作过程DHCP DISCOVERDHCP OFFERDHCP RQUESTDHCP ACK DHCP租约机制中继代理工作原理功能与优势 我们今天来计网的DHCP: 什么是DHCP DHCP(Dynamic Host Configuration Protocol&…...

Linux ComfyUI安装使用;Stable Diffusion 3使用
1、Linux ComfyUI安装使用 参考: https://zhuanlan.zhihu.com/p/689021495 安装步骤: ## 1、下载ComfyUI git clone https://github.com/comfyanonymous/ComfyUI ## 2、进入ComfyUI,安装依赖包 cd ComfyUI pip install -r requirements.txt ## 3\安装插件 cd custom_nodes…...

JavaScripts数组里的对象排序的24个方法
1. 使用 Array.prototype.sort() 这是最基本、也是最常用的方法。sort() 方法会原地修改数组,并返回排序后的数组。你需要传入一个比较函数来定义排序逻辑。 const array [{ name: Alice, age: 25 },{ name: Bob, age: 22 },{ name: Charlie, age: 30 } ];// 按照…...

Mongodb介绍及window环境安装
本文主要内容为nosql数据库-MongoDB介绍及window环境安装。 目录 什么是MongoDB? 主要特点 MongoDB 与Mysql对应 安装MongoDB 下载MongoDB 自定义安装 创建目录 配置环境变量 配置MongoDB服务 服务改为手动 启动与关闭 安装MongoDB Shell 下载安装包 …...

Spring响应式编程之Reactor核心组件
Reactor核心组件 Flux和Mono组件(1)Flux组件(2)Mono组件 Flux和Mono组件 Reactor 框架提供了两个核心组件来发布数据,分别是 Flux 和 Mono 组件。两者都是实现Publisher接口的高级抽象,可以说是应用程序开…...

动手学深度学习(Pytorch版)代码实践 -计算机视觉-37微调
37微调 import os import torch import torchvision from torch import nn import liliPytorch as lp import matplotlib.pyplot as plt from d2l import torch as d2l# 获取数据集 d2l.DATA_HUB[hotdog] (d2l.DATA_URL hotdog.zip,fba480ffa8aa7e0febbb511d181409f899b9baa5…...

视频监控平台:支持交通部行业标准JT/T905协议(即:出租汽车服务管理信息系统)的源代码的函数和功能介绍及分享
目录 一、视频监控平台介绍 (一)概述 (二)视频接入能力介绍 (三)功能介绍 二、JT/T905协议介绍 (一)概述 (二)主要内容 1、设备要求 2、业务功能要求…...

【jenkins1】gitlab与jenkins集成
文章目录 1.Jenkins-docker配置:运行在8080端口上,机器只要安装docker就能装载image并运行容器2.Jenkins与GitLab配置:docker ps查看正在运行,浏览器访问http://10....:8080/2.1 GitLab与Jenkins的Access Token配置:不…...

边缘计算设备有哪些
边缘设备是指那些位于数据源附近,能够执行数据处理、分析和决策的计算设备。这些设备通常具有一定的计算能力、存储能力和网络连接能力,能够减少数据传输到云端的需要,从而降低延迟、节省带宽并提高数据处理的效率。以下是一些常见的边缘设备…...

C++初学者指南第一步---7.控制流(基础)
C初学者指南第一步—7.控制流(基础) 文章目录 C初学者指南第一步---7.控制流(基础)1.术语:表达式/语句Expressions表达式Statements语句 2.条件分支3.Switching(切换):基于值的分支4.三元条件运算符5.循环迭代基于范围的循环 C…...