sql常用语句整理

建表

create table 表名(
       字段名 类型(长度) primary key, --约束条件
       字段名 类型(长度)        
       );

插入(行)

==================插入单条数据=========================
insert into table_1 values(280,6,2000,3000,4000,5000,6000);
===============用 union 插入多条数据==================
insert into table_1 
select 50,‘公关部‘,‘*‘ from dual
union
select 60,‘研发部‘,‘japan‘  from dual
union
select 70,‘培训部‘,‘uk‘ from dual
==================插入一个查询结果集==========================
insert into table_1 select 条件 from table_2;
--备份一个表
==================向表中插入一个常量结果集=====================
INSERT INTO table_1 SELECT ‘s100106‘,‘卢俊义‘,‘男‘,23,
 TO_DATE(‘2009-8-9 08:00:10‘,‘YYYY-MM-DD HH24:MI:SS‘),‘1001‘
FROM DUAL; 

select ... from dual,dual 表在系统中只有一行一列,为了select…from 的语法完整性而使用。

SELECT vale1, value2 into Table2 from Table1
--创建目标表table2并把table1中的数据复制到table2,table2 表不存在

select into from 和 insert into select都是用来复制表,两者的主要区别为: select into from 要求目标表不存在,因为在插入时会自动创建。insert into select from 要求目标表存在。

插入(列),更新

删除列:alter table 表名 drop column 列名;
添加列:alter table 表名 add 列名 类型(长度);
修改列属性:alter table 表名 modify 列名 类型(长度);
创建约束:ALTER TABLE 表名 ADD CONSTRAINT 约束名 约束内容
更新数据:UPDATE 表名称 SET 列名称 = 新值 WHERE 列名称 = 某值

删除表

1、drop (删除表):删除内容和定义,释放空间。简单来说就是把整个表去掉.以后要新增数据是不可能的,除非新增一个表。无法进行回滚操作。

drop table 表名称

2、truncate (清空表中的数据):删除内容、释放空间但不删除定义(保留表的数据结构)。与drop不同的是,只是清空表数据而已。无法进行回滚操作。

truncate table 表名称 

3、delete (删除表中的数据):delete 语句用于删除表中的行。delete语句执行删除的过程是每次从表中删除一行,并且同时将该行的删除操作作为事务记录在日志中保存,以便进行进行回滚操作。

delete from 表名称 where 列名称 = 值

拼接两个表的查询结果

(1)内连接:即等值连接

--简易写法
select a.字段名1,a.字段名2,d.字段名3 from table_1 a,table_2 d 
where a.字段名4=d.字段名4 and 筛选条件
===========sql/92标准写法(推荐),INNER 可以省略==================
SELECT a.字段名1,a.字段名2,d.字段名3 
FROM table_1 a INNER JOIN table_2 d ON a.字段名4=d.字段名4
WHERE 筛选条件

(2)LEFT OUTER JOIN:在内连接的基础上加上主表中的未匹配数据
(3)RIGHT OUTER JOIN :在内连接的基础上加上被连接表的不匹配数据
(4)FULL OUTER JOIN:结合的LEFT JOIN,RIGHT JOIN的结果

--简易写法
select  a.字段名1,a.字段名2,d.字段名3 from table_1 a,table_2 d  where a.字段名4(+)=d.字段名4
--(+):Oracle 专用的联接符,在条件中出现在左边指右外联接,出现在右边指左外
联接。
=================sql/92标准写法(推荐),outer 可以省略====================
select  a.字段名1,a.字段名2,d.字段名3 from table_1 a right join table_2 d on a.字段名4(+)=d.字段名4;
select  a.字段名1,a.字段名2,d.字段名3 from table_1 a left  join table_2 d on a.字段名4(+)=d.字段名4  where 条件;
select  a.字段名1,a.字段名2,d.字段名3 from table_1 a full  join table_2 d on a.字段名4(+)=d.字段名4  where 条件;

(5)Union:对两个结果集进行并集操作,不包括重复行,同时进行默认规则的排序;
(6)Union All:对两个结果集进行并集操作,包括重复行,不进行排序;
实例:

select empno as 编码,ename as 名称,nvl(mgr,deptno) as 上级编码 from emp where sal>=2000 
union all
select deptno as 编码,dname as 名称,null as 上级编码 from dept
--当数据集列不够时可以用null来填充该列的值

