MySQL数据库与JDBC编程基础

时间:2021-11-27 09:14:01

(1)由于Java语言的跨平台性,所以使用JDBC编写的程序不仅可以实现跨数据库,还可以跨平台,具有非常优秀的可移植性。
(2)程序使用JDBC API以统一的方式来连接不同的数据库,然后通过Statement对象来执行标准的 SQL语句,并可以获得SQL语句访问数据库的结果。
(3)JDBC 全称是Java Database Connectivity,即Java数据库连接,它是一种可以执行的SQL语句的Java API。程序可以通过JDBC API连接到关系数据库,并且使用结构化查询语言来完成对数据库的查询、更新。
(4)与其他数据库编程环境相比,JDBC为数据库开发提供了标准的API,所以用JDBC开发的数据库可以跨平台运行,而且可以跨数据库(如果全部使用标准的SQL),也就是说,如果使用JDBC开发一个数据库应用,在Windows Unix 都可以运行,既可以使用MySQL数据库,也可以使用Oracle数据库,程序无需进行任何修改。
(5)Sun提供的JDBC可以完成以下三个基本工作:
建立与数据库的连接;
执行SQL语句
获得SQL语句的执行结果。

——————————————————————————————————
JDBC驱动程序:
(1)数据库驱动程序是JDBC与数据库之间的转换层,数据库驱动程序负责将JDBC调用映射成特定的数据库调用。大部分数据库系统,都有相应的JDBC驱动程序。
(2)还有一种名为ODBC的技术(Open Database Connectivity),即开放数据库连接。ODBC和JDBC很像,
严格来说,应该是JDBC模仿了ODBC的设计,。ODBC也允许应用程序通过一组通用的API访问不同的数据库系统,从而使得基于ODBC的应用程序可以在不同的数据库之间切换,ODBC也需要各种数据库厂商提供相应的驱动程序,而ODBC则负责管理这些驱动程序。
(3)JDBC驱动通常有如下四种类型:
第一种JDBC驱动:称为JDBC-ODBC桥,这种驱动是最早实现的JDBC驱动程序,主要目的是为了快速推广JDBC。这种驱动将JDBC API映射到ODBC API。这种驱动在最新的Java8中已经被删除了
第二种JDBC驱动:直接将JDBC API映射到数据库特定的客户端API,这种数据库包含特定数据库的本地代码,用于访问特定数据库的客户端。
第三种JDBC驱动:支持三层结构的JDBC访问方式,主要用于Applet阶段,通过Applet访问数据库
第四种JDBC驱动:是纯Java的,直接与数据库实例交互,这种驱动是智能的,它知道数据库使用的底层协议。这种驱动是目前最流行的JDBC驱动。
(4)相比较而言,JDBC更加简单。总结起来,JDBC比ODBC多了如下几个优势:
ODBC更复杂,ODBC中有几个命令需要配置很多复杂的选项,而JDBC则采用简单直观的方式来管理连接数据库。
JDBC比ODBC安全性更高,更 易部署。

——————————————————————————————————————————
SQL语法:
(1)SQL语句是对所有的关系数据库都通用的命令语句,而JDBC API只是执行SQL语句的工具,JDBC允许对不同平台、不同数据库采用相同的编程接口来执行SQL语句
——————————————
关系数据库基本概念和MySQL基本命令:
(1)对于关系数据库而言,最基本的数据存储单元就是数据表,因此简单的将数据库想象成大量数据表的集合(当然,数据库绝不仅由数据表组成)
(2)MySQL使用命令来查看当前实例下包含多少个数据库:
show database;
(3)MySQL默认使用分号作为每条命令的结束符,所以每条MySQL命令结束后都应该输入一个英文分号(;)
(4)如果用户需要创建新的数据库,则可以使用如下命令:
create database [IF NOT EXISTS] 数据库名;
(5)如果用户需要删除指定的数据库则可以使用如下命令:
drop database 数据库名;
(6)进入指定数据库可使用如下命令:
drop 数据库名;
(7)进入数据库后,如果要查询该数据库下包含多少个表:
show tables;
(8)如果要查看指定数据表的表结构(详细信息),则可以使用如下命令:
desc 表名;
(9)在MySQL安装目录下有一个bin路径,该路径下包含一个mysql命令,该命令用于启动MySQL命令行客户端,执行的语法如下:
mysql -p -密码 -u 用户名 -h -主机名 –default-character-set=utf8
(10)MySQL数据库通常支持如下两种存储机制。
**MyISAM:这是MySQL早期默认的存储机制,对事务支持不够好。
**InnoDB:提供事务安全的存储机制,InnoDB通过建立行级锁来保证事务完整性,并以Oracle风格的共享锁来处理Select语句,系统默认使用InnoDB机制,如果不想使用InnoDB表,则可以使用skip-innodb选项。
(11)对比两种存储机制,发现InnoDB比MyISAM多了事务支持的功能,而事务支持是JavaEE最重要的特性,因此通常推荐使用InnoDB存储机制,因为系统默认使用InnoDB存储机制。如果需要在建表时显示指定存储机制,则可在标准语法后面添加下面任意一句:
ENGINE=MyISAM 强制使用MyISAM存储机制
ENGINE=InnoDB 强制使用InnoDB存储机制

