oracle知识点+例子1

一、简单查询:
1、查询数据表的所有列:
SELECT * FROM 表名;
SELECT 列名,列名.... FROM 表名;

2、起别名:
SELECT 列名 [AS 别名],列名 别名....
FROM 表名;

---正常
SELECT ename AS 员工姓名,sal salary
FROM emp;

---别名是关键字,别名需要用双引号引起来

SELECT ename "select",sal "from"
FROM emp;

---别名中间存在空格,别名需要用双引号引起来
SELECT ename "employee name",sal
FROM emp;

3、distinct:去重
---查询emp表中的不同职务
SELECT DISTINCT job
FROM emp;

---查询emp表中每个部门的不同职务
SELECT DISTINCT deptno,job
FROM emp;

---查询emp表中不同部门的不同职务
SELECT DISTINCT deptno,DISTINCT job
FROM emp; ---错误

注意:select后面,多列去重,在所有列的前面写一个distinct关键字即可

4、|| 连接输出
---将每个员工的信息输出为如下格式:
姓名为:xxxx,工资为:xxx。
字符串和日期用单引号引起来的。

SELECT '姓名为:'|| ename || ',工资为:' || sal || '。' 员工信息
FROM emp;

5、四则运算:
---查询员工的姓名和年薪
SELECT ename,sal*12 年薪
FROM emp;

SELECT ename,(sal+comm)*12 年薪
FROM emp;

---当与null值参与运算或是比较时,结果一定为null
nvl(agr1,arg2):判断arg1是否为Null,如果不为null,结果为arg1,如果为null,结果为arg2
SELECT ename,(sal+nvl(comm,0))*12 年薪
FROM emp;

1.员工转正后,月薪上调20%,请查询出所有员工转正后的月薪。
SELECT SAL*1.2 "员工转正后的月薪"
FROM EMP
2.员工试用期6个月,转正后月薪上调20%,请查询出所有员工工作第一年的年薪所得(不考虑奖金部分,年薪的试用期6个月的月薪+转正后6个月的月薪)
SELECT SAL*6+SAL*1.2*6 "工作第一年年薪"
FROM EMP
1.员工试用期6个月,转正后月薪上调20%,请查询出所有员工工作第一年的所有收入(需考虑奖金部分),要求显示列标题为员工姓名,工资收入,奖金收入,总收入。
SELECT ENAME 员工姓名,SAL*6+SAL*1.2*6 工资收入,nvl(comm,0) 奖金收入,(SAL*6+SAL*1.2*6+nvl(comm,0)) 总收入
FROM EMP
1.员工试用期6个月,转正后月薪上调20%,请查询出所有员工工作第一年的所有收入(需考虑奖金部分),要求显示格式为:XXX的第一年总收入为XXX
SELECT ENAME||'的第一年总收入为'||(SAL*6+SAL*1.2*6+nvl(comm,0))
FROM EMP

二、排序:
SELECT 列名 [AS 别名],列名 别名....
FROM 表名
ORDER BY 排序字段 ASC|DESC,排序字段 ASC|DESC...;

排序字段:列名,列的别名,列的顺序号,函数结果

SELECT *
FROM emp
ORDER BY deptno,sal desc;

SELECT ename a,deptno b,sal c
FROM emp
ORDER BY b,c desc;

SELECT ename a,deptno b,sal c
FROM emp
ORDER BY 2,3 desc;

---按照员工的部门编号 升序排序,部门相同按照奖金降序排序

SELECT ename a,deptno b,sal c,comm
FROM emp
ORDER BY 2,nvl(comm,0) desc;

三、限定查询
SELECT 列名 [AS 别名],列名 别名....
FROM 表名
WHERE 条件
ORDER BY 排序字段 ASC|DESC,排序字段 ASC|DESC...;

1、关系运算符:
>,<,<=,>=,=,<>,!=
可以比较数据类型:数值型,字符串,日期
---查询员工的工资大于2500的员工信息
SELECT *
FROM emp
WHERE sal>2500;

---查询员工姓名 为SMITH的员工信息
SELECT *
FROM emp
WHERE ename='SMITH';

---查询在1982年之后入职的员工信息
'日-月-年'
'DD-MM-RR'

