一、数据的更新操作
DML操作语法之中,除了查询之外还有数据的库的更新操作,数据的更新操作主要指的是:增加、修改、删除数据,但是考虑到emp表以后还要继续使用,所以下面先将emp表复制一份,输入如下指令:
CREATE TABLE myemp AS SELECT * FROM emp;
这种语法是Oracle中支持的操作,其他数据库不一样。
1、数据增加
如果现在要想实现数据的增加操作,则可以使用如下的语法完成:
INSERT INTO 表名称 [(字段1,字段2,…)] VALUES(值1,值2,…);
如果要想进行增加数据的话,则以下的几种数据类型要分别处理:
- 增加数字:直接编写数字,例如:123;
- 增加字符串:字符串应该使用“’“声明;
- 增加DATE数据:
- 第一种:可以按照已有的字符串的格式编写字符串,例如“’17-12月-80’”;
- 第二种:利用TO_DATE()函数将字符串变为DATE型数据;
- 第三种:如果设置的时间为当前系统时间,则使用SYSDATE;
可是对于数据的增加也有两种操作格式:完整型、简便型;
范例:增加数据 —— 完整语法编写
INSERT INTO myemp(empno,ename,hiredate,sal,mgr,job,comm)
VALUES(8888,'张三',TO_DATE('1960-08-17','yyyy-mm-dd'),8000,7369,'清洁工',1000);
INSERT INTO myemp(empno,ename,hiredate,sal,mgr,job,deptno)
VALUES(8889,'李四',SYSDATE,3000,7369,'清洁工',30);
范例:增加数据 —— 简便语法,不写增加的列名称
INSERT INTO myemp VALUES(8889,'李四','清洁工',7369,SYSDATE,3000,null,30);
很明显虽然简便语法代码少了,可是这种操作并不可取,所以在实际的开发之中,没有任何一个人会写简便语法,这样根本就不利于程序的维护,都编写完整的操作。
2、数据修改
如果要想修改表中已有的数据,则可以按照如下的语法进行:
UPDATE 表名称 SET 更新字段1=更新值1,更新字段2=更新值2,… [WHERE 更新条件(s)];
范例:更新雇员编号是7369的基本工资为5000,奖金为2000,职位修改为MANAGER,雇佣日期修改为今天
UPDATE myemp SET sal=5000,comm=2000,job='MANAGER',hiredate=SYSDATE WHERE empno=7369;
范例:所有人的工资改为7500
UPDATE myemp SET sal=7500;
如果更新时候不加上更新操作,则意味着更新全部的数据,但是这种做法绝对不可取,如果现在表中的数据量较大的话,这种更新所耗费的时间是相当长的,而且性能也会明显降低。
3、数据删除
当数据不再需要之后,就可以使用以下的语法删除数据:
DELETE FROM 表名称 [WHERE 删除条件(s)];
与更新一样,如果没有写删除条件的话,则表示删除全部数据;
范例:删除所有在1987年雇佣的雇员
DELETE FROM myemp WHERE TO_CHAR(hiredate,'yyyy')=1987;
一定要记住,如果删除的时候没有匹配条件的数据存在,则更新的记录为“0”,包括更新操作也是一样的。
范例:删除表中的全部记录
一般对于删除的操作而言,尽可能少去使用,包括以后在进行系统开发的时候,对于所有的删除操作之前实际上都建议大家先给出一个确认的提示框,以防止用户误删除。
二、事务处理
对于数据表的操作,很明显查询要比更新操作更加的安全,因为更新操作有可能会出现错误,以导致没有按照既定的要求正确的完成更新操作。
但是在很多时候更新有可能会有多条指令共同完成,例如:以银行转帐的方式为例:
- 判断A的账户上是否有5000W;
- 判断B账户是否存在并且状态是否正常;
- 从A的账户上移走5000W;
- 向B的账户之中增加5000W;
- 向银行支付手续费用5000;
以上的五个操作是一个整体,可以理解为一个完整的业务,如果这之中第三点出错了,那么其他的操作呢?所有的操作都应该不再执行,并且回归到最原始的状态,而这个操作流程就是事务的操作。
所有的事务处理操作都是针对于每一个session进行的,在Oracle数据库之中,把每一个连接到数据库上的用户都称为一个session,每一个session之间彼此独立,不会有任何的通讯,而每一个session独享自己的事务控制,而事务控制之中主要使用两个命令:
-
事务的回滚:ROLLBACK,更新操作回到原点;
-
事务的提交:COMMIT,真正的发出更新的操作,一旦提交之后无法回滚;
但是这样一来也会出现一些问题,例如:某一个session在更新数据表的时候还没有提交事务,其他session是无法更新的,必须等待之前的session提交后才可以;
这种问题从大的方面讲可以称为死锁,但是在Oracle之中死锁有很多的种类,这些与开发者没有太大的关系,是由DBA负责的。
所有的数据更新一定都会受到事务的控制。
三、数据伪列
数据伪列指的是用户不需要处理的列,而是由Oracle自行维护的数据列,在Oracle之中有两个数据伪列:ROWNUM、ROWID;
1、 ROWNUM
ROWNUM从单词含义上讲应该表示的是行号,实际上ROWNUM为每一个显示的记录都会自动的随着查询生成行号,例如,下面通过两个代码观察:
SELECT ROWNUM,empno,ename,job,hiredate,sal FROM emp;
此时的ROWNUM行号并不是永久固定的;
SELECT ROWNUM,empno,ename,job,hiredate,sal FROM emp WHERE deptno=30;
是每次动态的重新生成的,那么既然有了ROWNUM之后,下面就可以实现数据的部分显示;
范例:查询前5条记录
SELECT ROWNUM,empno,ename,job,hiredate,sal FROM emp
WHERE ROWNUM<=5;
范例:查询6-10条记录
按照正常的思维肯定是直接进行BETWEEN…AND的判断;
SELECT ROWNUM,empno,ename,job,hiredate,sal FROM emp
WHERE ROWNUM BETWEEN 6 AND 10;
这个时候并没有返回任何的数据,因为ROWNUM不是真实列,而要想真正的实现这种查询,思路是:先查询前10条记录,之后再显示后5条记录,要依靠子查询完成。
SELECT * FROM(
SELECT ROWNUM m,empno,ename,job,hiredate,sal FROM emp
WHERE ROWNUM<=10) temp
WHERE temp.m>5;
如果现在按照这个思路,下面就可以给出日后程序中所需要分页的功能实现。
范例:显示前5条记录
当前所在页(currentPage)为1;
每页显示的记录长度(lineSize)为5;
第一页:
SELECT * FROM(
SELECT ROWNUM m,empno,ename,job,hiredate,sal FROM emp
WHERE ROWNUM<=5) temp
WHERE temp.m>0;
范例:显示中间的5条记录
当前所在页(currentPage)为2;
每页显示的记录长度(lineSize)为5;
第二页:
SELECT * FROM(
SELECT ROWNUM m,empno,ename,job,hiredate,sal FROM emp
WHERE ROWNUM<=10) temp
WHERE temp.m>5;
范例:显示第三页的内容,currentPage=3,lineSize=10;
SELECT * FROM(
SELECT ROWNUM m,empno,ename,job,hiredate,sal FROM emp
WHERE ROWNUM<=15) temp
WHERE temp.m>10;
以上的程序就是分页显示操作的核心代码。
2、 ROWID
ROWID表示的是每一行数据保存的物理地址的编号,例如,观察如下的查询:
SELECT ROWID,deptno,dname,loc FROM dept;
此时返回许多的记录:
ROWID DEPTNO DNAME LOC
------------------ ---------- -------------- -------------
AAAL+XAAEAAAAANAAA 10 ACCOUNTING NEW YORK
AAAL+XAAEAAAAANAAB 20 RESEARCH DALLAS
AAAL+XAAEAAAAANAAC 30 SALES CHICAGO
AAAL+XAAEAAAAANAAD 40 OPERATIONS BOSTON
每一条记录的ROWID都不会重复,所以即便表中所有列的数据内容都重复了,ROWID也是不会重复的,而且以一个ROWID为例,说明ROWID组成,例如:AAAL+XAAEAAAAANAAA
- 数据对象号:AAAL+X;
- 相对文件号:AAE;
- 数据块号:AAAAAN;
- 数据行号:AAA;
面试题:请删除表中的重复记录
现在项目之中由于管理不善,所以导致出现了许多重复的信息,为了说明问题,下面为表中增加若干条记录。
INSERT INTO dept(deptno,dname,loc) VALUES (21,'RESEARCH','DALLAS');
INSERT INTO dept(deptno,dname,loc) VALUES (31,'SALES','CHICAGO');
INSERT INTO dept(deptno,dname,loc) VALUES (32,'SALES','CHICAGO');
INSERT INTO dept(deptno,dname,loc) VALUES (41,'OPERATIONS','BOSTON');
INSERT INTO dept(deptno,dname,loc) VALUES (42,'OPERATIONS','BOSTON');
INSERT INTO dept(deptno,dname,loc) VALUES (43,'OPERATIONS','BOSTON');
COMMIT;
此时的数据显示是:
SQL> select * from dept;
DEPTNO DNAME LOC
---------- -------------- -------------
10 ACCOUNTING NEW YORK
20 RESEARCH DALLAS
30 SALES CHICAGO
40 OPERATIONS BOSTON
21 RESEARCH DALLAS
31 SALES CHICAGO
32 SALES CHICAGO
41 OPERATIONS BOSTON
42 OPERATIONS BOSTON
43 OPERATIONS BOSTON
已选择10行。
现在要求删除掉所有重复的记录,保留最早增加的记录内容。
最终显示效果:
SQL> select * from dept;
DEPTNO DNAME LOC
---------- -------------- -------------
10 ACCOUNTING NEW YORK
20 RESEARCH DALLAS
30 SALES CHICAGO
40 OPERATIONS BOSTON
先按照查询的方式做,首先找到所有重复的数据,重复的数据就比较容易了,按照部门名称及位置分组,之后统计个数,如果个数大于1,则表示重复。
SELECT dname,loc,MIN(ROWID)
FROM dept
GROUP BY dname,loc
HAVING COUNT(deptno)>1;
此时返回的三个ROWID,与最早的ROWID比较一下。
ROWID DEPTNO DNAME LOC
------------------ ---------- -------------- -------------
AAAL+XAAEAAAAANAAA 10 ACCOUNTING NEW YORK
AAAL+XAAEAAAAANAAB 20 RESEARCH DALLAS
AAAL+XAAEAAAAANAAC 30 SALES CHICAGO
AAAL+XAAEAAAAANAAD 40 OPERATIONS BOSTON
SQL> SELECT dname,loc,MIN(ROWID)
2 FROM dept
3 GROUP BY dname,loc
4 HAVING COUNT(deptno)>1;
DNAME LOC MIN(ROWID)
-------------- ------------- ------------------
SALES CHICAGO AAAL+XAAEAAAAANAAC
RESEARCH DALLAS AAAL+XAAEAAAAANAAB
OPERATIONS BOSTON AAAL+XAAEAAAAANAAD
数据插入的早,ROWID就小,所以下一步首先必须确定的是不能删除的ROWID,去掉之前的限制(COUNT()>1),表示按照部门名称及位置分组,取出每一个最小的ROWID;
SELECT MIN(ROWID)
FROM dept
GROUP BY dname,loc;
以上的数据是删除的,所以下面编写DELETE语句:
DELETE FROM dept
WHERE ROWID NOT IN(
SELECT MIN(ROWID)
FROM dept
GROUP BY dname,loc);
COMMIT;
此时就是根据ROWID完成的,而这道题目也就是ROWID现在为止的唯一可以看的见的作用。
在所有的伪列之中,只有ROWNUM是以后开发之中最为重要的部分,一定要掌握,而对于ROWID知道就行了,不必做太深入的了解。
相关推荐
Oracle学习笔记(rownum和rowid),有具体的代码案例讲解rownum和rowid
在Oracle SQL中,`ROWID`和`ROWNUM`是两个非常重要的概念,它们在数据库查询和数据操作中起着至关重要的作用。本文将详细探讨这两个特性,包括它们的定义、用途以及如何在实际场景中有效利用它们。 一、ROWID详解 `...
Oracle ROWNUM 伪列详解 Oracle 的 ROWNUM 伪列是一个非常重要的概念,它对结果集加的一个伪列,即先查到结果集之后再加上去的一个列。了解 ROWNUM 的意义是非常重要的,否则可能会出现莫名其妙的结果。 ROWNUM ...
Oracle ROWNUM 用法详解 ROWNUM 是 Oracle 系统中一个伪列,用于对查询返回的行进行编号,从 1 开始,每行递增 1。ROWNUM 可以用于限制查询返回的总行数,但需要注意的是,ROWNUM 不能以任何表的名称作为前缀。 ...
在"rownum和rowid详解_平凡的三叶草_新浪博客.mht"中,可能会详细解释ROWNUM的使用方式,如限制返回结果的数量(如只取前N条记录)以及在分页查询中的作用。 3. **视图(View)**: Oracle视图是从一个或多个表或...
Oracle数据库中的ROWNUM是一个非常重要的概念,特别是在处理大型数据集时进行分页查询。ROWNUM是一个伪列,意味着它并不是数据库表中实际存在的列,而是Oracle数据库在执行查询时动态生成的一个序列号,用于标记查询...
Oracle提供了两种主要的伪列:rowid和rownum,它们各自拥有独特的功能和用途。 一、rowid伪列 1. rowid原理 rowid是Oracle用来唯一标识表中每一行数据的物理地址,它是一个10字节的值,但在显示时以18字节的字符串...
Oracle提供了一些内置的伪列供用户使用,如`ROWID`和`ROWNUM`等,这些伪列可以帮助开发人员更方便地进行查询、排序等操作。 #### 二、ROWID与ROWNUM详解 **ROWID:** - **定义**:ROWID是Oracle中用于唯一标识表中...
Oracle SQL 语句优化是数据库性能提升的关键环节,以下是对53个规则的详解中几个关键点的深入阐述: 1. 选择合适的优化器: ORACLE 提供三种优化器:基于规则(RULE)、基于成本(COST)和选择性(CHOOSE)。基于...
Oracle函数详解涵盖了从基础操作到复杂查询的各个方面,理解和熟练运用这些函数和操作对于有效管理Oracle数据库至关重要。无论是数据查询、数据更新还是数据统计,都有相应的SQL语句和函数支持,使得数据处理变得...
Hint.pdf Oracle中rowid与rownum的使用.pdf Oracle优化 之 索引.pdf Oracle优化器.pdf STATSPACK详解.pdf 学用ORACLE_AWR和ASH特性.pdf 执行计划.pdf
这包括使用SQL语言来进行数据的增删改查(DML操作),以及利用各种查询技术获取所需的数据。 - **SQL简介**:SQL(Structured Query Language)是一种用于管理关系型数据库的标准语言。了解基本的SQL语法对于使用...
Oracle语句优化是数据库管理的关键任务,以提升SQL查询的执行效率和系统整体性能。本文将详细介绍53个Oracle SQL优化规则,分为几个主要方面进行阐述。 首先,选择合适的优化器至关重要。Oracle提供了三种优化器:...
### Oracle 11g 操作详解 #### 一、Oracle 11g 安装与配置 ##### 1.1 安装准备 - **安装文件**:获取 Oracle 11g 的安装文件,通常包括数据库服务器端和客户端工具。 - **系统检测**:在安装前确保计算机满足 ...
6. Oracle PL-SQL语言基础 7. Oracle的分布式管理 8. ORACLE的数据类型 9. Oracle数据库碎片整理 10.ORACLE性能调整1 11.ORACLE性能调整2 12.Oracle专家调优秘密 13.PL_SQL单行函数和组函数详解 14...
以上就是关于Oracle中`RowID`、`RowNum`的使用方法,以及Oracle分页语句和存储过程的创建与使用的详细介绍。这些知识点对于Oracle开发人员来说非常重要,熟练掌握它们能够帮助你在实际工作中更高效地解决问题。
在Oracle数据库系统中,高级SQL技能是进行高效数据管理、查询优化和复杂数据处理的基础。 1. 集合操作包括UNION、UNION ALL、INTERSECT和MINUS等,它们用于合并两个或多个SELECT语句的结果集。UNION和UNION ALL用于...
Oracle数据库的优化是提高系统性能的关键,涉及到查询速度、资源利用率和整体系统效率。本文将详细探讨30个Oracle语句优化规则,旨在帮助数据库管理员和开发者提升数据库性能。 1. 选择合适的优化器 Oracle提供了三...