————————————————————————————————————————————
SQL语句基础:
(1)SQL的全称是 Structured Query Language,也就是结构化查询语言。SQL是操作和检索关系数据库的标准语言,标准的SQL语句可用于操作任何关系数据库。
(2)标准的SQL语句通常可分为如下类型:
**查询语句:主要由select关键字完成,查询语句是SQL语句中最复杂、功能最丰富的语句。
**DML(Data Manipulation Language,数据库操作语言)语句:主要由insert update delete三个关键字完成
**DDL(Data Definition Language,数据库定义语言)语句,主要由create alter drop truncate四个关键字组成。
**DCL(Data Control Language,数据库控制语言)语句,主要由grant revoke两个关键字完成。
**事务控制语句:主要由commit rollback savepoint三个关键字完成。
(3)SQL语句不区分大小写。
————————————————————————————————————
DDL语句:
(1)DDL语句是操作数据库对象的语句,包括创建(create) 删除(drop) 和修改(alter)数据库对象。
(2)最基本的数据库对象是数据表,数据表是存储数据的逻辑单元。但是数据库里还有其他的数据库对象,如数据字典,约束,视图,索引,函数,存储过程,触发器等。因为存在不同的数据库对象,所以create后面可以跟不同的关键字,如建表create table,建索引create index,建视图create view.
(3)创建表的语法:
**标准的建表语法如下:
create table [模式名.] 表名

#可以有多个列定义
columnName1 datatype [dafault expr],
……

上面圆括号中可以包含多个列定义,每个列定义之间用英文逗号隔开,最后一个列定义不需要使用英文逗号,而是直接以括号结束。

(4)建立数据表只是建立表结构,就是指定该数据表有多少列,每列的数据类型,所以建表语句的重点就是圆括号里的列定义,列定义由列名,列类型和可选的参数值组成。如果要指定列的默认值,则使用default关键字。
(5)实例建表语句。
craete table test
(
#整型通常用int
test_id int,
#小数点数
test_price decimal,
#普通长度文本,使用default指定默认值
test_name varchar(255) default ‘xxx’,
#大文本类型
test_desc text,
#图片
test_img blob,
test_date datetime
);

(6)建表时需要指定每列的数据类型,不同数据库所支持的类型不同。
(7)修改表结构的语法:修改表结构使用alter table ,修改表结构包括增加列定义,修改列定义,删除列,重命名列等操作,增加列定义的语法如下:
alter table 表名

可以有多个列定义

 columnName1  datatype [dafault  expr],
......

);

如果只是新增一列,则可以上略圆括号,仅在add后面紧跟一个列定义即可

(8)为数据表增加字段的SQL语句如下:

为scu增加一个scu_id字段,该字段的类型为int

alter table scu
add scu_id int;

为scu数据表增加aaa bbb字段,两个字段的类型都是varchar(255)

alter table scu
(
aaa varchar(255) default ‘xxx’,
bbb varchar(255)
);

注意:SQL语句中的字符串值不是用双引号,而是单引号
**如果数据表中已经有了数据记录,除非给新增的列指定了默认值,否则新增的数据列不可指定非空约束,因为那些已有的记录在新增列上肯定是空。

(8)修改列定义的语法如下:
alter table 表名
modify column_name datatype [dafault expr] [first | after col_name];

上面first或者after col_name指定需要将目标修改到指定位置。

该修改语句每次只能修改一个列定义

实例:

将scu表的scu_id列修改成varchar(255)类型

alter table scu
modify scu_id varchar(255);

将scu表的bbb列修改成int 类型

alter table scu
modify bbb int;

(9)从数据表中删除列的语法比较简单:
alter table 表名
drop column_name

实例:
alter table scu
drop aaa;

上面这些增加修改删除列的语法是标准的SQL语法,对所有的数据库都通用,除此之外,MySQL还提供了两种特殊的语法:重命名数据表和完全改变列定义

重命名数据表的语法如下:
alter table 表名
rename to 新表名

MySQL为alter table提供了change选项,该选项可以改变列名。语法如下:

change old_column_name new_column_name type [default expr] [first | after col_name]
实例:
alter table scu
change bbb ddd int;

(10)删除表的语法:
删除表的语法:drop table 表名;
实例:drop table scu;
删除表的效果如下:
表结构被删除,表对象不再存在
表里的所有数据也被删除
该表所有的相关索引 约束也被删除。
(11)truncate表
对于大部分数据库而言,truncate都被当成DDL处理,truncate称为截断某个表–它的作用是删除表里的全部数据,但是保留表结构。相对于DML里的delete而言,truncate的速度要快很多,而且truncate不像delete可以删除指定的记录,而是删除整个表的记录。

————————————————————————————————

数据库约束:
(1)所有的关系数据库都支持对数据表使用约束,通过约束可以更好的保证数据表里的数据完整性。约束是在表上强行执行的数据校验规则,约束主要用于保证数据库里数据的完整性。除此之外,当表中的数据存在相互依赖性时,可以保护相关的数据不被删除。
(2)大部分数据库支持下面5种完整性约束:
NOT NULL 非空约束,指定某列不能为空
UNIQUE 唯一约束,指定某列或者激烈不能重复
PRIMARY KEY 主键,指定该列的值可以唯一的标识该条记录。
FOREIGN KEY 外键,指定该行记录从属于主表中的一条记录,主要用于保证参照完整性。、
CHECK 检查,指定一个布尔表达式,用于指定该列的值必须满足该表达式。

注意:MySQL不支持CHECK约束

(3)根据约束对数据列的限制,约束分为如下两类:
单列约束:每个约束只约束一列
多列约束:每个约束可以约束多个数据列
(4)为数据表指定约束有如下两个时机。
建表的同时为相应的数据列指定约束
建表后创建,以修改表的方式来增加约束
————————————————————————————————
NOT NULL约束:
(1)非空约束用于确保指定列不允许为空,非空约束是比较特殊的约束,它只能作为列级约束使用,只能使用列级约束语法定义。
SQL中的null值不区分大小写,SQL中的null具有如下特征:
所有数据类型的值都可以是null,包括int float boolean等数据类型。
与Java类似的是,空字符串不等于null,0也不等于null。

如果需要在建表时为指定列指定非空约束,只要在列定义后增加not null即可,
create table scu

#建立了非空约束,这意味着scu_id不能为null
scu_id int not null,
);

也可以在使用alter table修改表时增加或者删除非空约束,SQL命令如下:

增加非空约束

alter table scu
modify scu_jiang varchar(2) not null

取消非空约束

alter table scu
modify scu_name varchar(2) null
取消非空约束,并指定默认值
alter table scu
modify scu_name vaechar(2) default ‘nnn’ null;

————————————————————————————————————————

UNIQUE约束:
(1)唯一约束用于保证列或者指定列组合不允许出现重复值。虽然唯一约束的列不可以出现重复值,但可以出现多个null值(因为在数据库中null不等于null)
(2)同一个表内可建立多个唯一约束,唯一约束可由多列组合而成。当为某列创建唯一约束时,MySQL会为该列相应的创建唯一索引,如果不给唯一约束起名,则默认与列名相同。
(3)唯一约束既可以用列级约束语法建立,也可以使用表级约束语法建立。如果需要为多列建组合约束,或者需要为唯一约束指定约束名,则只能使用表级约束法。
(4)实例:

建表时创建唯一约束,使用列级约束语法建立约束

.create table scu
(
#建立唯一约束,使用列级语法建立约束
scu_name varchar(255) unique
);