SELECT *
FROM emp
WHERE hiredate > '31-12月-1982';

2、逻辑运算符:
and:与
or:或
not:非

not>and>or

---查询员工的职务是MANAGER或是SALESMAN,且工资大于1500的员工的姓名,职务,工资
SELECT ename,job,sal
FROM emp
WHERE (job='MANAGER' OR JOB = 'SALESMAN') and sal>1500;

3、between...and... 闭区间
语法:字段名 [not] between 最小值 and 最大值

--查询在1982年入职的员工信息
SELECT *
FROM emp
WHERE hiredate between '1-1月-1982' and '31-12月-1982';

4、in:集合运算
语法:字段名 [not] in(值1,值2,值3...)
---查询员工的职务是MANAGER或是SALESMAN,且工资大于1500的员工的姓名,职务,工资
SELECT ename,job,sal
FROM emp
WHERE job in('MANAGER','SALESMAN') and sal>1500;

5、is null:没有
is not null:有

---查询没有领导的员工信息
SELECT *
FROM emp
WHERE mgr is null;

---查询奖金不为null的员工信息
SELECT *
FROM emp
WHERE comm is not null;

6、like:模糊查询
语法:字段名 [not] like '匹配串' [ESCAPE '转义字符']
_:任意1个字符
%:0个或 多个任意字段

---查询员工姓名中包含S的员工姓名
SELECT ename
FROM emp
WHERE ename like '%S%';

insert into emp(empno,ename,sal,comm,deptno) values(2222,'li_si',2100,200,30);

commit;
---查询员工姓名中包含%的员工的姓名
SELECT ename
FROM emp
WHERE ename like '%#%%' ESCAPE '#';

SELECT ename
FROM emp
WHERE ename like '%#_%' ESCAPE '#';

SELECT ename
FROM emp
WHERE ename like '%!%%' ESCAPE '!';

SELECT ename
FROM emp
WHERE ename like '%a_%' ESCAPE 'a';

1.查询入职时间在1982-7-9之后,并且不从事SALESMAN工作的员工姓名、入职时间、职位。
select ename,hiredate,job
from emp
where hiredate>'9-7月-1982' and job<>'SALESMAN'


2.查询员工姓名的第三个字母是a的员工姓名。
select ename
from emp
where ename like '__a%';

3.查询除了10、20号部门以外的员工姓名、部门编号。

select ename,deptno
from emp
where deptno not in(10,20);


4.查询部门号为30号员工的信息,先按工资降序排序,再按姓名升序排序。
select *
from emp
order by sal desc,ename

5.查询没有上级的员工(经理号为空)的员工姓名。
select ename
from emp
where mgr is null

6.查询工资大于等于4500并且部门为10或者20的员工的姓名\工资、部门编号。
select ename,sal,deptno
from emp
where sal>=4500 and deptno in(10,20)

四、单行函数
字符函数,数值函数,日期函数,转换函数,通用函数
1、字符函数:
(01) upper():转大写
(02) lower():转小写
(03) initcap():转首字符大写,其它字符小写
(04) length():长度

DUAL:sys用户的一张表,只有一个字段,sys创建了该表的公共同义词

SELECT upper(ename),lower(ename),initcap(ename),length(ename)
FROM emp;

(05)trim():去首尾的空格
SELECT length(trim(' abc '))
FROM dual;

trim(letter from str):去掉str首尾的字母letter
SELECT trim('h' from 'hello')
FROM dual;

SELECT trim('t' from 'test')
FROM dual;

SELECT trim('t' from 'ttttttttesttttttt')
FROM dual;

(06)concat(str1,str2):连接字符串 ||

SELECT concat(ename,job)
FROM emp;

SELECT concat(concat(ename,job),hiredate)
FROM emp;

(07)instr(str1,str2,[n1,n2]):返回str2在str1中的位置,从n1开始查找第n2次出现的位置
没在str1存在的时,返回0

SELECT instr('hello world','l')
FROM dual;

SELECT instr('hello world','l',1,2)
FROM dual;

SELECT instr('hello world','a')
FROM dual;

---查询员工姓名中不含有A的员工姓名
SELECT ename
FROM emp
WHERE instr(ename,'A')=0;

SELECT instr('hello world','world')
FROM dual;

