数据库查询及以后知识的笔记:
--分组
--1.1 group by 和having 的使用
--select *
--from emp
--查找平均工资大于2500的部门
select avg(sal) as '平均工资',deptno
from emp
group by deptno
having avg(sal)>2500
--分组前的条件写在where中,分组后的条件使用having
--1.2 eg:
--查找员工姓名包含'A'的员工,不同的岗位的人数,哪些岗位的人数在1-3之间
select deptno,count(ename) as '人数'
from emp
where ename like '%A%'
group by deptno
having count(ename)>0 and count(ename)<4
--等价于:-- having count(ename) between 1 and 3
--orcale:
/*select count(count(ename))
from emp
group by job,deptno*/
--
--1.3 连接查询
select ename,dept.DNAME
from emp join dept on emp.deptno=dept.deptno
--1.3.1
/*广义笛卡尔积 ,很少使用(属于内连接)
select student.*,sc.*
from student,sc
*/
--1.3.2
--"等值"连接(属于内连接)
select e.*,d.*
from emp e ,dept d
where e.DEPTNO=d.DEPTNO
--规范性写法:表必须有表别名,列名前有表名修饰,不用*来代替表中的所有列名。
--eg:规范性写法
select e.empno,e.ename,e.job,e.MGR,e.hiredate,e.sal,e.deptno,d.deptno,d.dname,d.loc
from emp e ,dept d
where e.deptno=d.deptno
--1.3.3非等值连接(属于内连接)
--查询员工信息表中,所有员工的工资等级
--涉及到emp 表,salgrade 表
-- emp中的sal是在salgrade.losal,salgrade.hisal之间
select e.ENAME,s.GRADE
from emp e,salgrade s
where e.sal>=s.losal and e.sal<= hisal;
--1.3.4 自身连接(属于内连接)
/*一个表与其自己进行连接,称为表的自身连接。
此时表必须使用别名,不然无法区分
*/
--eg:
select e1.empno,e1.ename,e1.job,e1.mgr,e2.ename as '上司'
from emp e1,emp e2
where e1.mgr=e2.empno or (e1.mgr is null and e1.empno=e2.empno)
--1.3.5 外连接,包含left join 和right join
--查询结果
select e1.empno,e1.ename,e1.job,e1.mgr,e2.ename as '上司'
from emp e1 left join emp e2 on (e1.mgr=e2.empno)
/*仅仅在oracle下可以使用操纵符(+)来实现左外连接/右外连接
eg:
select e1.empno,e1.ename,e1.job,e1.mgr,e2.ename as '上司'
from emp e1,dept e2
where e1.detpno=e2.deptno(+)相当于from emp e1 left join emp e2 on (e1.mgr=e2.empno)
也可以说,+号在哪一方,另一方就是主表,另一方的所有内容都要显示(即使没有满足匹配的条件)
*/
--1.3.6 复合条件连接
--自幼向左执行,因此多表连接写在左侧,效率更高,因此先进行过滤,再进行连接
select *
from emp,dept
where emp.deptno=dept.DEPTNO
and emp.DEPTNO!=30
--1.3.7自然连接
/*
select e1.ename,deptno,d1.dname,d.loc
from emp e1 natural join dept d1
a表和b表中同名同类型的列作为连接条件,完成连接(Oracle中可以,sql server不支持自然连接)
同名列名会合并,因此没有限定名
*/
--1.3.8 USING子句
--可以选择用哪一列作为连接条件
/*
eg:
select *
from a1 e1 natural join a2 e2
using
*/
/*select emp.ename,emp.deptno,dept.dname,dept.loc
from emp left join dept
using (emp.deptno)*/
-- 1.4.1 子查询(嵌套查询)
-- 将一个查询块嵌套再另一个查询块的where子句或having短语的条件中的查询称为嵌套查询
--C400周三下午上机!!
-- 选修2号课程的学生都有哪些,这些学生的姓名都是什么?
--子查询的限制,不能使用order by子句
-- 查询员工姓名叫'ALLEN'的部门号相同的员工有哪些
select *
from emp
where emp.deptno = (select deptno
from emp
where ENAME='ALLEN')
-- 如果子查询返回的是多行的时候,不能用“=”。而是用in
select *
from emp
where emp.deptno IN (select deptno
from emp
where ENAME='ALLEN' OR ENAME='CLARK')
-- 除了 in、not in、=、>、<、>=、<=、!=等比较运算符外,还可以使用带有ANY 和ALL谓词的子查询
/*eg:
>ANY 表示大于子查询结果中任意一个值(相当于大于最小值)
<ANY 表示小于子查询结果中任意一个值(相当于小于最大值)
>ALL 表示大于子查询结果中所有的值(相当于大于最大值)
<ALL 表示小于子查询结果中所有的值(相当于小于最小值)
!= ALL 相当于 not in
......
*/
select *
from emp
where emp.deptno < any(select deptno
from emp
where ENAME='ALLEN' OR ENAME='CLARK')
--1.4.2 相关子查询
/*子查询的查询条件依赖于父查询
首先取外层查询中表的第一个元组,根据它与内层循环相关的属性值...
*/
-- eg:查询所有选修了一号课程的学生姓名
/*
select sname
from student
where exists (select * from sc
where sno=student.sno and con='1')
*/
-- 查询哪些员工的工资低于本部门的平均工资
select sal,ename,deptno
from emp e1
where sal<(select avg(sal)
from emp e2
where e1.DEPTNO=e2.DEPTNO
)
-- 父查询查询一次,子查询查询一次,父查询查询一次,子查询查询一次......
--查询员工所在部门人数超过三人的员工信息
select *
from emp e1
where exists(select *
from emp e2
where e1.deptno=e2.DEPTNO
group by DEPTNO
having COUNT(*)>3)
-- 查询哪些学生没有班级信息
/*
select
*/
-- 查询班级名称为'电信01'的学生人数。
/*
select count(*)
from student2
where exists (select * from classtable2
where student2.cid=classtable2.cid and cname=
'电信01' )
*/
-- 1.4.3集合查询
/*
要进行并交运算的两个表,表的列数/对应项的数据类型 都必须相同。
*/
--1.4.3.1 并集
-- union/union all
-- union 去重(重 :指的是两个表相交的部分)
select *
from emp
where DEPTno=10
union
select *
from emp
where DEPTno<=20
-- union all不去重
select *
from emp
where DEPTno=10
union all
select *
from emp
where DEPTno<=20
--1.4.3.2交集
-- intersect
select *
from emp
where DEPTno=10
intersect
select *
from emp
where DEPTno<=20
--1.4.3.3 差集
-- minus
(select *
from emp
where DEPTno<=20)
except--(Oracle中使用minus)
(select *
from emp
where DEPTno=10)
-- 2.
create table emp2
AS
(select * from emp where 1=2)
-- SQL函数
-- 数字函数round和trunc()四舍五入,mod()取模运算
select round(100.567,0)
from emp;
-- 字符函数
-- 转换大小写
select sal--initcap(ename)首字母大写函数,upper(ename)全部字母大写,lower(ename)全部字母小写(oracle中适用)
from emp
where lOWER(JOB)='Clerk' --大小写区分
-- 求字符长度
-- 显示人员名字的长度
select len(ename),ename,len('中国')-- sql server中用len,oracle中用length()函数
from emp
-- ltrim,rtrim去左右空格
select ltrim(' __kkk '),rtrim(' __kkk '),trim(' kkk ')--trim()去除左右空格
from emp
-- 常用于char varchar2类的数据处理中
-- SUBSTR: 返回第一个参数从n1字符开始,长度为n2的字串,
--如果n1是负数,表示从后向前截取abs(n1)位,也就是说(n2无意义)
--select substr('helloworld',-2,10000) 返回值为ld
--如果没有写n2,表示从n1开始截取到最后
--select substr('helloworld',1) 返回值为helloworld
/*
SUBSTR('helloworld',1,5)
*/
select substr('helloworld',1,5)
from emp
-- 获取子串的索引下标
/*
select instr('helloworld','hello')
from dual返回是1,表示从第一个字符开始
select instr('helloworld','hello2')
from dual返回是0,表示找不到
select instr('helloworld','hello',2)
from dual返回是0,表示从第2个字符开始找,这时找不到,因此返回0
select instr('helloworld','o',2)
from dual返回是5,表示从第2个字符开始找,找到的第1个o的位置,为5
select instr('helloworld','hello',2,2)
from dual返回是7,表示从第2个字符开始,找到的第2个o的位置,为7
*/
-- 连接字符串concat
select --'my name is'||ename,(oracle中适用)
concat('my name is ',ename)
from emp;
--填充字符串,统一变成指定长度
select len(ename),ename
from emp;
--左填充,右填充:
/*select len(ename),ename,lpad(ename,10,'*'),rpad(ename,10,'*')
from emp*/
-- 字符串替换
/*
select ename,REPLACE(ename,upper('a),'*')
from dual*/
-- 日期函数
/*select hiredate,ename,add_month(hiredate,6)月份的加,给负数的话就是减
from emp
select hiredate,ename,last_day(hiredate)月份最后一天,会考虑到闰年,月份的不同情况 日期可以加减运算,默认加1为增加一天。
from emp
日期的写法'01-2月-2019'
MONTHS_BETWEEN()
查询每个员工在公司服务的月份数
select months_between(sysdate,hiredate),ename
from emp
NEXT_DAY():返回某一日期的下一指定日期。
select next_day('01-2月-2019','星期一')
from dual结果:01-2月-2019的下一个星期一
extract:返回从日期类型中取出指定的年/月/日
select extract(month from hiredate),ename 取出日期类型date中的月份
from emp
where extract(month from hiredate)<=6;
日期的四舍五入:
select round(SYSDATETIME,'MM'),trunc(SYSDATETIME,'MM')//MM表示月份,DD表示天,trunc是截断,不进位
from emp;
查询部门10/20的员工,截止到2000年1月1日,工作了多少个月份
select months_between(hiredate,'01-1月-2000'),extract(month from hiredate)
from emp
where deptno=10 or deptno=20
员工试用期6个月,查询职位不是MANAGER的员工姓名,
入职日期,转正日期,入职日期后的第一个星期一,入职当月的最后一天日期
select ename,hiredate,addmonth(hiredate,6),next_day(hiredate,'星期一'),last_day(hiredate)
from emp
where job<>'MANAGER'
*/
-- 转换函数
/*
隐式转换
对于INSERT 和 UPDATE 操作,oracle会把插入值或者更新值隐式转换为字段的数据类型。
对于SELECT 语句,oracle会把字段的数据类型隐式转换为变量的数据类型。
当比较一个字符型和数值型的值时,oracle会自动把字符型的值变成数值型进行比较。
当比较字符型和数值型的值时,oracle会把字符型转化为字符类型。
用连接符(||)时,oracle会将
*/
-- 显式转换
--1.日期转换
--to_date函数:将字符串转换成日期
--eg:2019-09-12 ---> to_date()
/*
select to_date('2019-09-12','YYYY-MM-DD')+1
from dual
select to_date('2019/09/12','YYYY/MM/DD')+1
from dual
*/
-- to_char函数:把日期转换成字符串。
--数字转换成字符:to_char
--字符转换成数字:to_number
/*TO_CHAR()函数eg:
to_char(date|number,[,'fmt']);
select sysdate,
to_char(sysdate,'YYYY-MM-DD')
from DUAL;
*/
/*
数字具体格式如下
9:一位数字
*/
-- to_char 数字转字符串,to_number字符串转数字
/*
select to_char(100,'$999')
from dual
select to_char(2340.23,'L9,999.99'),
to_number('$1,234,567','$999,999,999')
from dual
select ename,to_char(sal,'L999,999,999')
from emp;
*/
-- 单行函数
--decode函数
--nvl函数
/*查询员工表中员工的总工资,因为有的人的comm(奖金)为NULL,所以不能直接让总工资=comm+sal;
解决方法:nvl函数:nvl(input_value,result_if_value_is_null)如果input_value是null,把它变成result_if_value,
select ename,sal,comm,sal+nvl(comm,0) realsalary
from emp;
*/
-- 复习
-- 查询员工信息表,显示员工姓名、工资、奖金(有奖金显示有,无奖金显示无)
select ename,sal,nvl2(comm,'有','无'),comm
from emp;
-- 显示员工信息表中员工的工资等级
--0-1000 低 1001-2000 中 2001以上 高
select (case
when sal between 0 and 1000 then '低'
when sal between 1001 and 2000 then '中'
else '高'end) 工资等级
from emp;
-- 层次查询
--自然树结构
-- 从上级找下级
select empno,ENAME,mgr,LEVEL
from emp
start with ENAME='KING'
connect by prior empno=MGR--父节点的empno等于子节点的mgr
order by LEVEL asc;
-- 从下级找上级怎么找呢?
select empno,ENAME,mgr,LEVEL
from emp
start with ENAME='SMITH'
connect by empno= prior mgr;--父节点的mgr等于子节点的empno
-- 部门号,部门名,上级部门号,部门人数
-- 翻译函数
select translate('ABCDEBFGHIJA','ABC','123')--A替换为1,B替换为2,C替换为3
from dual;
-- 特殊情况,第二个参数和第二个参数不同的话
select translate('abcdefgabcde','abcdefg','123')--它会忽略defg对应情况,没有长的那一部分对应的字符
from dual;
select translate('abcdefgabcde','abcdefg','123456746546546465')--它会忽略46546546465对应情况,没有长的那一部分对应的字符
from dual;
--分析查询
select sum(sal),ENAME
from EMP--报错,求和不能和ename一块显示出来
--over()
select sum(SAL)OVER(),ENAME
FROM EMP
/*
分析函数带有一个开窗函数over(),
包含三个分析子句:
窗口()
排序(order by)
分组(partition by)
*/
-- 统计部门编号平均工资,部门编号,部门人员名单
select avg(sal),DEPTNO
from EMP
group by deptno;
--普通的group by不能显示部门人员名单
select avg(sal)over(partition by DEPTNO),DEPTNO,ENAME
from EMP
/*
row_number() over(partition by ... order by ...)
partition by 和group by 一样效果
order by 体现的是连续的统计结果
*/
select sal,avg(sal)over(partition by DEPTNO order by sal),DEPTNO,ENAME
from emp;
-- row_number,连续的编号,其实就是行编号
select row_number()over(order by sal) 行编号,ENAME,SAL
from EMP;
-- rank
select rank()over(order by sal) rank排名,ENAME,SAL--相同的sal排名一样,后面的+n
from EMP;
--dense_rank
select dense_rank()over(order by sal) rank排名,ENAME,SAL--相同的sal排名一样,后面的+1
from EMP;
-- first_value ,last_value
select first_value(ename) over(partition by deptno),last_value(ename) over(partition by deptno),ename,sal,DEPTNO
from EMP;
--计算每个部门薪水的平均值,并将每个员工的平均值和该部门的平均值比较
select DEPTNO,ename,sal,round(average_sal_dept,0) as average_sal_dept,
round(sal-average_sal_dept,0) as sal_variance
from (select deptno,ename,sal,avg(sal)over(partition by deptno) as average_sal_dept from emp);
-- 查询本单位最先招聘的3个雇员
select rownum as rank,ENAME,ename,HIREDATE
from (select ename,HIREDATE from emp order by HIREDATE nulls last ) where ROWNUM<=3;
-- 练习
-- 显示BLAKE的所有下级,包括直接和间接下级
select empno,ENAME,LEVEL,DEPTNO
from emp
start with ENAME='BLAKE'
connect by prior empno=MGR--父节点的empno等于子节点的mgr
order by LEVEL asc;
--显示对于雇员SMITH的经理的层次,包括级别和姓名
select empno,ENAME,LEVEL,DEPTNO
from emp
start with ENAME='SMITH'
connect by prior mgr=EMPNO--父节点的empno等于子节点的mgr
order by LEVEL asc;
-- 查询员工信息的同时,查询员工工资与所在部门最低、最高工资的差额
select ENAME,DEPTNO,sal,sal-amin,amax-sal
from(select DEPTNO,ENAME,sal,max(sal)over(partition by DEPTNO) as amax, min(sal)over(partition by DEPTNO) as amin from emp);
-- 数据类型
/*
1.数值类型
1.1 NUMBER:精度,也称总位数,取值范围1-38,默认为38
NUMBER(precision,scale)第一个为总位数,第二个为小数点右边的位数
输入数 Number表示 最终结果
1234567.89 Number 1234567.89
1234567.89 Number(9,3) 出错
1234567.89 Number(9,1) 1234567.9
1234567.89 Number(*,1) 1234567.9
1234567.89 Number(5,-2) 1234600
1.2 BINARY_FLOAT/BINARY_DOUBLE 浮点数,单精度和双精度
oracle在语法上支持的其他数值数据类型:NUMERIC(p,a) DECIMAL(p,a) DEC(p,s) INTEGER INT SMALLINT FLOAT(b)
create table test(
tid integer允许这么写,自动进行转换
)
*/
/*
2.字符类型
2.1 CHAR和VARCHAR2
char最大长度为2000字节,char的长度固定,一个汉字占两个字节。
eg:
char(5)
varchar2最大长度为4000字节,可变长度的字符串,一个汉字两个字节
varchar2(10)最大为10,可少不可多
2.2NCHAR和NVARCHAR2
NCHAR:根据字符集而定的固定长度字符串,最大长度2000 bytes
NVARCHAR2:根据字符集而定的可变长度字符串,最大长度4000 bytes
例如:字符集设置成ZHS16GBK:汉字占2个字节
字符集设置成AL32UTF8:汉字占3个字节
*/
/*
3.日期类型
3.1 DATE类型
DATE是最常用的数据类型,日期数据类型存储日期和时间信息。
虽然可以用字符或数字类型表示日期和时间信息,但是日期数据类型具有特殊关联的属性。
为每个日期值,Oracle 存储以下信息: 世纪、 年、 月、 日期、 小时、 分钟和秒。
一般占用7个字节的存储空间。
3.2 TIMESTAMP类型 (小数秒)
这是一个7字节或12字节的定宽日期/时间数据类型。
它与DATE数据类型不同,因为TIMESTAMP可以包含小数秒,
带小数秒的TIMESTAMP在小数点右边最多可以保留9位
*/
/*
ROWID/UROWID类型
ROWID是数据库中一行的地址。
Oracle中除了索引组织表(IOT)外的所有行
都有ROWID。ROWID主要用于作为物理地址
来减少行更新操作的操作代价,加快访问任何
表中某一行的速度。
UROWID是ROWID的“近亲”。它用于比如
索引组织表(IOT)和通过异构数据库网关访问的,
没有固定ROWID的表。
*/
select ROWID,ENAME
from emp;
/*
序列(补充)
序列就是一个计数器,属于用户创建的数据库对象,
可以被多个用户共享。每使用一次,它的值就增加1。
*/
--创建序列
drop sequence SEQUENCE_NAME;
create sequence sequence_name
INCREMENT BY 1--每次增长1
START WITH 1--从1开始
MAXVALUE 1000--最大值
cycle--循环
cache 10;
-- 使用序列
select SEQUENCE_NAME.nextval--下一个序号
from dual;
select SEQUENCE_NAME.currval--当前序号
FROM dual;
/*
Insert into classtable2
values(SEQUENCE_NAME.NEXTVAL,'电信01');//能够代替自动增长,如果本次sal语句出错,那么序列已经调用了一次nextval,在调用的话会隔着一个。
修改序列
ALTER SEQUENCE sequence_name
INCREMENT BY n
MAXVALUE n| NOMAXVALUE
MINVALUE n| NOMINVALUE
CYCLE | NOCYCLE
*/
--oracle的视图和同义词
/*
视图是对根据预定义的选择标准由一个或多个行的集合
建立起来的动态表的静态定义
eg:如果有一个查询结果你要经常要在它的基础上进行查询
你可以把这个查询结果作为一个视图来使用。
视图还可以隐藏数据的复杂性。同时可以处理权限问题,有的你能查到,有的你没有权限查到。
使用视图的原因很多,比如:集中用户使用的
数据、隐藏数据的复杂性、简化权限管理以及
为向其他应用程序输出而重新组织数据等等
eg:为emp表制作几个视图,包括基本信息,没有sal信息,对普通员工开放,员工可以查询到,但不能查询到sal信息
创建包含sal信息的视图,对领导开放,让领导可以查阅到员工的所有信息。这就解决了权限问题。
*/
--视图的种类
--1.关系视图
/*
表中的数据通过查询基表,可以将其输出看作输出一个表。
可以长期使用
CREATE [OR REPLACE] [FORCE | NOFORCE](强制force或者不强制noforce建立) VIEW
[USER.] view_name(视图名字)
[column1[, column2]…]
AS query(子查询)
[WITH CHECK OPTION [CONSTRAINT constraint_name](query中带where语句的约束)
[WITH READ ONLY](只读视图,不能用来更改)
*/
--eg:
create or replace force view my_view
as
select ename,DEPTNO,sal
from emp
with read only ;--只读权限,不能修改视图。
--with check option 检查性选项,根据where子句的条件,始终满足 插入的数据,或者修改的数据 符合where的条件
select *
from my_view;
/*
insert into my_view
values ('MSI',3000,10);
用视图去添加数据,实际上会添加到原表中,但是如果添加数据不能满足表中格式,如主键,非空等等,会添加失败。
delete from my_view
where ename='SMITH'
*/
select *
from user_views
where view_name='MY_VIEW'
/*
如果视图包含了下面的内容,那么不能通过视图删除
基本表中的数据:
¤ 分组函数,例如sum、avg、min、max等;
¤ group by子句;
¤ distinct关键字;
¤ 包含了表达式;
¤ rownum伪列。
*/
-- 内嵌视图
/*
子查询,只能当前视图
SELECT a.EName, a.ESal, DName, b.maxsal
FROM Employee a,
(SELECT DID, MAX(ESal) maxsal
FROM Employee GROUP BY DID) b,
Department dept
WHERE a.DID = b.DID
AND a.ESal = b.maxsal AND b.DID=dept.DID;
*/
-- 对象视图
/*
在ORACLE中,可以自定义一个对象类型
定义一个类型的SQL语法所需:
create or replace type employee as object(
employee_id number,employee_name varchar2(20)
,employee_position varchar2(20)
)
create table emp of employee;
create or replace view ov_employee of employee
with object oid(employee_id) as
select employee_id a_id, employee_name, employee_position from employees;
insert into ov_employee values( employee(6, '张三','测试工程师'));
*/
create or replace type employee as object(
employee_id number,employee_name varchar2(20)
,employee_position varchar2(20)
);
create table tmp_employee of employee;
declare
e employee;
a number(4);
begin
e:=employee(1,'zs','dalian');
insert into tmp_employee
values (e);
end;
select *
from tmp_employee;
/**
declare
e employee;
begin
select value(t) into e
from tmp_employee t
where employee_id=1;
dbms_output.put_line
end;*/
--对象视图的创建
create or replace view ov_employee of employee
with object oid(employee_id)
as
(select employee_id a_id, employee_name, employee_position from tmp_employee);
select * from ov_employee;
-- 物化视图
/*
视图中查询出来的数据备份
*/
--最后一节课
--top N分析
--得到最先参加工作的3个员工的名单。
--rownum
select HIREDATE,empno,ENAME,ROWNUM
from (select HIREDATE,empno,ENAME from emp order by HIREDATE)
where ROWNUM<=3;
--注意rownum如果要是条件为》=,》符号,需要再多写一个子查询
select HIREDATE,ra
from (select HIREDATE,empno,ENAME,ROWNUM as ra
from (select HIREDATE,empno,ENAME from emp order by HIREDATE)
where ROWNUM<=5)
where ra>=2;
-- 事务
-- 数据库在并发性问题上的处理:事务和锁
/*
事务是数据库区别于文件系统的特性之一,所谓事务,就是用户定义的一个数据库操作序列,这些序列要么全做,要么全不做,是一个不可分割的工作单位。
事务的特性:
A(原子性)Atomicity:事务就像原子一样,不可分割,要么全成功,要么全失败
C(一致性)Consistency:一旦事务完成,不管是成功的,还是失败的,整个系统处于数据一致的状态。
I(隔离性)Isolation:一个事务的执行不会被另一个事务干扰。比如两个人同时从一个账户中取钱,通过事务的隔离性保证账户余额的正确性。
D(持久性)Durability:一旦事务提交,对数据的改变就是永久的,不能回滚。
事务控制语句:
COMMIT
ROLLBACK
SAVEPOINT
*/
SAVEPOINT A;
DELETE FROM tmp_employee WHERE EMPLOYEE_ID=1;
SELECT * FROM tmp_employee;
ROLLBACK to savepoint A;
COMMIT ;
-- 管理安全性
--Oracle-SQL开发: 用户、权限与角色
/*
用户是数据库的使用者。一般是由DBA来创建和维护的,创建用户后,用户不可以执行任何Oracle操作,包括建立会话。
只有赋予用户相关的权限,用户才能执行权限允许范围内的操作。
创建用户语法:
create user user_name
identified by password(设置密码)
:eg
create user test identified by test;
*/
create user test identified by test;
grant create session to test;
--删除账号
drop user test cascade;
--修改账号的密码:
alter user test identified by test1;
--设置账号锁定/解锁
alter user test account lock;--unlock为解锁
/*
权限
分类:系统权限和对象全新
系统权限:允许用户在数据库中执行指定的行为,一般可以理解为比较通用的一类权限
对象权限:允许用户访问和操作一个指定的对象,该对象是一个确切存储
授予系统权限:
grant sys_priv_list to user_list [with admin option]
with admin option:允许权限的接受者再把此特权授予其他用户。
--eg:授予test用户权限:
create user test1 identified by test1;
grant create session to test1 with admin option;
这样进入test1用户下,可以在test1下的窗口授予此特权授予其他用户(如test2)。
如果用户取消了test1的session权限,不会影响test2的权限,即不传递回收。
授予对象权限
grant object_priv|[ALL PRIVILEGES]|[{column}]
ON [schema.]object
TO {user|public} [with admin option]
eg:
grant select
on scott.emp
to test2 (授予test2用户select操作,不能delete,update等等操作)
回收用户权限:
REVOKE CONNECT, RESOURCE FROM 用户名;
REVOKE SELECT ON 表名 FROM 用户名;
REVOKE SELECT, INSERT, DELETE ON 表名 FROM 用户名1, 用户名2;
*/
-- 定义角色
create role myrole;
--为角色授权
--grant 权限列表 to 角色
grant create session to myrole;
--通过角色为用户授权
--grant myrole to test;test会拥有myrole的所有权限
--回收权限
--revoke 权限 from 角色