(5)如果需要为多列组合建立唯一约束,或者想自行制定约束名,则需要使用表级约束法,格式如下:
[constraint 约束名] 约束定义
既可以放在create table 语句中与列定义并列,也可以放在alter table 语句中使用add关键字来添加约束,SQL语句如下:
create table unique scu
(
#建立的非空约束,意味着scu_id不能为空
scu_id int not null,
scu_name varchar(255),
#使用表级约束法建立唯一约束
unique ( scu_name)
) ;

————————————————————————————————————
PRIMARY约束:
(1)主键约束相当于非空约束和唯一约束,即主键呢约束的列既不允许出现重复值,也不允许出现null值,如果多列组合建立主键约束,则多列里包含的每一列都不能为空,但只要求这些列组合不能重复,主键列的值可以用于唯一的标识表中的一条记录。
(2)每一个表中最多允许有一个主键,但这个主键约束可由多个数据列组成,主键是一个表中能唯一确定一行记录的字段或者字段组合
create table scu
(
#建立主键约束,使用列级语法建立约束
scu_name varchar(255) primary key,
);

create table scu
(

  scu_id   int  not null,
scu_name varchar(255),
#指定主键约束为scu_pri,对大部分数据库有效,但对MySQL无效,主键约束名仍然是PRIMARY
constraint scu_pri primary key(scu_id)

) ;

(3)有很多数据库随主键列都支持一种自动增长的特性,如果某个数据列的类型是整型,而且该列作为主键列,则可指定该列具有自增长功能
MySQL使用auto_increment来设置增长,语法如下

create table scu
(
#建立主键约束,使用自增长
scu_id int auto_increment primary key,
scu_name varchar(255)

);


FOREIGN KEY 约束:
(1)外键约束主要用于保证一个或两个数据表之间的参照完整性,外键是构建于一个表的两个字段或者两个表的两个字段之间的参照关系。外键确保了相关的两个字段的参照关系:子表外键列的值必须在主表被参照列的值范围之内,或者为空。
(2)当主表的记录被子表参照时,主表记录不允许被删除,必须先把子表里参照该记录的所有记录全部删除之后,才能删除主表的该记录。
(3)MySQL支持使用列级约束来建立外键约束,但是这种约束并不会生效,仅仅是为了和标准SQL保持良好的兼容性。如果要想使MySQL中的外键约束生效,则应该使用表级约束法。
实例程序:

为了子表的参照存在,通常应该先建主表

create table teacher
(
teacher_id int auto_increment,
teacher_name varchar(255),
primary key(teacher_id)
);

create table student
(
student_id int auto_increment primary key,
student_name varchar(255),

指定java_teacher参照到teacher中的teacher_id列

  java_teacher   int,

foreign key(java_teacher) references teacher(teacher_id)
);

————————————————————————————————————

索引:
(1)*索引是存放在模式(schema)中的一个数据库对象,虽然索引总是从属于数据库表,但他也和数据库表一样属于数据库对象。创建索引的唯一作用就是加速对表的查询,索引通过使用快速路径访问方法来迅速定位数据,从而减少的磁盘的输出
(2)索引作为数据库对象,在数据字典中独立存放,但不能独立存在,必须从属于某个表;
(3)MySQL使用information_schema数据库里的STATISTICS表来保存该数据库实例中的所有索引信息,用户可以通过查询该表来获取该数据库的索引信息。
(4)创建索引有两种方式:
**自动:当在表上定义主键约束,唯一约束和外键约束时,系统会为该数据列自动创建对应的索引
**手动:用户可以通过create index来创建索引
同理:删除索引也有两种方式
**自动:数据表被删除时,该表上的索引自动被删除
**手动:用户可以通过drop index来删除索引
(5)创建索引的语法格式如下:
create index index_name on table_name (column[,column]);
//下面的索引将会提高employees基于last_name字段的查询速度
create index emp_last_name_idx on employees(last_name);

————————————————————————————————————
DML语句语法:
与DDL操作数据库对象不同,DML主要操作数据表里的数据,使用DML可以完成如下三个任务:
插入新数据
修改已有数据
删除不需要的数据