(08)replace(str1,str2,str3):将str1中的str2替换为str3
SELECT replace('abc aaa abc bbb abc ccc','abc','ABC')
FROM dual;

(09)substr(str,loc,length):截取子串,从str的loc开始截取长度为length的子串
--从首位截取,起始位置可以为0或者1
SELECT substr('hello world',1,3)
FROM dual;

SELECT substr('hello world',0,3)
FROM dual;

---截取到字符串的尾部,第三个参数省略
SELECT substr('hello world',5)
FROM dual;

---截取中间子串
SELECT substr('hello world',4,3)
FROM dual;

(10)lpad(str1,length,str2):判断 str1的长度是否等于Length,如果小于length,在str1的左边补充str2,直到长度等于length为止。
(11)rpad(str1,length,str2):判断 str1的长度是否等于Length,如果小于length,在str1的右边补充str2,直到长度等于length为止。

---判断hello的长度是否等于10,如果 不等于,在左边补充#
SELECT lpad('hello',10,'#')
FROM dual;

SELECT lpad('hellohellohello',10,'#')
FROM dual;

SELECT lpad('hello',10,'#$')
FROM dual;

1.写一个查询,用首字母大写,其它字母小写显示雇员的 ename,显示名字的长度,并给每列一个适当的标签,
条件是满足所有雇员名字的开始字母是J、A 或 M 的雇员,并对查询结果按雇员的ename升序排序。(提示:使用initcap、length、substr)
SELECT initcap(ename),LENGTH(ename)
FROM emp
WHERE substr(ename,1,1) IN('J','A','M')
ORDER BY 1;


1.查询员工姓名中中包含大写或小写字母A的员工姓名。

SELECT ename
FROM emp
WHERE upper(ename) like '%A%';

---查询emp表中职务是clerk的员工姓名
SELECT ename
FROM emp
WHERE lower(job)='clerk';


2.查询部门编号为10或20,入职日期在81年5月1日之后,并且姓名中包含大写字母A的员工姓名,
员工姓名长度(提示,要求使用INSTR函数,不能使用like进行判断)

3.查询每个职工的编号,姓名,工资
要求将查询到的数据按照一定的格式合并成一个字符串.
前10位:编号,不足部分用*填充,左对齐
中间10位:姓名,不足部分用*填充,左对齐
后10位:工资,不足部分用*填充,右对齐

SELECT rpad(empno,10,'*') || rpad(ename,10,'*') || lpad(sal,10,'*')
FROM emp;

2、数值函数
(01)round(num,p):四舍五入
p=0:round(num),四舍五入为整数
SELECT round(455.55)
FROM dual;
p>0:四舍五入到小数点右边第P位
SELECT round(455.55,1)
FROM dual;
p<0:从小数点左边的第|p|位进行四舍五入
SELECT round(455.55,-1)
FROM dual;

SELECT round(455.55,-3)
FROM dual;
SELECT round(555.55,-3)
FROM dual;
(02)trunc(num,p):截断
p=0:trunc(num),截断为整数
SELECT trunc(455.55)
FROM dual;
p>0:截断到小数点右边第p位
SELECT trunc(455.55,1)
FROM dual;
p<0:从小数点左边的第|p|位进行截断
SELECT trunc(455.55,-1)
FROM dual;

(03):mod(num1,num2):求余
SELECT mod(3,2)
FROM dual;

SELECT mod(3,0)
FROM dual;

3、日期函数
规则: 日期-日期=天数
日期+天数=日期

当前系统日期:sysdate

(01)months_between(date1,date2):返回两个日期之间相差的月份。如果date1>date2,返回正数,反之,返回是负数
SELECT trunc(months_between(SYSDATE,'1-1月-2000'))
FROM dual;

---统计 emp表中每人入职了多少个月?
SELECT ename,trunc(months_between(SYSDATE,hiredate))
FROM emp;

---统计 每个人到目前为止入职了多少年零多少月零多少天?
SELECT trunc(months_between(SYSDATE,hiredate)/12) 年, trunc(mod((SYSDATE-hiredate),365)/30) 月,
trunc(mod(mod((SYSDATE-hiredate),365),30)) 天
FROM emp;

