- 表关系设计
- 外键:用于建立关系的字段称为外键
- 1对1关系
- 有AB两张表,A表中一条数据对应B表中一条数据,同时B表中一条数据也对应A表中的一条数据
- 应用场景:为了提高查询效率,把原有的一张表查分成两张表,如:商品表和商品详情表,用户表和用户信息扩展表
- 有AB两张表,A表中一条数据对应B表中一条数据,同时B表中一条数据也对应A表中的一条数据
- 1对多关系
- 有AB两张表,A表中一条数据对应B表中多条数据,同时B表中一条数据对应A表中的一条数据
- 应用场景:员工表和部门表,商品表和商品分类表,用户表和地址表
- 有AB两张表,A表中一条数据对应B表中多条数据,同时B表中一条数据对应A表中的一条数据
- 多对多关系
- 有AB两张表,A表中一条数据对应B表中多条数据,同时B表中一条数据也对应A表中的多条数据
- 应用场景:用户表和权限表,老师表和学生表
- 有AB两张表,A表中一条数据对应B表中多条数据,同时B表中一条数据也对应A表中的多条数据
- 如何建立关系:额外创建关系表,在关系表中添加两个外键指向另外两个表的主键
- 外键:用于建立关系的字段称为外键
-
数据库范式
- 第一范式(1NF)
- 字段唯一值唯一
- 由基本类型构成,包括
- 整型、实数、字符型、逻辑型、日期型、其他类型
- 整型、实数、字符型、逻辑型、日期型、其他类型
- 字段唯一值唯一
- 第二范式(2NF)
- 数据库表满足第一范式
- 数据库每张表均有主键
- 单字段主键
- 联合主键
2个或2个以上的字段共同组成的注解- 不能存在联合主键中某个主键字段决定非主键字段的情况如:表中有A、B、C、D、E五个字段若A与B为联合主键(A,B)如有A决定C的情况(A>C)则不符合2NF
- 不能存在联合主键中某个主键字段决定非主键字段的情况如:表中有A、B、C、D、E五个字段若A与B为联合主键(A,B)如有A决定C的情况(A>C)则不符合2NF
- 单字段主键
- 数据库表满足第一范式
- 第三范式(3FN)
- 满足第二范式
- 非主键字段不能决定其他非主键字段(没有依赖关系)
如:表中有A、B、C、D、E五个字段;若A为主键,如有C决定D的情况(C——>D)则不符合3NF
- 满足第二范式
- 反三范式
- 没有冗余的数据库未必是最好的数据库,有时为了提高运行效率,提高读性能,就必须降低范式标准,适当保留冗余数据。具体做法是: 在概念数据模型设计时遵守第三范式,降低范式标准的工作放到物理数据模型设计时考虑。降低范式就是增加字段,减少了查询时的关联,提高查询效率,因为在数据库的操作中查询的比例要远远大于DML【(Data Manipulation Language)语句数据操纵语句,用于添加、删除、更新和查询数据库记录,并检查数据完整性的比例。】但是反范式化一定要适度,并且在原本已满足三范式的基础上再做调整的。
- 没有冗余的数据库未必是最好的数据库,有时为了提高运行效率,提高读性能,就必须降低范式标准,适当保留冗余数据。具体做法是: 在概念数据模型设计时遵守第三范式,降低范式标准的工作放到物理数据模型设计时考虑。降低范式就是增加字段,减少了查询时的关联,提高查询效率,因为在数据库的操作中查询的比例要远远大于DML【(Data Manipulation Language)语句数据操纵语句,用于添加、删除、更新和查询数据库记录,并检查数据完整性的比例。】但是反范式化一定要适度,并且在原本已满足三范式的基础上再做调整的。
- 还有其他范式,不一一说明,其他百度看吧
- 第一范式(1NF)
- JDBC
- jdbc全称是java数据库连接(Java Database Connectivity),是一套用于执行sql语句的java API。应用程序可通过这套API连接到关系型数据库,并使用sql语句
- 作用
- 相当于统一了各个数据库的接口,使得代码的通用性更强。
- 相当于统一了各个数据库的接口,使得代码的通用性更强。
- JDBC常用API
- 位于java.sql包中,该包定义了一系列访问数据库的接口和类
- Drive接口
- 是所有JDBC驱动程序必实现的接口,该接口提供给数据库厂商使用
- 是所有JDBC驱动程序必实现的接口,该接口提供给数据库厂商使用
- 注意:编写JDBC程序时,必须要把所使用的数据库驱动程序或类库加载到项目的classpath中(这里指mysql驱动jar包).
- DriverManager类
- 用于加载JDBC驱动并且创建与数据库的连接
- DriverManager类中有两个比较重要的静态方法
- static void registerDriver(Driver)
- 用于向DriverManager中注册给定的JDBC驱动程序;不建议用这种,因为Driver类的源码中,已经在静态代码块中完成了数据库驱动的注册。所以为了避免数据库被重复注册,只需在程序中使用Class.forName()方法加载驱动类即可。
- 用于向DriverManager中注册给定的JDBC驱动程序;不建议用这种,因为Driver类的源码中,已经在静态代码块中完成了数据库驱动的注册。所以为了避免数据库被重复注册,只需在程序中使用Class.forName()方法加载驱动类即可。
- static Connection getConnection(String url,String user,String pwd)
- 用于建立和数据库的连接,并返回表示连接的Connection对象
- 用于建立和数据库的连接,并返回表示连接的Connection对象
- static void registerDriver(Driver)
- 用于加载JDBC驱动并且创建与数据库的连接
- Connection接口
- 代表Java程序和数据库的连接,只有获得该连接对象后,才能访问数据库,操作数据库。
- 常用方法
- DatabaseMetaData_getMetaData()
- 用于返回表示数据库的元数据的DatabaseMetaData对象
- 用于返回表示数据库的元数据的DatabaseMetaData对象
- Satement createStatement()
- 用于创建一个Statement对象将sql语句发送到 数据库
- 用于创建一个Statement对象将sql语句发送到 数据库
- PrepareStatement prepareStatement(String sql)
- 用于创建一个PreparedStatement对象来将参数化的sql语句发送到数据库
- 用于创建一个PreparedStatement对象来将参数化的sql语句发送到数据库
- CallableStatement prepareCall(String sql)
- 用于创建一个CallableStatement对象来调用数据库存储过程
- 用于创建一个CallableStatement对象来调用数据库存储过程
- DatabaseMetaData_getMetaData()
- 代表Java程序和数据库的连接,只有获得该连接对象后,才能访问数据库,操作数据库。
- Statement接口
- 用于执行静态的sql语句,并返回一个结果对象。Statement接口对象可以通过Connection实例的createStatement()方法获得,该对象会把静态sql语句发送到数据库中编译执行,然后返回数据库的处理结果。
- 常用方法
- boolean execute(String sql)
- 用于执行各种sql语句,改方法返回一个boolean类型的值,如果为true,表示所执行的sql语句有查询结果,可通过Statement的getResultSet()方法获得查询结果
- 用于执行各种sql语句,改方法返回一个boolean类型的值,如果为true,表示所执行的sql语句有查询结果,可通过Statement的getResultSet()方法获得查询结果
- int executeUpdate(String sql)
- 用于执行sql中的insert、update和delete语句。该方法返回一个int类型的值,表示数据库中受该sql语句影响的记录条数
- 用于执行sql中的insert、update和delete语句。该方法返回一个int类型的值,表示数据库中受该sql语句影响的记录条数
- ResultSet executeQuery(String sql)
- 用于执行sql中的select语句,该方法返回一个表示查询结果的ResultSet对象
- 用于执行sql中的select语句,该方法返回一个表示查询结果的ResultSet对象
- boolean execute(String sql)
- 用于执行静态的sql语句,并返回一个结果对象。Statement接口对象可以通过Connection实例的createStatement()方法获得,该对象会把静态sql语句发送到数据库中编译执行,然后返回数据库的处理结果。
- PreparedStatement接口
- 封装了JDBC执行SQL语句的方法,完成java程序执行SQL语句的操作。实际开发过程中往往将程序中变量作为SQL语句的查询条件,而使用Statement接口操作这些SQL语句过于繁琐,且存在安全问题,针对这一问题,JDBC提供扩展的PreparedStatement接口
- 常用方法
- int executeUpdate()
- 在PreparedStatement对象中执行SQL语句,该语句必须是一个DML语句或者是无返回内容的SQL语句,如DDL语句
- 在PreparedStatement对象中执行SQL语句,该语句必须是一个DML语句或者是无返回内容的SQL语句,如DDL语句
- ResultSet executeQuery()
- 在PreparedStatement对象中执行SQL查询,该方法返回的是ResultSet对象
- 在PreparedStatement对象中执行SQL查询,该方法返回的是ResultSet对象
- void setlint(int parameterindex,int x)
- 将指定参数设置为给定的int值
- 将指定参数设置为给定的int值
- void setFloat(int parameterindex,float x)
- 将指定参数设置为给定的float值
- 将指定参数设置为给定的float值
- void setString(int parameterindex,String x)
- 将指定参数设置为给定String值
- 将指定参数设置为给定String值
- void setDate(int parameterindex,Data x)
- 将指定参数设置为给定的Date值
- 将指定参数设置为给定的Date值
- void addBatch()
- 将一组参数添加到此PreparedStatement对象的批处理命令中
- 将一组参数添加到此PreparedStatement对象的批处理命令中
- void setCharacterStream(int parameterindex,java.io.Reader reader,int length)
- 将指定的输入流写入数据库的文本字段
- 将指定的输入流写入数据库的文本字段
- void setBinaryStream(int parameterindex,java.io.inputStream x,int length)
- 将二进制的输入流数据写入到二进制字段中
- 将二进制的输入流数据写入到二进制字段中
- 注意:
- setDate()方法可以设置日期内容,但参数Date的类型是java.sql.Date而不是java.util.Date。
- setDate()方法可以设置日期内容,但参数Date的类型是java.sql.Date而不是java.util.Date。
- int executeUpdate()
- 封装了JDBC执行SQL语句的方法,完成java程序执行SQL语句的操作。实际开发过程中往往将程序中变量作为SQL语句的查询条件,而使用Statement接口操作这些SQL语句过于繁琐,且存在安全问题,针对这一问题,JDBC提供扩展的PreparedStatement接口
- ResultSet接口
- 用于保存JDBC执行查询时返回的结果集,该结果集封装在一个逻辑表格中。在ResultSet接口内部有一个指向表格数据行的游标(或指针)。ResultSet对象初始化时,游标在表格的第一行之前,调用next()方法可将游标移动到下一行。如果下一行没有数据则返回false。在应用程序中经常使用next()方法作为while循环的条件来迭代ResultSet结果集。
- 常用方法
- String getString(int columnindex)
- 用于获取指定字段的String类型的值,参数columnindex代表字段的suoyin。
- 用于获取指定字段的String类型的值,参数columnindex代表字段的suoyin。
- String getString(String columnName)
- 用于获取指定字段的String类型的值,参数columnName代表字段的名称。
- 用于获取指定字段的String类型的值,参数columnName代表字段的名称。
- int getInt(int columnIndex)
- 用于获取指定字段int类型的值,参数columIndex代表字段的索引
- 用于获取指定字段int类型的值,参数columIndex代表字段的索引
- int getInt(String columnName)
- 用于获取指定字段int类型的值,参数colunIndex代表字段的名称
- 用于获取指定字段int类型的值,参数colunIndex代表字段的名称
- Date getDate(int columnIndex)
- 用于获取指定字段的Date类型的值,参数columnIndex代表字段的索引
- 用于获取指定字段的Date类型的值,参数columnIndex代表字段的索引
- Date getDate(String columnName)
- 用于后去指定字段的Date类型的值,参数columnName代表字段的名称
- 用于后去指定字段的Date类型的值,参数columnName代表字段的名称
- boolean next()
- 将游标从当前位置向下移一行
- 将游标从当前位置向下移一行
- boolean absolute(int row)
- 将游标移动到此 ResultSet对象的指定行
- 将游标移动到此 ResultSet对象的指定行
- void afterLast()
- 将游标移动到此ResultSet对象的末尾,即最后一行之后
- 将游标移动到此ResultSet对象的末尾,即最后一行之后
- void beforeFirst()
- 将游标移动到此ResultSet对象的开头,即第一行之前
- 将游标移动到此ResultSet对象的开头,即第一行之前
- boolean previous()
- 将游标移动到此ResultSet对象的上一行
- 将游标移动到此ResultSet对象的上一行
- boolean last()
- 将游标移动到此ResultSet对象的最后一行
- 将游标移动到此ResultSet对象的最后一行
- String getString(int columnindex)
- 注意
- 字段的索引是从1开始编号的,程序既可以用字段名称来获取指定数据,也可以通过字段的索引获取。采用哪种getXxx()方法取决于字段的数据类型。
- 字段的索引是从1开始编号的,程序既可以用字段名称来获取指定数据,也可以通过字段的索引获取。采用哪种getXxx()方法取决于字段的数据类型。
- 用于保存JDBC执行查询时返回的结果集,该结果集封装在一个逻辑表格中。在ResultSet接口内部有一个指向表格数据行的游标(或指针)。ResultSet对象初始化时,游标在表格的第一行之前,调用next()方法可将游标移动到下一行。如果下一行没有数据则返回false。在应用程序中经常使用next()方法作为while循环的条件来迭代ResultSet结果集。
- 位于java.sql包中,该包定义了一系列访问数据库的接口和类
- 实现一个JDBC程序
- 1.加载并注册数据库驱动
- Class.forName("DriverName);或者DriverManager.registerDriver(Driver driver);不建议用后者
- Class.forName("DriverName);或者DriverManager.registerDriver(Driver driver);不建议用后者
- 2.通过DriverManager类获取数据库连接
- Connection conn=DriverManager.getConnection(String url,String user,String pwd);
- url书写:jdbc:mysql://数据库主机地址:端口/数据库名
- Connection conn=DriverManager.getConnection(String url,String user,String pwd);
- 3.通过Connection对象获取Statement对象
- 以创建基本Statement对象为例:Statement stmt=conn.createStatement();
- 以创建基本Statement对象为例:Statement stmt=conn.createStatement();
- 4.使用Statement执行SQL语句
- 例:ResultSet rs=stmt.executeQuery(sql);
//执行SQL语句获得结果集
- 例:ResultSet rs=stmt.executeQuery(sql);
- 5.操作ResultSet结果集
- 如果执行的SQL语句是查询语句,执行结果将返回一个ResultSet对象,该对象保存了SQL语句查询的结果。可以通过该对象取出查询的结果。
- 如果执行的SQL语句是查询语句,执行结果将返回一个ResultSet对象,该对象保存了SQL语句查询的结果。可以通过该对象取出查询的结果。
- 6.关闭连接,释放资源
- 每次操作完数据库后都要关闭数据库连接,释放资源,包括关闭ResultSet、Statement和Connection等资源。
- 每次操作完数据库后都要关闭数据库连接,释放资源,包括关闭ResultSet、Statement和Connection等资源。
- 注意:
- 当数据库资源使用完毕后,一定要记得释放资源。把释放资源的操作应写在finally代码块中。
- Class.forName有一个装载类对象的作用。装载就包括了初始化的操作。JDBC规范要求Driver类在使用前必须向DriverManger注册自己。注册过程在Driver类的静态类已经实现。也就是说只要类被加载,就完成了向驱动管理器的注册。
- 当数据库资源使用完毕后,一定要记得释放资源。把释放资源的操作应写在finally代码块中。
- 1.加载并注册数据库驱动
- jdbc全称是java数据库连接(Java Database Connectivity),是一套用于执行sql语句的java API。应用程序可通过这套API连接到关系型数据库,并使用sql语句
- 代码练习
-
1 package star; 2 import java.sql.*; 3 public class pres { 4 public static void main(String[] args){ 5 Statement stem=null; 6 ResultSet rs=null; 7 Connection conn=null; 8 try { 9 //1.注册数据库驱动 10 Class.forName("com.mysql.jdbc.Driver"); 11 //2.通过DriverManager获取数据库连接,语法jdbc:mysql://数据库地址:端口:数据库名。。?useSSL=false是出现警告信息时加的(不建议在没有服务器身份验证的情况下建立SSL连接) 12 conn =DriverManager.getConnection("jdbc:mysql://localhost:3306/star?useSSL=false","root","root"); 13 //3.通过Connection后去Statement对象 14 stem = conn.createStatement(); 15 //用Statement的executeUpdate方法插入下数据试试//insert into users(name,password,email,birthday) values('ac','123456','ac@sina.com','1978-08-28') 16 //delete from users where name='ac' 17 int jieguo =stem.executeUpdate("delete from users where name='ac'"); 18 //因为上面那个方法返回int类型表示修改的条数,所以加个成功否判断 19 if(jieguo!=0){ 20 System.out.println("数据修改成功"); 21 }else { 22 System.out.println("数据修改失败"); 23 } 24 //4.使用Statement执行sql语句 25 String sql="select * from users"; 26 //执行select语句返回一个表示查询结果的ResultSet对象 27 rs=stem.executeQuery(sql); 28 if(rs!=null){ 29 System.out.println("数据表查询成功"); 30 }else { 31 System.out.println("数据表查询失败"); 32 } 33 //5.操作ResultSet结果集 34 System.out.println("id| name | password"+"| email | birthday"); 35 while (rs.next()){ 36 int id=rs.getInt("id");//通过列名获取指定字段的值 37 String name =rs.getString("name"); 38 String psw=rs.getString("password"); 39 String email=rs.getString("email"); 40 Date birthday=rs.getDate("birthday"); 41 System.out.println(id+"|"+name+" | "+psw+" | "+email+" | "+birthday); 42 } 43 }catch (Exception e){ 44 e.printStackTrace(); 45 }finally { 46 { 47 //6.回收数据库资源 48 if(rs!=null){ 49 try{ 50 rs.close(); 51 }catch(SQLException e){ 52 e.printStackTrace(); 53 } 54 rs=null; 55 } 56 57 58 if(stem!=null){ 59 try { 60 stem.close(); 61 }catch (SQLException e){ 62 e.printStackTrace(); 63 } 64 stem=null; 65 } 66 if (conn!=null){ 67 try{ 68 conn.close(); 69 }catch (SQLException e){e.printStackTrace();} 70 conn=null; 71 } 72 } 73 } 74 75 } 76 }
-
相关文章
- 02-185.表关系设计、范式、JDBC
- 02-18关系型数据库设计:三大范式的通俗理解
- 02-18数据库表设计五大范式所解决的问题
- 02-18数据库表设计三范式
- 02-182021.1.5.- 外键约束 - 数据库与表之间的关系 - 三大范式 - 多表查询 - 事务 - DCL
- 02-18数据库表中多对多关系怎么设计?
- 02-18关系型数据库设计:三大范式的通俗理解
- 02-18关系数据库设计一般方法 范式及完整性
- 02-18关系数据库的范式和反范式设计
- 02-18数据库表设计时一对一关系存在的必要性 数据库一对一、一对多、多对多设计 面试逻辑题3.31 sql server 查询某个表被哪些存储过程调用 DataTable根据字段去重 .Net Core Cors中间件解析 分析MySQL中哪些情况下数据库索引会失效