备份

1. 备份表
create table [备份名] as select * from [表名];
--根据结果集创建一个新表
2. 恢复表
insert into org_group select * from [备份名] ;

去除重复数据

一、数据库中的去重操作(删除数据库中重复记录的SQL语句)主要有三种方法
(1)、rowid方法

delete from table_1 a where rowid>(select min(rowid) from table_1 b where a.字段名1=b.字段名1)
/*根据字段名1删除重复数据*/

ROWID 伪列返回的就是该行的物理地址,ROWID 值可以唯一的标识表中的一行。
ROWNUM 标识的是查询结果中的行的次序,可以作为限制返回行数的条件。
(2)、group by 方法
适用于单独对某列进行去重。推荐使用group by。因为distinct会导致全表扫描,而group by如果索引建的恰当的话,会有性能上的提高。

--查数据,列出表中的重复的记录数,并按照字段1分组后找出表中字段1列出现次数大于一次的。
Select 字段1 from 表 Group by 字段1 Having count(字段1)>1 
--删除表中字段1列所有重复的数据
Delete from 表 Group by 字段1 Having count(字段1)>1

(3)、distinct方法
两条记录或者多条记录的每一个字段值完全相同,这种情况去重复最简单,用关键字distinct就可以去掉。

SELECT DISTINCT 字段名 FROM 表名; 

查询

where条件

1.数字比较:> < >= <= != <> ^=
2.between ..and.. 值在两者之间
3.in,exists:值在列表中
4.like:字符串的模糊匹配
5.is null:值为null,select * from deal_info where deal_time is not null
6.or、and:满足多个条件

IN适合于外表大而内表小的情况;EXISTS适合于外表小而内表大的情况

having子句

Having 子句与where子句的功能类似,都是对行进行筛选。
where搜索条件是在分组操作之前对记录进行筛选,然后再由group BY 对筛选后符合条件的行进行分组;而Having搜索条件则是对分组操作之后得到的行进行筛选操作。

1.Where 子句用来筛选From 子句中指定的操作所产生的行;

2.Group By 子句用来分组Where子句的输出;

3.Having 子句用来从分组的结果中筛选行。

没有Group By子句的情况下,使用Where子句会更高效。因为Where 子句能够事先把不必要的数据过滤掉,从而减少了在执行select时数据处理量。但是,有些数据事先并不知道是否需要过滤掉,要根据结果才能确定,就必须使用having子句解决

统计

select 字段名,count(1) from 表 group by 字段名

count(*)将返回表格中所有存在的行的总数包括值为null的行,然而count(列名)将返回表格中除去null以外的所有行的总数(有默认值的列也会被计入)

select 字段1,sum(字段2)  from 表 where 条件语句 group by 字段1 

自关联查询

自连接查询其实等同于连接查询,需要两张表,只不过它的左表(父表)和右表(子表)都是自己。做自连接查询的时候,是自己和自己连接,分别给父表和子表取两个不同的别名,然后附上连接条件。

select * from emp t1,emp t2 where t1.mgr=t2.empno;

条件逻辑(筛选)

case函数:Case函数只返回第一个符合条件的值,剩下的Case部分将会被自动忽略。
第一种格式 : 简单Case函数

  case 列名
    when   条件值1   then  选项1
    when   条件值2    then  选项2.
    ......
    else   默认值      end

第二种 格式 :Case搜索函数

case  
    when  列名= 条件值1   then  选项1
    when  列名=条件值2    then  选项2.
    ......
    else    默认值  end

嵌套查询

在 SELECT、UPDATE、DELETE 语句内部可以出现 SELECT 语句。内部的 SELECT 语句结果可以作为外部语句中条件子句的一部分,也可以作为外部查询的临时表;包括exists、in、any、all等

--单行单行单列子查询
select 字段名1,字段名2 from table_1  
where 字段名3 比较运算符 (select 字段 from table_2 where 条件 )

比较运算符:=、>、<、>=、<=、<>等
All:只有当其所有数据都满足条件时,条件才成立
Any:只要有一条数据满足条件,条件就成立

=ANY:表示与子查询中的每个元素进行比较,功能与IN类似(然而<>ANY不等价于NOT IN)
>ANY:比子查询中返回结果的最小的要大(还包含了>=ANY)
<ANY:比子查询中返回结果的最大的要小(还包含了<=ANY)

ALL有如下三种使用形式:

ALL操作符有以下三种用法:
<>ALL:等价于NOT IN(但是=ALL并不等价于IN)
>ALL:比子查询中最大的值还要大(还包含了>=ALL)
<ALL:比子查询中最小的值还要小(还包含了<=ALL)

例子:

select 字段名1,字段名2 from table_1  
where 字段名3 比较运算符 any(select 字段 from table_2 where 条件 )

with……as……

在比较复杂,数据量大的情况下,为了提高查询效率,需要用到一些子查询。一层一层嵌套的子查询不方便,显得sql语句比较繁琐,这时可以使用with语句,with as 相当于虚拟视图,其实就是把一大堆重复用到的sql语句放在with as里面,取一个别名,后面的查询就可以用它,很多查询通过这种方法都可以提高速度。

--针对一个别名
with tmp as (select * from tb_name)
--针对多个别名
with
tmp as (select * from tb_name),
tmp2 as (select * from tb_name2),
tmp3 as (select * from tb_name3),
…

相当于建了个e临时表

with e as (select * from scott.emp e where e.empno=7499)
select * from e;
--相当于建了e、d临时表
with
e as (select * from scott.emp),
d as (select * from scott.dept)
select * from e, d where e.deptno = d.deptno;

二、with的相关总结
1.with子句只能被select查询块引用,一般在with查询用到多次情况下。在引用的select语句之前定义,同级只能定义with关键字只能使用一次,多个用逗号分割。

2.with子句的返回结果存到用户的临时表空间中,只做一次查询,反复使用,提高效率。

3.在同级select前有多个查询定义的时候,第1个用with,后面的不用with,并且用逗号隔开。

4.最后一个with 子句与下面的查询之间不能有逗号,只通过右括号分割,with 子句的查询必须用括号括起来

5.前面的with子句定义的查询在后面的with子句中可以使用。但是一个with子句内部不能嵌套with子句。

6.with查询的结果列有别名,引用的时候必须使用别名或*。

oracle函数

格式化字符串:

yyyy-mm-dd,HH24:MI:SS,
ddd 年中的第几天 
day 星期几,中文显示
WW 年中的第几个星期 
W 该月中第几个星期 
DL 返回长的日期格式
DS 返回短的日期格式

常用转换函数:

TO_CHAR(d|n[,fmt])
--把日期和数字转换为制定格式的字符串。fmt 是格式化字符串,使用双引号对非格式化字符进行引用
TO_DATE(x [,fmt])
--把一个字符串以设置的格式转换为一个日期类型
TO_NUMBER(x[,fmt])
--把一个字符串以设置的格式转换为一个数字

常用日期函数:

sysdate
select to_char(sysdate,‘yyyy-mm-dd HH24:MI:SS‘) from dual
--日期+数字,表示若干天之后的日期。
SELECT SYSDATE,TO_CHAR(SYSDATE+1,‘yyyy-mm-dd HH24:MI:SS‘) FROM DUAL; 
--日期-数字,表示若干天之前的日期。
--日期-日期,表示两个日期间的天数,但是肯定是大日期-小日期
SELECT SYSDATE,TO_CHAR(SYSDATE-1/24,‘yyyy-mm-dd HH24:MI:SS‘) FROM DUAL; --减1小时 
SELECT SYSDATE,TO_CHAR(SYSDATE-1/24/60,‘yyyy-mm-dd HH24:MI:SS‘) FROM DUAL; --减1分钟 
SELECT SYSDATE,TO_CHAR(SYSDATE-1/24/60/60,‘yyyy-mm-dd HH24:MI:SS‘) FROM DUAL; --减1秒 
TRUNC(number,num_digits)  --用于截取时间或者数值,返回指定的值
Number 需要截尾取整的数字;Num_digits 用于指定取整精度的数字。
Num_digits 的默认值为 0。
select trunc(sysdate) from dual  ;--2011-3-18  今天的日期为2011-3-18
select trunc(sysdate, ‘mm‘)   from   dual ; --2011-3-1    返回当月第一天.
select trunc(sysdate,‘yy‘) from dual;  --2011-1-1       返回当年第一天
select trunc(sysdate,‘dd‘) from dual;  --2011-3-18    返回当前年月日
select trunc(sysdate,‘yyyy‘) from dual;  --2011-1-1   返回当年第一天
select add_months(to_date(‘2018-01-01‘,‘yyyy-mm-dd‘),12)-1 from dual;  -- 2018-12-31  返回当年第一天
select trunc(sysdate,‘d‘) from dual ; --2011-3-13 (星期天)返回当前星期的第一天
select trunc(sysdate, ‘mi‘) from dual ; --2011-3-18 14:41:00   TRUNC()函数没有秒的精确
SELECT to_date(‘20180818‘,‘yyyymmdd‘)-to_date(‘20180727‘,‘yyyymmdd‘) FROM dual;
ADD_MONTHS(d,n)
--在某一个日期 d 上,加上指定的月数 n,返回计算后的新日期。d 表示日期,n 表示要加的月数。n可以是负数。
ROUND(d[,fmt])
--返回一个fmt格式的四舍五入日期值,d 是日期,fmt是格式模型。默认 fmt 为 DDD,即月中的某一天。
LAST_DAY(d)
--返回指定日期当月的最后一天。
EXTRACT(fmt FROM d)
--提取日期中的特定部分。fmt 为:YEAR、MONTH、DAY、HOUR、MINUTE、SECOND。