(02)next_day(DATE,weekday):返回指定日期的下个星期几是什么日期
SELECT next_day(SYSDATE,'星期一')
FROM dual;

(03) last_day(DATE):返回指定日期的所在月份的最后一天

SELECT last_day(SYSDATE)
FROM dual;

(04)add_months(DATE,months):在指定日期上增加若干个月后的日期
SELECT add_months(sysdate,4)
FROM dual;

(05)EXTRACT([MONTH DAY YEAR] FROM DATE):从指定日期中取出日期中的年,月,日
SELECT EXTRACT(MONTH FROM SYSDATE)
FROM dual;

SELECT EXTRACT(year FROM SYSDATE)
FROM dual;

---查询在1982年入职的员工信息
SELECT *
FROM emp
WHERE extract(year from hiredate)=1982;

---在一年月前半年入职的员工信息
SELECT *
FROM emp
WHERE EXTRACT(MONTH FROM hiredate)<=6;

(06)round(DATE,fmt):
(07)trunc(DATE,fmt):
fmt:
CC:世纪
YY:年
MM:月
DD:日
HH:时
SELECT round(SYSDATE,'MM')
FROM dual;

SELECT round(to_date('17-3月-2018'),'MM')
FROM dual;

4、转换函数
(01)to_char():转为字符串
将日期转为字符串:
to_char(DATE,'format'):将日期转为固定格式的字符串
常用的格式:
yyyy:年
mm:月
dd:日
day:星期
hh:时 hh24:24小时制
mi:分
ss:秒
mon:月

SELECT to_char(SYSDATE,'yyyy-mm-dd hh24:mi:ss day')
FROM dual;

SELECT to_char(SYSDATE,'yyyy')
FROM dual;

SELECT ename,hiredate
FROM emp
WHERE to_char(hiredate,'yyyy')='1982';

将数值 转为字符串:
to_char(NUMBER,'format'):将指定的数据转为固定格式的字符串
SELECT to_char(455.55)
FROM dual;
常见的格式:
.:小数点
9:任意数字
,:千位符
L:本地货币符号
$:美元

SELECT to_char(4555.55,'L999,999.99')
FROM dual;

(02)to_number(str,'format'):转为数值,将固定格式的字符串转为数值

SELECT TO_NUMBER('¥4,555.55','L9,999.99')
FROM dual;

(03)to_date(str,'format'):转为日期,将固定格式的字符串转为日期
SELECT to_date('21-12-2017','dd-mm-yyyy')
FROM dual;

5、通用函数:
(01)nvl():
(02) nvl2(arg1,arg2,arg3):判断arg1是否为null,如果不为Null,返回arg2,如果为Null,返回arg3
SELECT ename,comm,nvl2(comm,comm,0)
FROM emp;

---查询员工的姓名,奖金,如果奖金为null,输出为“No comm.”
SELECT ename,comm,nvl2(comm,to_char(comm),'No comm.')
FROM emp;

(03)decode():类似于等值判定,swith
语法:decode(exp/comm,值1,结果1,值2,结果2....,值n,结果n,结果m);
---判定员工姓名中含A或a的位置,如果位置在首位,显示“A在首位”,如果位置在末尾,显示“A在末尾”,如果A在中间,显示"A在中间",否则,“不包含A”
SELECT ename,decode(instr(upper(ename),'A'),1,'A在首位',0,'不包含A',LENGTH(ename),'A在末尾','A在中间')
FROM emp;

(04):CASE():
格式一:
CASE WHEN 条件1 THEN 结果1
WHEN 条件2 THEN 结果2
....
WHEN 条件N THEN 结果n
ELSE 结果m
END;

SELECT ename,CASE WHEN upper(ename) LIKE 'A%' THEN 'A在首位'
WHEN upper(ename) LIKE '%A' THEN 'A在末尾'
WHEN upper(ename) NOT LIKE '%A%' THEN '不包含A'
ELSE 'A在中间'
END
FROM emp;

格式二:
CASE 表达式/列名 WHEN 值1 THEN 结果1
WHEN 值2 THEN 结果2
。。。
WHEN 值n THEN 结果n
ELSE 结果m
END

猜你喜欢

转载自www.cnblogs.com/haxy/p/9285750.html