DML语句由insert into \update\delete from三个命令组成
(1)insert into 语句:
insert into 用于向指定数据表中插入记录。对于标准的SQL语句而言,每次只能插入一条记录。其语法格式如下:
insert into table_name [(column [, column…])] values (value [,value…]);
(2)**执行插入操作时,表名后可以用括号列出所有需要插入值的列名,而values后用括号列出对应需要插入的值
**如果省略了表名后面的括号以及括号里的列名列表,默认将为所有列都插入值,则需要我每一列都指定一个值。如果既不想在表名后列出列名,又不想为所有列都指定值,则可以为那些无法确定值的列分配null。
(3)实例:
insert into teacher (teacher_name) values(‘zhang’);

insert into teacher values(null,’zhang’); 使用null代替主键列的值

(4)根据前面说的外键约束规则:外键列的值必须是被参照列里已有的值,所以像子表插入记录之前,通常应该先向主表中插入记录,否则子表外键列只能是null
insert into student values(null,’张三’,2);

(5)MySQL提供了提供了一种扩展的语法,通过这种扩展的语法可以一次性的插入多条记录。MySQL允许在values后使用多个括号包含多个记录,表示多条记录的多个括号之间以英文逗号隔开:
实例:
insert into teacher values (null,”juji”),(null,”fdes”);

————————————————————————————————————————

update语句:
(1)update语句用于修改数据表的记录,每次可以修改多条记录,通过使用where字句限定修改哪些记录。where是一个条件表达式,该条件表达式类似于Java的if ,只有符合条件的记录才会被修改,没有where字句则意味着where表达式的值总是为true,即该表的所有记录都会被修改,语法格式如下:
update table_name set column1=value1,[,column2=value2]…
[where condition]

使用update语句不仅可以一次修改多条记录,也可以一次修改多列。
(2)实例:下面SQL语句会将表中所有的teacher_name改为 钱钟书
update teacher set teacher_name=”钱钟书”;
也可以修改特定记录:
update teacher set teacher_name=”钱钟书”
where teacher_id>10;
————————————————————————————————————

delete from语句:
(1)delete from语句用于删除指定数据表的记录,使用delete from语句删除时不需要指定列名,因为总是整行的删除。
(2)使用delete from语句可以一次删除多行,删除哪些行采用where字句限定,只删除满足where条件的记录,没有where字句的限定将会把表里的记录全部删除。
(3)delete from语法格式如下:
delete from table_name [where condition];
实例:delete from student where student_id>20;

——————————————————————————————————————————

单表查询:
(1)select语句的功能就是查询数据,select语句是SQL语句中功能最丰富的语句。
(2)select后面的列表用于确定哪些列,where条件用于确定哪些行,只有满足where条件的行才会被选出来;如果没有where条件,则默认选出所有行。如果向选择出所有列,则可使用*号代表所有列。
(3)实例:
选择出teacher中的所有行,所有列的数据:
select * from teacher;
如果增加where条件,则只选出符合where条件的记录
select student_name from student where java_teacher>3;
(4)当使用select语句进行查询时,还可以在select语句中使用算术运算符(+,-,*,/)创建表达式。实例:

查询出teacher_id *3 >4的记录:
select * from teacher where teacher_id * 3> 4;
(5)SQL语句中算术运算符的优先级与Java语言中算术运算符的优先级完全相同。
(6)MySQL中没有提供字符串连接运算符,MySQL使用concat函数进行字符串连接运算。
选择teacher_name和’xx’字符串连接后的结果
select concat(teacher_name,’xx’) from teacher;
(7)对于MySQL而言,如果在算术表达式中使用null,将会导致整个算术表达式返回null;如果在字符串连接中出现null,也会导致连接结果是null。下面语句返回null
select concat(teacher_name,null) from teacher;
(8)如果不希望直接使用列名作为列标题,则可以为数据列或表达式起一个别名,以逗号或as关键字隔开:
select teacher ad MY_ID from teacher;
(9)select默认会把所有符合条件的记录全部选出来,即使两行的记录完全一样。如果想要去除重复行,则可以使用distint关键字从查询结果中清除重复行。
选出所有记录,包括重复行:
select student_name ,java_teacher from student;
去除重复行
select distinct student_name ,java_teacher from student;

(10)SQL中判断两个值是否相等的比较运算符是 但等号(=),判断不相等的运算符是 <> 赋值运算符是冒号等号(:=).
除此之外,SQL还支持以下特殊比较运算符:
MySQL数据库与JDBC编程基础

选出大于等于2,小于等于4的记录:
select * from student where student_id between 2 and 4;
(11)使用in比较运算符时,必须在in后的括号中列出一个或者多个值,它要求指定列必须与in括号里任意一个值相等。
选出student_id为2或4的记录
select * from student where student_id in(2,4);

