一. oracle 删除主键约束_SQL基础知识:约束(实例)
给大家介绍SQL中六种工作中经常使用到的约束,供大家参考!
1. NOT NULL约束
- NOT NULL 约束强制列不接受 NULL 值。
- NOT NULL 约束强制字段始终包含值。这意味着,如果不向字段添加值,就无法插入新记录或者更新记录。
下面的 SQL 强制表"Customers" 的"客户ID" 列和 "姓名" 列不接受 NULL 值:
CREATE TABLE Customers(
客户ID INT NOT NULL,
姓名 VARCHAR(10) NOT NULL,
地址 VARCHAR(50) NULL,
城市 VARCHAR(20) NULL,
邮编 CHAR(6) NULL,
省份 VARCHAR(20) NULL
) ;
一旦这两列有空值NULL被插入,系统就会报错提示,例如我们插入如下信息:
INSERT INTO dbo.Customers ( 姓名, 地址, 城市, 邮编, 省份 )
VALUES (NULL,'花城大道1号','广州市','51000',NULL)
结果:
2. UNIQUE约束
UNIQUE 约束唯一标识数据库表中的每条记录,和 PRIMARY KEY 约束均为列或列集合提供了唯一性的保证,PRIMARY KEY 约束拥有自动定义的 UNIQUE约束。
请注意,每个表可以有多个 UNIQUE 约束,但是每个表只能有一个 PRIMARY KEY 约束。
2.1 CREATE TABLE 时的 SQL UNIQUE 约束
下面的 SQL 在 "Orders" 表创建时在 "订单ID" 列上创建 UNIQUE 约束:
MySQL:
CREATE TABLE dbo.Orders(
订单ID INT NOT NULL,
客户ID INT NULL,
员工ID INT NULL,
订单日期 DATETIME NULL,
发货ID INT NULL,
UNIQUE (订单ID)
) ;
SQL Server / Oracle / MS Access:
CREATE TABLE dbo.Orders(
订单ID INT NOT NULL UNIQUE,
客户ID INT NULL,
员工ID INT NULL,
订单日期 DATETIME NULL,
发货ID INT NULL
) ;
唯一约束是被约束的列在插入新数据时,如果和已经存在的列有相同的值,则会报错。
INSERT INTO dbo.Orders
( 订单ID, 客户ID, 员工ID, 订单日期, 发货ID )
VALUES
( 1001,1,2,'2018-11-21 19:21:32',1),
( 1001,2,3,'2018-11-22 11:22:32',5)
结果为:
如需命名 UNIQUE 约束,并定义多个列的 UNIQUE 约束,请使用下面的 SQL 语法:
MySQL / SQL Server / Oracle / MS Access:
CREATE TABLE dbo.Orders(
订单ID INT NOT NULL ,
客户ID INT NULL,
员工ID INT NULL,
订单日期 DATETIME NULL,
发货ID INT NULL,
CONSTRAINT uc_OrderID UNIQUE (订单ID,发货ID)
) ;
2.2 ALTER TABLE 时的 UNIQUE 约束
当表已被创建时,如需在 "订单ID" 列创建 UNIQUE 约束,请使用下面的 SQL:
MySQL / SQL Server / Oracle / MS Access:
ALTER TABLE Orders
ADD UNIQUE (订单ID)
如需命名 UNIQUE 约束,并定义多个列的 UNIQUE 约束,请使用下面的 SQL 语法:
MySQL / SQL Server / Oracle / MS Access:
ALTER TABLE Customers
ADD CONSTRAINT uc_CustomerID UNIQUE (客户ID,姓名)
2.3 删除UNIQUE 约束
如需删除UNIQUE 约束,请使用下面的 SQL:
MySQL:
ALTER TABLE Orders
DROP INDEX uc_OrderID
SQL Server / Oracle / MS Access:
ALTER TABLE Customers
DROP CONSTRAINT uc_CustomerID
3. PRIMARY KEY约束
PRIMARY KEY 约束唯一标识数据库表中的每条记录,主键必须包含唯一的值,主键列不能包含 NULL 值,每个表都应该有一个主键,并且每个表只能有一个主键。
3.1 CREATE TABLE 时的 PRIMARY KEY 约束
下面的 SQL 在 "Customers" 表创建时在 "客户ID" 列上创建 PRIMARY KEY 约束:
MySQL:
CREATE TABLE dbo.Customers(
客户ID INT NOT NULL,
姓名 VARCHAR(10) NULL,
地址 VARCHAR(50) NULL,
城市 VARCHAR(20) NULL,
邮编 CHAR(6) NULL,
省份 VARCHAR(20) NULL,
PRIMARY KEY (客户ID)
) ;
SQL Server / Oracle / MS Access:
CREATE TABLE dbo.Customers(
客户ID INT NOT NULL PRIMARY KEY,
姓名 VARCHAR(10) NULL,
地址 VARCHAR(50) NULL,
城市 VARCHAR(20) NULL,
邮编 CHAR(6) NULL,
省份 VARCHAR(20) NULL
) ;
如需命名 PRIMARY KEY 约束,并定义多个列的 PRIMARY KEY 约束,请使用下面的 SQL 语法:
MySQL / SQL Server / Oracle / MS Access:
CREATE TABLE dbo.Customers(
客户ID INT NOT NULL PRIMARY KEY,
姓名 VARCHAR(10) NULL,
地址 VARCHAR(50) NULL,
城市 VARCHAR(20) NULL,
邮编 CHAR(6) NULL,
省份 VARCHAR(20) NULL,
CONSTRAINT pk_CustomerID PRIMARY KEY (客户ID,姓名)
) ;
注释:在上面的实例中,只有一个主键 PRIMARY KEY(pk_CustomerID)。然而,pk_CustomerID 的值是由两个列(客户ID和姓名)组成的。
3.2 ALTER TABLE 时的 PRIMARY KEY 约束
当表已被创建时,如需在 "客户ID" 列创建 PRIMARY KEY 约束,请使用下面的 SQL:
MySQL / SQL Server / Oracle / MS Access:
ALTER TABLE Customers
ADD PRIMARY KEY (客户ID)
如需命名 PRIMARY KEY 约束,并定义多个列的 PRIMARY KEY 约束,请使用下面的 SQL 语法:
MySQL / SQL Server / Oracle / MS Access:
ALTER TABLE Customers
ADD CONSTRAINT pk_CustomerID PRIMARY KEY (客户ID,姓名)
注释:如果您使用 ALTER TABLE 语句添加主键,必须把主键列声明为不包含 NULL 值(在表首次创建时)。
3.3 删除 PRIMARY KEY 约束
如需删除 PRIMARY KEY 约束,请使用下面的 SQL:
MySQL:
ALTER TABLE Customers
DROP PRIMARY KEY
SQL Server / Oracle / MS Access:
ALTER TABLE Customers
DROP CONSTRAINT pk_CustomerID
4. FOREIGN KEY约束
一个表中的 FOREIGN KEY 指向另一个表中的 PRIMARY KEY,让我们通过一个实例来解释外键。
5. DEFAULT约束
DEFAULT 约束用于向列中插入默认值。
如果没有规定其他的值,那么会将默认值添加到所有的新记录。
6. CHECK约束
CHECK 约束用于限制列中的值的范围,如果对单个列定义 CHECK 约束,那么该列只允许特定的值。如果对一个表定义 CHECK 约束,那么此约束会基于行中其他列的值在特定的列中对值进行限制。
二. oracle数据库 中to_number、to_char、to_date用法介绍
- TO_DATE 是把字符串转换为数据库中得日期类型转换函数
- TO_CHAR 是把日期或数字转换为字符串
- TO_NUMBER 将字符转化为数字
1. TO_DATE
使用TO_DATE函数将字符转换为日期,规范:TO_DATE(char, '格式')
例1:
select to_date('2012-07-01 10:00:00','yyyy-mm-dd hh24:mi:ss') from dual;
select to_date('2012-07-01 10:00','yyyy-mm-dd hh24:mi') from dual;
select to_date('2012-07-01 10','yyyy-mm-dd hh24') from dual;
select to_date('2012-07-01','yyyy-mm-dd') from dual;
select to_date('2012-07','yyyy-mm') from dual;
select to_date('2012','yyyy') from dual;
注意:yyyy / yyy / yy 分别代表4位 / 3位 / 2位的数字年,mm代表月,dd代表日,hh24 / hh12分别代表24小时制 / 12小时制,mi代表分,ss代表秒
例2:
表jmzs里的czsj是vachar2类型,转换成date类型:
select to_date(czsj,'yyyy-mm-dd hh24:mi:ss') from jmzs;
2. TO_CHAR
使用TO_CHAR函数处理数字,规范:TO_CHAR(number, '格式')
使用TO_CHAR函数处理日期,规范:TO_CHAR(date,’格式’);
例1:
select To_Char(to_date('2012-07-01 10:00:00','yyyy-mm-dd hh24:mi:ss'),'yyyymmddhhmiss') from dual;
例2:
表jmzs里的czsj是vachar2类型,先转换成date类型,再转成char类型:
select To_Char(to_date(czsj,'yyyy-mm-dd hh24:mi:ss'),'yyyymmddhhmiss') from jmzs;
3. TO_NUMBER
使用TO_NUMBER函数将字符转换为数字,规范:TO_NUMBER(char, '格式')
例1:
select To_Number(To_Char(to_date('2012-07-01 10:00:00','yyyy-mm-dd hh24:mi:ss'),'yyyymmddhhmiss')) from dual;
例2:
表jmzs里的czsj是vachar2类型,先转换成date类型,再转成char类型,最后才能转成number类型:
select To_Number(To_Char(to_date(czsj,'yyyy-mm-dd hh24:mi:ss'),'yyyymmddhhmiss')) from jmzs;
To_number函数中也有很多预定义的固定格式:
格式值 | 含义 |
---|---|
9 | 代表一个数字 |
0 | 强迫0显示 |
$ | 显示美元符号 |
L | 强制显示一个当地的货币符号 |
. | 显示一个小数点 |
, | 显示一个千位分隔符号 |
3.1 将一个字符串转成数值
TO_NUMBER('123.45') 结果 123.45
TO_NUMBER('$123,456.78','$999,999.99') 结果 123,456.78
3.2 将字符串转换为数字数据类型
select to_number('00001228') from dual;--to_number('00001228') 1228
select trunc(to_number('123.123'),2) from dual;
结果为:123.12
3.3 转换一个十六进制数的浮标
SELECT TO_NUMBER('0A', 'XX') FROM dual;
结果为:10
3.4 一个十六进制数转换为十进制
SELECT TO_NUMBER(100000,'XXXXXXXX') FROM dual;
结果为:1048576
select to_number('0123')number1, --converts a string to number
trunc(to_number('0123.123'),2) number2,
to_number('120.11','999.99') number3,
to_number('0a','xx') number4, --converts a hex number to decimal
to_number(100000,'xxxxxx') number5
from dual;
三. java实体entity转map对象
方法一:一句搞定,直接返回map对象:
import org.springframework.cglib.beans.BeanMap;
BeanMap.create(entityObj);
方法二:利用fastjson处理(未验证,但是理论上没问题)
import com.alibaba.fastjson.JSONObject;
String json = JSONObject.toJSONString(entityObj);
Map map = JSONObject.parseObject(json, Map.class);
四. oracle中如何让01+1等于02
写SQL指令即可:
select to_char('01'+1,'00') from dual;
需求:同一天的飞行编码没有的话从01开始,有的话取最大的值+1
实现sql
SELECT to_char(NVL(max(m.SERIAL_NUMBER),'00')+1,'00') SERIAL_NUMBER
FROM T_SLXF_AVIATION_PLAN_IMPLEM m
WHERE m.TASK_TYPE = '2' AND m.PLAN_DATE ='2020-12-25' and m.DEPT_TYPE = '2' and m.IS_DELETE = '0' GROUP BY m.PLAN_DATE
五. Java8 使用 stream().sorted()对List集合进行排序
1. 集合对像定义
集合对象以学生类(*StudentInfo*)为例,有学生的基本信息,包括:姓名,性别,年龄,身高,生日几项。
使用stream().sorted()进行排序,需要该类实现 *Comparable* 接口,该接口只有一个方法需要实现,如下:
public int compareTo(T o);
有关compareTo方法的实现说明,请参考:Java 关于重写compareTo方法
我的学生类代码如下:
import java.time.LocalDate;
import java.util.List;
public class StudentInfo implements Comparable<StudentInfo> {
//名称
private String name;
//性别 true男 false女
private Boolean gender;
//年龄
private Integer age;
//身高
private Double height;
//出生日期
private LocalDate birthday;
public StudentInfo(String name, Boolean gender, Integer age, Double height, LocalDate birthday){
this.name = name;
this.gender = gender;
this.age = age;
this.height = height;
this.birthday = birthday;
}
public String toString(){
String info = String.format("%s\t\t%s\t\t%s\t\t\t%s\t\t%s",this.name,this.gender.toString(),this.age.toString(),this.height.toString(),birthday.toString());
return info;
}
public static void printStudents(List<StudentInfo> studentInfos){
System.out.println("[姓名]\t\t[性别]\t\t[年龄]\t\t[身高]\t\t[生日]");
System.out.println("----------------------------------------------------------");
studentInfos.forEach(s->System.out.println(s.toString()));
System.out.println(" ");
}
@Override
public int compareTo(StudentInfo ob) {
return this.age.compareTo(ob.getAge());
//return 1;
}
2. 添加测试数据
下面来添加一些测试用的数据,代码如下:
//测试数据,请不要纠结数据的严谨性
List<StudentInfo> studentList = new ArrayList<>();
studentList.add(new StudentInfo("李小明",true,18,1.76,LocalDate.of(2001,3,23)));
studentList.add(new StudentInfo("张小丽",false,18,1.61,LocalDate.of(2001,6,3)));
studentList.add(new StudentInfo("王大朋",true,19,1.82,LocalDate.of(2000,3,11)));
studentList.add(new StudentInfo("陈小跑",false,17,1.67,LocalDate.of(2002,10,18)));
3. 排序
3.1 使用年龄进行升序排序
//排序前输出
StudentInfo.printStudents(studentList);
//按年龄排序(Integer类型)
List<StudentInfo> studentsSortName = studentList.stream().sorted(Comparator.comparing(StudentInfo::getAge)).collect(Collectors.toList());
//排序后输出
StudentInfo.printStudents(studentsSortName);
结果如下图:
3.2 使用年龄进行降序排序(使用reversed()方法)
//排序前输出
StudentInfo.printStudents(studentList);
//按年龄排序(Integer类型)
List<StudentInfo> studentsSortName = studentList.stream().sorted(Comparator.comparing(StudentInfo::getAge).reversed()).collect(Collectors.toList());
//排序后输出
StudentInfo.printStudents(studentsSortName);
结果如下图:
3.3 使用年龄进行降序排序,年龄相同再使用身高升序排序
//排序前输出
StudentInfo.printStudents(studentList);
//按年龄排序(Integer类型)
List<StudentInfo> studentsSortName = studentList.stream()
.sorted(Comparator.comparing(StudentInfo::getAge).reversed().thenComparing(StudentInfo::getHeight))
.collect(Collectors.toList());
//排序后输出
StudentInfo.printStudents(studentsSortName);
结果如下图: