1、with table as 相当于建个临时表(用于一个语句中某些中间结果放在临时表空间的SQL语句),Oracle 9i 新增WITH语法,可以将查询中的子查询命名,放到SELECT语句的最前面。
语法就是
with tempname as (select ....)
select ...
例子:
with t as (select * from emp where depno=10)
select * from t where empno=xxx
with
wd as (select did,arg(salary) 平均工资 from work group by did),
em as (select emp.*,w.salary from emp left join work w on emp.eid = w.eid)
select * from wd,em where wd.did =em.did and wd.平均工资>em.salary;
2、何时被清除
临时表不都是会话结束就自动被PGA清除嘛! 但with as临时表是查询完成后就被清除了!
23:48:58 SCOTT@orcl> with aa as(select * from dept)
23:57:58 2 select * from aa;
DEPTNO DNAME LOC
---------- -------------- -------------
10 ACCOUNTING NEW YORK
20 RESEARCH DALLAS
30 SALES CHICAGO
40 OPERATIONS BOSTON
已用时间: 00: 00: 00.12
23:58:06 SCOTT@orcl> select * from aa;
select * from aa
*
第 1 行出现错误:
ORA-00942: 表或视图不存在
已用时间: 00: 00: 00.02
23:58:14 SCOTT@orcl>
3、就这一功能来说,子查询就可以达到啊,为什么要用with呢? 用with有什么好处?
都能写,但执行计划不同的。当有多个相似子查询的时候,用with写公共部分,因为子查询结果在内存临时表中,执行效率当然就高啦~
4、问题:
有张表数据如下:
aaa 高
bbb 低
aaa 低
aaa 高
bbb 低
bbb 高
需要得到下列结果,
高 低
aaa 2 1
bbb 1 2
问 SQL 语句怎么写??
答案:
with tt as (
select 'aaa' id, '高' value from dual union all
select 'bbb' id, '低' value from dual union all
select 'aaa' id, '低' value from dual union all
select 'aaa' id, '高' value from dual union all
select 'bbb' id, '低' value from dual union all
select 'bbb' id, '高' value from dual)
SELECT id,
COUNT(decode(VALUE, '高', 1)) 高,
COUNT(decode(VALUE, '低', 1)) 低
FROM tt
GROUP BY id;
===================================================================
扩展:
Oracle9i新增WITH语法,可以将查询中的子查询命名,放到SELECT语句的最前面。
一个简单的例子:
SQL> WITH
2 SEG AS (SELECT SEGMENT_NAME, SUM(BYTES)/1024 K FROM USER_SEGMENTS GROUP BY SEGMENT_NAME),
3 OBJ AS (SELECT OBJECT_NAME, OBJECT_TYPE FROM USER_OBJECTS)
4 SELECT O.OBJECT_NAME, OBJECT_TYPE, NVL(S.K, 0) SIZE_K
5 FROM OBJ O, SEG S
6 WHERE O.OBJECT_NAME = S.SEGMENT_NAME (+)
7 ;
OBJECT_NAME OBJECT_TYPE SIZE_K
------------------------------ ------------------- ----------
DAIJC_TEST TABLE 128
P_TEST PROCEDURE 0
IND_DAIJC_TEST_C1 INDEX 128
通过WITH语句定义了两个子查询SEG和OBJ,在随后的SELECT语句中可以直接对预定义的子查询进行查询。从上面的例子也可以看出,使用WITH语句,将一个包含聚集、外连接等操作SQL清晰的展现出来。
WITH定义的子查询不仅可以使查询语句更加简单、清晰,而且WITH定义的子查询还具有在SELECT语句的任意层均可见的特点。
即使是在WITH的定义层中,后定义的子查询都可以使用前面已经定义好的子查询:
SQL> WITH
2 Q1 AS (SELECT 3 + 5 S FROM DUAL),
3 Q2 AS (SELECT 3 * 5 M FROM DUAL),
4 Q3 AS (SELECT S, M, S + M, S * M FROM Q1, Q2)
5 SELECT * FROM Q3;
S M S+M S*M
---------- ---------- ---------- ----------
8 15 23 120
利用WITH定义查询中出现多次的子查询还能带来性能提示。Oracle会对WITH进行性能优化,当需要多次访问WITH定义的子查询时,Oracle会将子查询的结果放到一个临时表中,避免同样的子查询多次执行,从而有效的减少了查询的IO数量。
WITH能用在SELECT语句中,UPDATE和DELETE语句也是支持WITH语法的,只是需要版本支持:
http://www.oracle.com.cn/viewthread.php?tid=83530
=============================================================================
with
sql1 as (select to_char(a) s_name from test_tempa),
sql2 as (select to_char(b) s_name from test_tempb where not exists (select s_name from sql1 where rownum=1))
select * from sql1
union all
select * from sql2
union all
select 'no records' from dual
where not exists (select s_name from sql1 where rownum=1)
and not exists (select s_name from sql2 where rownum=1);
再举个简单的例子
with a as (select * from test)
select * from a;
其实就是把一大堆重复用到的SQL语句放在with as 里面,取一个别名,后面的查询就可以用它
这样对于大批量的SQL语句起到一个优化的作用,而且清楚明了
这是搜索到的英文文档资料(说得比较全,但是本人英文特菜,还没具体了解到,希望各高手具体谈谈这个with
as 的好处)
About Oracle WITH clause
Starting in Oracle9i release 2 we see an incorporation of the SQL-99 “WITH clause”, a tool for materializing subqueries to save Oracle from having to re-compute them multiple times.
The SQL “WITH clause” is very similar to the use of Global temporary tables (GTT), a technique that is often used to improve query speed for complex subqueries. Here are some important notes about the Oracle “WITH clause”:
? The SQL “WITH clause” only works on Oracle 9i release 2 and beyond.
? Formally, the “WITH clause” is called subquery factoring
? The SQL “WITH clause” is used when a subquery is executed multiple times
? Also useful for recursive queries (SQL-99, but not Oracle SQL)
To keep it simple, the following example only references the aggregations once, where the SQL “WITH clause” is normally used when an aggregation is referenced multiple times in a query.
We can also use the SQL-99 “WITH clause” instead of temporary tables. The Oracle SQL “WITH clause” will compute the aggregation once, give it a name, and allow us to reference it (maybe multiple times), later in the query.
The SQL-99 “WITH clause” is very confusing at first because the SQL statement does not begin with the word SELECT. Instead, we use the “WITH clause” to start our SQL query, defining the aggregations, which can then be named in the main query as if they were “real” tables:
WITH
subquery_name
AS
(the aggregation SQL statement)
SELECT
(query naming subquery_name);
Retuning to our oversimplified example, let’s replace the temporary tables with the SQL “WITH clause”:
WITH
sum_sales AS
select /*+ materialize */
sum(quantity) all_sales from stores
number_stores AS
select /*+ materialize */
count(*) nbr_stores from stores
sales_by_store AS
select /*+ materialize */
store_name, sum(quantity) store_sales from
store natural join sales
SELECT
store_name
FROM
store,
sum_sales,
number_stores,
sales_by_store
where
store_sales > (all_sales / nbr_stores)
;
Note the use of the Oracle undocumented “materialize” hint in the “WITH clause”. The Oracle materialize hint is used to ensure that the Oracle cost-based optimizer materializes the temporary tables that are created inside the “WITH” clause. This is not necessary in Oracle10g, but it helps ensure that the tables are only created one time.
It should be noted that the “WITH clause” does not yet fully-functional within Oracle SQL and it does not yet support the use of “WITH clause” replacement for “CONNECT BY” when performing recursive queries.
To see how the “WITH clause” is used in ANSI SQL-99 syntax, here is an excerpt from Jonathan Gennick’s great work “Understanding the WITH Clause” showing the use of the SQL-99 “WITH clause” to traverse a recursive bill-of-materials hierarchy
The SQL-99 “WITH clause” is very confusing at first because the SQL statement does not begin with the word SELECT. Instead, we use the “WITH clause” to start our SQL query, defining the aggregations, which can then be named in the main query as if they were “real” tables:
WITH
subquery_name
AS
(the aggregation SQL statement)
SELECT
(query naming subquery_name);
Retuning to our oversimplified example, let’s replace the temporary tables with the SQL “WITH” clause”:
- 浏览: 219940 次
文章分类
- 全部博客 (195)
- CSS/HTML/JS (26)
- 动态代理 (1)
- java编程思想 (2)
- maven (9)
- java 基础 (36)
- 开发工具 (6)
- Java 调试体系 (4)
- Java Web (2)
- oracle 数据库 (24)
- 操作系统 (6)
- Java PDF处理 (2)
- HTTP (7)
- XML (5)
- Spring (7)
- 编码和解码 (2)
- 国际化 (1)
- WebService (5)
- 服务器部署 (2)
- J2EE (1)
- Hibernate (2)
- JVM (1)
- weblogic (5)
- jQuery学习 (6)
- 权限设计 (2)
- GitHub (2)
- 数据结构与算法 (2)
- json (1)
- POI (1)
- 正则表达式 (3)
- 杂谈 (1)
- 搜索相关 (1)
- 版本管理相关知识 (4)
- Linux (3)
- Mybaties (1)
- 计算机知识 (2)
- 设计模式 (2)
- 工作流 (3)
- 论坛 (2)
- Git (1)
最新评论
发表评论
-
PL/SQL中集合出现“ORA-06533:下表超出数量”的问题解决
2017-05-04 10:32 641PL/SQL中集合出现“ORA-06533:下表超出数量”的 ... -
pl/sql developer 怎么导入sql文件
2016-12-15 17:11 760在确定你的.sql文件没有错误的情况下,在pl/sql命令行 ... -
plsql 32位,Oracle Client 64位 无法读取tnsnames.ora文件
2016-11-05 15:21 1664ORACLE_HOME=C:\app\fjz\product\ ... -
oracle split去逗号,行列转换
2016-08-24 20:40 29651.针对 '1','2','3','4','5'(逗号在字 ... -
Oracle数据库中chr()、ascii()、asciistr()、convert()函数的使用(附ASCII编码表)
2016-08-24 15:42 2656在oracle数据库中有很多的转换函数,主要有chr()、a ... -
字符 转换 为blob字段的一些方法。
2016-08-24 15:40 1719我们经常会遇到把字符类型的数据以BLOB的方式存放到orac ... -
如何判断oracle大字段(clob)为空?
2016-08-20 21:09 1831--assume x is a clob field -- ... -
一、物化视图的一般用法
2016-06-20 15:59 1154物化视图是一种特殊的 ... -
JDBC操作LOB字段详解
2016-06-01 20:58 695在Oracle中,lob类型主要是指:CLOB和BLOB,这 ... -
Let’s Review How to Insert Clob or Blob via JDBC
2016-06-01 15:55 362最近在使用JDBC来访问数据,处理LOB字段的时候出现了问题 ... -
Oracle遍历游标的几种方式
2016-05-19 11:02 42681.for循环 会自动open和close游标,自动定义 ... -
在 Oracle 中使用正则表达式
2016-05-19 10:05 620Oracle使用正则表达式离不开这4个函数: 1。rege ... -
教你如何阅读Oracle数据库官方文档
2016-04-26 20:22 933教你如何阅读Oracle数据库官方文档 文章出处:ht ... -
sql中in和exists的区别效率问题
2016-02-19 15:28 417in 和exists in是把外表和内表作hash 连接, ... -
ORACLE恢复删除表或表记录
2016-01-12 11:06 740一:表的恢复对误删的表,只要没有使用PURGE永久删除选项, ... -
oracle超出打开游标的最大数的原因和解决方案
2015-12-26 21:30 1548处理超出打开游标的最 ... -
Oracle游标和jdbc的关系的总结
2015-10-26 21:59 2045碰到一个jdbc游标超出最大数的异常。正好对Ora ... -
ORACLE锁机制深入理解
2015-08-15 22:06 1251若对并发操作不加控制就可能会读取和存储不正确的数 ... -
修改Oracle XE Listener 占用的1521、8080端口
2015-08-04 14:12 744今天在帮开发人员Demon安装oracleXE时,有这么一段 ... -
oracle 10g中的几个概念(sid/db_name/server_name)
2015-07-29 17:05 888一、数据库名 1.数据库名的概念 数据库名( ...
相关推荐
本文将详细介绍Oracle临时表的创建方法、使用场景以及优缺点,帮助读者更好地理解和运用这一特性。 #### 二、Oracle临时表概述 Oracle临时表是一种特殊的表,用于存储临时数据,通常用于事务处理或特定会话期间的...
Oracle 临时表用法 Oracle 临时表是一种特殊的表结构,它可以在数据库中临时存储数据,用于实现一些特定的应用场景。下面是 Oracle 临时表的详细知识点: 创建临时表 创建临时表的语法为: ``` CREATE GLOBAL ...
以下将详细介绍如何在Oracle中创建表空间、临时表空间以及赋予用户对表空间的权限。 首先,我们来了解如何创建一个常规表空间: 1. **创建表空间**: 使用`CREATE TABLESPACE`语句来创建一个新的表空间。例如,...
本文将详细介绍如何在Oracle中创建临时表,并探讨其应用场景以及两种主要类型的临时表:全局临时表(Global Temporary Table)与局部临时表(Local Temporary Table)的区别及其使用方法。 #### 二、Oracle临时表...
### Oracle临时表详解 #### 一、Oracle临时表概述 在Oracle数据库中,临时表是一种特殊类型的数据表,主要用于存储暂时性的数据。与永久表不同的是,临时表中的数据不会一直保留,而是根据不同的条件(如事务结束...
- 使用`CREATE GLOBAL TEMPORARY TABLE`语句创建临时表。 - 可以通过`ON COMMIT`子句来定义数据的生命周期,即数据在何时被清除。 #### 三、创建临时表 **1. 基本语法:** ```sql CREATE GLOBAL TEMPORARY TABLE ...
以下是一个简单的示例,展示了如何在存储过程中使用临时表返回结果集: ```sql CREATE OR REPLACE PROCEDURE get_data(p_id IN NUMBER, c OUT SYS_REFCURSOR) AS TYPE data_table_type IS TABLE OF your_table%...
根据提供的文件信息,以下是从标题、描述以及部分代码示例中提炼出的关于Oracle数据库中与表(Table)操作相关的常用命令及其详细解释: ### 1. 创建表(Create Table) **命令格式**: ``` sql> create table table_...
本篇文章将深入探讨如何使用Java调用Oracle存储过程,并通过游标获取存储过程中返回的临时表数据。 首先,Oracle存储过程是一种在数据库端执行的预编译SQL语句和PL/SQL代码集合。它可以接收参数、执行业务逻辑并...
Oracle的临时表是一种特殊的数据存储结构,主要用于处理一次性或短暂性的数据需求,尤其在处理大量数据和复杂查询时,能够显著提升性能。临时表在Oracle中有两种类型:会话级临时表和事务级临时表。 1. **会话级...
### Oracle 创建表空间、用户及分配权限详解 在Oracle数据库管理中,创建表空间和用户是常见的基础操作之一。本文将详细介绍如何在Oracle数据库中创建表空间、创建用户并分配相应的权限,以及如何设置表空间的自...
### 数据库临时表详解 #### 一、临时表的概念与作用 在数据库操作过程中,我们经常会遇到需要存储一些中间结果或临时数据的情况。...在实际开发和运维工作中,掌握临时表的使用方法是非常重要的。
除了基本的使用方法之外,Oracle临时表还支持一些高级特性,如: - **索引**: 可以为临时表创建索引,进一步提高查询性能。 - **分区**: 对于非常大的数据集,可以考虑使用分区技术来管理临时表。 - **并发控制**: ...
- 在CallableStatement中设置TABLE参数,使用setObject方法,传入OracleTable对象和相应的OracleTypes常量。 - 执行包含TABLE参数的存储过程。 在实际开发中,你可能还需要关注以下几点: - **兼容性**:确保使用...
在Oracle中删除表中的重复数据,可以采用多种策略,但通常涉及创建一个临时表来保存去重后的数据,然后用这个临时表覆盖原始表。这种方法可以避免直接修改原表带来的风险,确保操作的安全性。以下是一种具体的实现...
### Oracle 创建表空间、创建用户、创建表 #### 一、创建表空间 表空间是Oracle数据库中的逻辑存储单元,它由一个或多个数据文件组成。表空间是Oracle数据库存储结构的基本单位,用来组织和管理数据库中的数据。在...
在Oracle数据库管理中,创建临时表空间是十分重要的步骤之一,尤其是在处理大量临时数据或排序操作时。临时表空间主要用于存储排序、索引创建和其他临时操作过程中产生的中间结果。以下是创建临时表空间的具体命令:...
#### 1.1 创建临时表空间 临时表空间主要用于存储SQL执行过程中产生的临时数据。例如,在排序操作或大表的扫描时,会使用到临时表空间。创建临时表空间的基本语法如下: ```sql CREATE TEMPORARY TABLESPACE test_...
创建临时表空间的基本语法如下: ```sql CREATE TEMPORARY TABLESPACE "TEST_TEMP" TEMPFILE 'D:/ORACLE/PRODUCT/10.2.0/ORADATA/GIS/TEST_DATA.ora' SIZE 20M AUTOEXTEND ON NEXT 32M MAXSIZE 2048M EXTENT ...
2. 创建一个临时表 tmp_1,将符合条件的记录全部取出来。 3. 设定一个随机数种子,可以使用固定值或当前系统时间。 4. 调用 DBMS_RANDOM.VALUE 函数生成随机数,并将其存储在临时表 tmp_2 中。 5. 将临时表 tmp_1 和...