(12)like运算符主要用于模糊查询,例如,若要查询以 “孙” 开头的所有记录,这就需要用到模糊查询,在模糊查询中需要用到like关键字,
SQL可以使用两个通配符:下划线 _ 可以代表任意一个字符,而 百分号 % 可以代表任意多个字符。
select * from student where student_name like ‘孙%’; 查询所有学生中名字以孙开头的学生

select * from student where student_name like ‘__’ ; 查询出名字为两个字符的所有学生(使用两个下划线代表两个字符)

(13)在某些特殊情况下,查询的条件需要使用下划线或者百分号,不希望SQL把下划线和百分号当成通配符使用,这时就需要使用转义字符,MySQL使用反斜线\作为转义字符。
选出所有名字以下划线开头的学生
select * from studt where student_name like ‘_%’ ;en

而标准SQL并没有提供反斜线\的转义字符,而是使用escape关键字进行转义:
select * from studt where student_name like ‘_%’ escape ‘\’

(14) is null 用于判断某些值是否为空,
select * from student where student_name is null ;
(1 5)如果where字句后有多个条件需要组合,SQL提供了and 和or逻辑运算来组合两个条件,并提供not 来对逻辑表达式求否。
select * form student where student_name like ‘孙%’ and student_id >9 ;

(16)执行查询后的查询结果默认按照插入顺序排列,如果需要某列值的大小进行排序,则可以使用order by字句;进行排序时默认按照升序进行排序,如果强制按照降序进行排列,则需要在列后使用desc关键字。
select * from student order by java_teacher;
(17)如果指定了多个排序列,则第一个排序列是首要排序列,只有当第一列中存在多个相同的值时,第二个排序列才会起作用。
//先按java_teacher降序排列,当相同时再按照student_name列的升序排列。
select * from student order by java_teacher desc,sdudent_name;

————————————————————————————————————

数据库函数:
(1)每个数据库都会在标准的SQL基础上扩展一些函数,这些函数用于数据处理或者复杂运算,他们通过对一组函数进行计算,最终得到想要的结果,函数一般都会有一个或者多个输入,这些输入被称为函数的参数,函数内部会对这些参数进行判断和计算,最终只有一个值作为返回值。函数可以出现在SQL语句的各个位置,比较常用的是select之后的where子句。

(2)根据函数对多行数据的处理方式,函数被分为单行函数和多行函数,单行函数对每行输入值单独计算,每行得到一个计算结果返回给用户;多行函数对多行输入值整体计算,最终只得到一个结果。
(3)SQL中的函数和Java语言中的方法有点类似,但SQL中的函数是独立的程序单元,也就是说,调用函数时无须使用任何类、对象的调用者,而是直接执行函数。语法如下:
function_name(arg1 ,arg2 …)
(4)多行函数也称为聚集函数、分组函数,主要用于完成一些统计功能,在大部分数据库中基本相同。但不同数据库中单行函数差异很大。
(5)单行函数的参数可以是变量、常量或数据列。单行函数可以接受多个参数,但只返回一个值。
单行函数会对每行单独起作用,每行(可能包含多个参数),返回一个结果
使用单行函数可以改变参数的数据类型。单行函数支持嵌套使用,即内层函数的返回值是外层函数的参数。
(6)单行函数分类:日期时间函数 数值函数 字符函数 字符函数 转换函数 其他函数(位函数 流程控制函数 加密解密函数 信息函数)
(7)MySQL单行函数的用法:
select char_length(teacher_name) from teacher_table ; 选出表中teacher_name列的字符长度
select sin(char_length(teacher_name)) from teacher_table; 计算列的字符长度的sin值。
select sin(1.57) 计算1.57的sin值
SELECT DATE_ADD(‘1998-01-01’,3);
select CURDATE(); 获取当前日期
select curtim(); 获取当前时间
select MD5(”testing); MD5的加密函数

(8)MySQL提供了如下几个处理nul的函数:
ifnull(expr1,expr2) 如果exp1为null,则返回expr2,否则返回expr1。
nullif(expr1,expr2) 如果expr1和expr2相等,则返回null,否则返回expr1
if(expr1,expr2,expr3) 类似三目运算符,如果expr1为true,不等于0,且不等于null,则返回expr2,否则返回expr3
isnull(expr1) 判断expr1是否为null,是返回null,不是返回false