常用字符函数:

concat(str1,str2)  --str1与str2字符串连接

replace(str1,str2,str3) 
--str3替换str1中出现的所有str2,返回新的字符串,如果有某个参数为NULL,此函数返回NULL  
/*并不会修改数据库中原始值*/

substr(x,a[,b])  --返回字符串中的指定的字符
这些字符从字符串的第a个位置开始,长度为b个字符;
如果a是负数,则从x字符串的末尾开始算起;如果b省略,则将返回一直到字符串末尾的所有字符

substrb(‘字符串‘,a,b) --按字节截取,一个汉字占两个字节
COALESCE(),NVL()函数,空值转换
1.COALESCE ( expression1, expression2 );
2.COALESCE ( expression1, expression2, ... expression-n );
--第二种可以包含n个表达式,表示如果第一个不为空取第一个,否则判断下一个
NVL(x,value)
--如果 x 为空,返回 value,否则返回 x。
NVL2(x,value1,value2)
--如果 x 非空,返回 value1,否则返回 value2。

常用聚合函数:一个集合(集或者多重集)为输入、返回单个值的函数

avg(x)  --返回x的平均值,avg函数在计算时,不包含任何值为 null 的资料。
count(x)  --返回统计的行数
max(x)  --作用在同一列的一个Group上面的
min(x)  --作用在同一列的一个Group上面的
sum(x)  --返回x的总计值
length(‘字符串‘)  --length按字符计,汉字、英文、数字都是1个字符
row_number() over() -- 分组排序
row_number() over(partition by 分组列 order by 排序列 desc)
--over()里头的分组以及排序的执行晚于 where 、group by、  order by 的执行。

oracle锁表的原因,及解决方案

锁表的原因 :
第一种、 A程序执行了对 tableA 的 insert ,并还未 commite时,B程序也对tableA 进行insert 则此时会发生资源正忙的异常 就是锁表;锁表常发生于并发而不是并行(并行时,一个线程操作数据库时,另一个线程是不能操作数据库的,cpu 和i/o 分配原则)
解决方法:以SYSDBA登陆数据库,执行以下语句

select b.owner,b.object_name,a.session_id,a.locked_mode from v$locked_object a,dba_objects b where b.object_id = a.OBJECT_ID;
--查看被锁的表

select a.session_id,b.username,b.sid,b.serial#,logon_time from v$locked_object a,v$session b where a.session_id = b.sid order by b.logon_time;
--查看那个用户那个进程照成死锁,查看连接的进程 ,查出锁定表的sid,serial#

杀掉进程 sid,serial#

alter system kill session‘153,28830‘;

还有一种,在外键上没有加索引引起的死锁,由于程序在主子表上删除数据,缺少索引导致行级锁升级为表级锁,最终导致大量的锁等待和死锁。

sqlserver常用日期函数

DATEADD(datepart,number,date)
getdate() --获得日期/时间信息。

datepart是日期的格式化字符串,date 参数是合法的日期表达式。number 是您希望添加的间隔数--对于未来的时间,此数是正数,对于过去的时间,此数是负数。

sql常用语句整理

上一篇:C#操作Xml:XSLT语法 在.net中使用XSLT转换xml文档示例


下一篇:mysql索引【第四篇】