实例程序:
select ifnull(student_name,’没有名字’) from student_table; 如果student_name列为null,则返回 没有名字
select nullif(student_name,’张三’) from student_table; 如果stdent_name列等于张三,则返回null。

(9)通常不推荐在Java程序中使用特定数据库函数,因为这将导致程序函数与特定数据库耦合,如果将程序移植到其他数据库系统上时,可能需要打开源程序,重新修改SQL语句。

——————————————————————————————————————————————
分组和组函数:
(1)组函数就是多行函数,组函数将一组记录作为整体计算,每组记录 返回一个结果,常用的组函数有以下五个:
avg(expr) 计算多行expr的平均值
count(expr) 计算多行expr的总行数
max(expr) 计算多行expr的最大值
min(expr) 计算多行expr的最小值
sum(expr) 计算多行expr的总和。

select count(*) from student_table; 计算表中记录的总条数
select count(distinct java_teacher) from student_table; 计算java_teacher共有多少值。
select sum(student) from student_table; 统计所有student_id的总和

(2)在默认情况下,组函数会把所有记录当成一组,为了对记录进行显示分组,可以在select语句后使用group by子句,gropu by字句后面通常紧跟一个或多个列名,表明查询结果根据一列或多列进行分组
select count(*) from student_table group by java_teacher;

(3)如果需要对分组进行过滤,则应该使用having子句,having后面也是一个条件表达式,只有满足该条件表达式的分组才会被选出来。having和where都有过滤功能,但他们有如下区别:
不能在where子句中过滤组,where子句仅用来过滤行。过滤组必须选用having子句。
不能在where子句中使用组函数,having子句才能使用组函数。
例子: select * from student_table group by java_teacher having count(*);

————————————————————————————————————————————————————————

多表连接查询:
很多时候,需要选择的数据并不是来自于一个表,而是来自多个数据表,这就需要使用多表连接查询
多表连接查询有两种规范,较早的SQL92规范支持如下几种多表连接查询:
等值连接
非等值连接
外连接
广义笛卡尔积
————————————————————————————
SQL92的连接查询
(1)SQL92的多表连接语法比较简洁,这种语法把多个数据表都放在from之后,多个表之间以逗号隔开;连接条件放在where之后,与查询条件之间用and逻辑运算符连接。如果连接条件要求两列值相等,则成为等值连接,否则成为非等值连接;如果没有任何连接条件,则称为广义笛卡尔积。语法如下:
select column1,column2 from table1,table2 [where join_condition];

实例:select s.*,teacher_name from student_table s,teacher_table t where s.java_teacher=t.teacher_id;

把上面where后的连接条件去掉,就可以得到广义笛卡尔乘积。select s.*,teacher_name from student_table s,teacher_table t;

————————————————————————————————————————————————————
集合运算:
(1)select语句查询的即如果是一个包含多个数据的结果集,类似于数学里的集合,可以进行交(intersect)、并(union)、和差(minus)运算。
(2)对于两个结果集进行集合运算,这两个结果集必须满足以下条件:
两个结果集所包含的数据列的数量必须相等
两个结果集所包含的数据列的数据类型也必须一一对应。
(3)union运算:
语法:select 语句 union select 语句
实例:select * from teacher_table union select student_id,student_name from student_table;
(4)minus运算
语法:select 语句 minus select 语句
MySql不支持minus
(5)intersect运算
语法:select 语句 intersect select 语句
MySQL也不支持intersect运算

————————————————————————————————————————————————————————

JDBC的典型用法:java8支持JDBC4.2的标准,JDBC4.2在原有JDBC标准上增加了一些新特性:
(1)DriverManager:用于管理JDBC驱动程序的服务类。程序使用该类的功能是获取connection对象,该类包含如下方法:
public static synchronized Connection getConnection (String url,String user,String pass) throws SQLException
该方法获得对应url的数据库连接。
(2)Connection:代表数据库连接对象,每个Connectio代表一个物理连接会话。要想访问数据库,必须先获得数据库连接,该接口常用方法如下:
****Statement createStatement() throws SQLException:该方法返回一个Statement对象
****PreparedStatement preparedStatement(String sql) throws SQException:该方法返回预编译的Sttaement对象,即将SQL语句提交到数据库进行预编译。
****CallableStatement prepareCall(String sql) throws SQLException:该方法返回CallableStatement对象,该对象调用存储过程。

上面三个方法都返回用于执行SQL语句的Statement对象,PreparedStatement CallableStatement是Statement的子类,只有在获得了Statement之后才可以执行SQL语句。

除此之外,Connection还有如下几个用于控制事务的方法:
Savepoint setSavepoint() 创建一个保存点
Savepoint setSavepoint(String name) 以指定名字来创建一个保存点
void setTransactionIsolation(int level): 设置事务的隔离级别
void rollback() 回滚事务
void rollbacl(Savepoint savepoint) 将事务回滚到指定保存点。
void setAutoCommit(bolean autoCommit) 关闭自动提交,打开事务
void commit() 提交事务

******Java7为Connection新增了setSchema(String schema)方法和getSchema(String schema)方法,这两个方法用于控制该Connection访问数据库的Schema,Java7 还为Connection新增了setNetworkTimeout(Executor int millisends)和getNetworkTimeout()这两个方法来控制数据库连接的超时行为。

(3)Statement:用于执行SQL语句的工具接口,该对象即用于执行DDL,DCL语句,也可用于执行DML语句,还可用于执行SQL语句。当执行SQL查询时,返回查询到的结果集,常用方法如下:
ResultSet executeQuary (String sql) throws SQLException: 该方法用于执行查询语句,并返回查询结果对应的ResultSet对象,该方法只能用于查询语句

int executeUpdate(String sql) throws SQLException:该方法用于执行DML语句,并返回受影响的行数;该方法也可用于执行DDL语句,执行DDL语句将返回0.

boolean excute(String sql)throws SQLException:该方法可执行任何SQL语句。如果执行后的第一个结果为Result对象,则返回true,如果执行就后第一个结果受影响的行数或没有任何结果,则返回false。

(4)PreparedStatement: 预编译的Statement对象。PreparedStatement是Statement的子接口,它允许数据库预编译SQL语句(这些SQL语句通常带有参数),以后只改变SQL命令的参数,避免数据库每次都要编译SQL语句,因此性能更好。相对于Statement而言,使用PreparedStatement执行SQL语句时,无需再传入SQL语句,只需要为预编译的SQL语句传入参数值即可,所以他比Statement多了如下方法:
void setXxx(int parameterIndex,Xxx value) :该方法根据传入参数值的类型不同,需要使用不同的方法。传入的值根据索引传给SQL语句中指定位置的参数。

PreparedStatement同样有executeUpdate() executeUpdate() excute()方法,只是这三个方法无需接受SQL字符串,因为PreparedStatement对象已经预编了SQL命令,只要为这些命令传入参数即可。

Java8还为PreparedStatement增加了不带参数的executeLargeUpdate()方法—执行DML语句影响的记录行数可能超过Integer.MAX_VALUE时,就应该使用executeLargeUpdate()方法。

(5)ResultSet:结果集对象,该对象包含返回查询结果的方法,ResultSet可以通过列索引或列名获得列数据。它包含了如下常用方法来移动记录指针。
void close() 释放ResultSet对象
boolean absolute(int row) 将结果集的记录指针移到第row行,如果row是负数,则移到倒数第row行。如果移动后的记录指针指向一条有效记录,则该方法返回true。
void beforeFirst() 将ResultSet记录指针定位到首行之前(即初始状态)
boolean previous() 将ResultSet记录指针定位到上一行,如果移动后的记录指针指向一条有效记录,则该方法返回true
boolean next() 将ResultSet记录指针定位到下一行,如果移动后的记录指针指向一条有效记录,则该方法返回true
boolean last() 将ResultSet记录指针定位到最后一行,如果移动后的记录指针指向一条有效记录,则该方法返回true
void afterLast() 将ResultSet记录指针定位到最后一行之后。

当把记录指针移动到指定行之后,ResultSet可通过getXxx(int columnIndex) 或者getXxx(String columnLabel) 方法来获取当前行、指定列的值,前者根据列索引获取值,后者根据列名获取值。

Java7提供了 T getObject(int columnIndex ,Class type) 和 T getObject(String columnLabel ,Class type)
两个泛型方法,他们可以获取任意类型的值。

————————————————————————————————————————