??xml version="1.0" encoding="utf-8" standalone="yes"?> Function Use ADD_MONTHS Adds months to a date LAST_DAY Computes the last day of the month MONTHS_BETWEEN Determines the number of months between two dates NEW_TIME Translates a time to a new time zone NEXT_DAY Returns the date of the next specified weekday ROUND Rounds a date/time value to a specified element SYSDATE Returns the current date and time TO_CHAR Converts dates to strings TO_DATE Converts strings and numbers to dates TRUNC Truncates a date/time value to a specific element
EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
----- ------ --------- ---- ----------- ---- ---- -------
7369 SMITH CLERK 7902 17-DEC-1980 800 20
7499 ALLEN SALESMAN 7698 20-FEB-1981 1600 300 30
7521 WARD SALESMAN 7698 22-FEB-1981 1250 500 30
7566 JONES MANAGER 7839 02-APR-1981 2975 20
7654 MARTIN SALESMAN 7698 28-SEP-1981 1250 1400 30
7698 BLAKE MANAGER 7839 01-MAY-1981 2850 30
7782 CLARK MANAGER 7839 09-JUN-1981 2450 10
7788 SCOTT ANALYST 7566 09-DEC-1982 3000 20
7839 KING PRESIDENT 17-NOV-1981 5000 10
7844 TURNER SALESMAN 7698 08-SEP-1981 1500 0 30
7876 ADAMS CLERK 7788 12-JAN-1983 1100 20
7900 JAMES CLERK 7698 03-DEC-1981 950 30
7902 FORD ANALYST 7566 03-DEC-1981 3000 20
7934 MILLER CLERK 7782 23-JAN-1982 1300 10
2.问题Q查找DEPTNO 20中出现最多次数的工资Q?/span>
select sal
from emp
where deptno = 20
order by sal
SAL
----------
800
1100
2975
3000
3000
3.解决Ҏ(gu)
使用H口函数 DENSE_RANK,把工资重复出现的ơ数分等U?br />
1 select sal
2 from (
3 select sal,
4 dense_rank()over( order by cnt desc) as rnk
5 from (
6 select sal, count(*) as cnt
8 from emp
9 where deptno = 20
10 group by sal
11 ) x
12 ) y
13 where rnk = 1
]]>
2.NULLIFQ字D名Q字D|(j)若字D名的gؓ(f)"字段?Q则该字段值替换成NULL
3.COALESCE(表达?Q表辑ּ2Q?..表达式nQ?从左到右 依次判断表达式的?q回W一个非I的表达式的倹{?br />
]]>
Oracle?i开始就提供?jin)大量的日期函数Q这些日期函数包括对日期q行加减、{换、截取等功能。下面是Oracle提供的日期函C览表
更多详细内容请参考:(x)http://www.aygfsteel.com/pengpenglin/archive/2008/06/30/211589.html
]]>
1.AVG
功能描述Q用于计一个组和数据窗口内表达式的q_倹{?br />
SAMPLEQ下面的例子中列c_mavg计算员工表中每个员工的^均薪水报告,该^均值由当前员工和与之具有相同经理的前一个和后一个三者的q_数得来;
SELECT manager_id, last_name, hire_date, salary,
AVG(salary) OVER (PARTITION BY manager_id ORDER BY hire_date
ROWS BETWEEN 1 PRECEDING AND 1 FOLLOWING) AS c_mavg
FROM employees;
MANAGER_ID LAST_NAME HIRE_DATE SALARY C_MAVG
---------- ------------------------- --------- ---------- ----------
100 Kochhar 21-SEP-89 17000 17000
100 De Haan 13-JAN-93 17000 15000
100 Raphaely 07-DEC-94 11000 11966.6667
100 Kaufling 01-MAY-95 7900 10633.3333
100 Hartstein 17-FEB-96 13000 9633.33333
100 Weiss 18-JUL-96 8000 11666.6667
100 Russell 01-OCT-96 14000 11833.3333
2.COUNT
功能描述Q对一l内发生的事情进行篏U计敎ͼ如果指定*或一些非I常敎ͼcount对所有行计数Q如果指定一个表辑ּQcountq回表达式非I值的计数Q当有相同值出现时Q这些相{的值都?x)被U_被计的|可以使用DISTINCT来记录去掉一l中完全相同的数据后出现的行数?br />
SAMPLEQ下面例子中计算每个员工在按薪水排序中当前行附近薪水在[n-50,n+150]之间的行敎ͼn表示当前行的薪水例如QPhiltanker的薪?200Q排在他之前的行中薪水大于等?200-50的有1行,排在他之后的行中薪水于{于2200Q?50的行没有Q所以count计数值cnt3?Q包括自己当前行Q;cnt2值相当于于{于当前行的SALARY值的所有行?
SELECT last_name, salary, COUNT(*) OVER () AS cnt1,
COUNT(*) OVER (ORDER BY salary) AS cnt2,
COUNT(*) OVER (ORDER BY salary RANGE BETWEEN 50 PRECEDING
AND 150 FOLLOWING) AS cnt3 FROM employees;
LAST_NAME SALARY CNT1 CNT2 CNT3
------------------------- ---------- ---------- ---------- ----------
Olson 2100 107 1 3
Markle 2200 107 3 2
Philtanker 2200 107 3 2
Landry 2400 107 5 8
Gee 2400 107 5 8
Colmenares 2500 107 11 10
Patel 2500 107 11 10
3.DENSE_RANK
功能描述Q根据ORDER BY子句中表辑ּ的|从查询返回的每一行,计算它们与其它行的相对位|。组内的数据按ORDER BY子句排序Q然后给每一行赋一个号Q从而Ş成一个序列,该序列从1开始,往后篏加。每ơORDER BY表达式的值发生变化时Q该序列也随之增加。有同样值的行得到同L(fng)数字序号Q认为null时相{的Q。密集的序列q回的时没有间隔的数
SAMPLEQ下例中计算每个员工按部门分区再按薪水排序,依次出现的序列号Q注意与RANK函数的区别)(j)
SELECT d.department_id , e.last_name, e.salary, DENSE_RANK()
OVER (PARTITION BY e.department_id ORDER BY e.salary) as drank
FROM employees e, departments d
WHERE e.department_id = d.department_id
AND d.department_id IN ('60', '90');
DEPARTMENT_ID LAST_NAME SALARY DRANK
------------- ------------------------- ---------- ----------
60 Lorentz 4200 1
60 Austin 4800 2
60 Pataballa 4800 2
60 Ernst 6000 3
60 Hunold 9000 4
90 Kochhar 17000 1
90 De Haan 17000 1
90 King 24000 2
RANK()与DENSE_RANK()用法相当Q但是有一个区别:(x)DENSE_RANK在处理相同的{Ӟ{的数g?x)蟩q?RANK()则蟩q?br />
RANK
功能描述Q根据ORDER BY子句中表辑ּ的|从查询返回的每一行,计算它们与其它行的相对位|。组内的数据按ORDER BY子句排序Q然后给每一行赋一个号Q从而Ş成一个序列,该序列从1开始,往后篏加。每ơORDER BY表达式的值发生变化时Q该序列也随之增加。有同样值的行得到同L(fng)数字序号Q认为null时相{的Q。然而,如果两行的确得到同样的排序,则序数将随后跌。若两行序数?Q则没有序数2Q序列将l组中的下一行分配?QDENSE_RANK则没有Q何蟩跃?br />
SAMPLEQ下例中计算每个员工按部门分区再按薪水排序,依次出现的序列号Q注意与DENSE_RANK函数的区别)(j)
SELECT d.department_id , e.last_name, e.salary, RANK()
OVER (PARTITION BY e.department_id ORDER BY e.salary) as drank
FROM employees e, departments d
WHERE e.department_id = d.department_id
AND d.department_id IN ('60', '90');
DEPARTMENT_ID LAST_NAME SALARY DRANK
------------- ------------------------- ---------- ----------
60 Lorentz 4200 1
60 Austin 4800 2
60 Pataballa 4800 2
60 Ernst 6000 4
60 Hunold 9000 5
90 Kochhar 17000 1
90 De Haan 17000 1
90 King 24000 3
4.FIRST
功能描述Q从DENSE_RANKq回的集合中取出排在最前面的一个值的行(可能多行Q因为值可能相{)(j)Q因此完整的语法需要在开始处加上一个集合函C从中取出记录SAMPLE.
下面例子中DENSE_RANK按部门分区,再按佣金commission_pct排序QFIRST取出佣金最低的对应的所有行Q然后前面的MAX函数从这个集合中取出薪水最低的|LAST取出佣金最高的对应的所有行Q然后前面的MIN函数从这个集合中取出薪水最高的?
SELECT last_name, department_id, salary,
MIN(salary) KEEP (DENSE_RANK FIRST ORDER BY commission_pct)
OVER (PARTITION BY department_id) "Worst",
MAX(salary) KEEP (DENSE_RANK LAST ORDER BY commission_pct)
OVER (PARTITION BY department_id) "Best"
FROM employees
WHERE department_id in (20,80)
ORDER BY department_id, salary;
LAST_NAME DEPARTMENT_ID SALARY Worst Best
------------------------- ------------- ---------- ---------- ----------
Fay 20 6000 6000 13000
Hartstein 20 13000 6000 13000
Kumar 80 6100 6100 14000
Banda 80 6200 6100 14000
Johnson 80 6200 6100 14000
Ande 80 6400 6100 14000
Lee 80 6800 6100 14000
Tuvault 80 7000 6100 14000
Sewall 80 7000 6100 14000
Marvins 80 7200 6100 14000
Bates 80 7300 6100 14000
5.FIRST_VALUE
功能描述Q返回组中数据窗口的W一个倹{?br />
SAMPLEQ下面例子计按部门分区按薪水排序的数据H口的第一个值对应的名字Q如果薪水的W一个值有多个Q则从多个对应的名字中取~省排序的第一个名?
SELECT department_id, last_name, salary, FIRST_VALUE(last_name)
OVER (PARTITION BY department_id ORDER BY salary ASC ) AS lowest_sal
FROM employees
WHERE department_id in(20,30);
DEPARTMENT_ID LAST_NAME SALARY LOWEST_SAL
------------- ------------------------- ---------- --------------
20 Fay 6000 Fay
20 Hartstein 13000 Fay
30 Colmenares 2500 Colmenares
30 Himuro 2600 Colmenares
30 Tobias 2800 Colmenares
30 Baida 2900 Colmenares
30 Khoo 3100 Colmenares
30 Raphaely 11000 Colmenares
6.LAST
功能描述Q从DENSE_RANKq回的集合中取出排在最后面的一个值的行(可能多行Q因为值可能相{)(j)Q因此完整的语法需要在开始处加上一个集合函C从中取出记录
SAMPLEQ下面例子中DENSE_RANK按部门分区,再按佣金commission_pct排序QFIRST取出佣金最低的对应的所有行Q然后前面的MAX函数从这个集合中取出薪水最低的|LAST取出佣金最高的对应的所有行Q然后前面的MIN函数从这个集合中取出薪水最高的?br />
SELECT last_name, department_id, salary,
MIN(salary) KEEP (DENSE_RANK FIRST ORDER BY commission_pct)
OVER (PARTITION BY department_id) "Worst",
MAX(salary) KEEP (DENSE_RANK LAST ORDER BY commission_pct)
OVER (PARTITION BY department_id) "Best"
FROM employees
WHERE department_id in (20,80)
ORDER BY department_id, salary;
LAST_NAME DEPARTMENT_ID SALARY Worst Best
------------------------- ------------- ---------- ---------- ----------
Fay 20 6000 6000 13000
Hartstein 20 13000 6000 13000
Kumar 80 6100 6100 14000
Banda 80 6200 6100 14000
Johnson 80 6200 6100 14000
Ande 80 6400 6100 14000
Lee 80 6800 6100 14000
Tuvault 80 7000 6100 14000
Sewall 80 7000 6100 14000
Marvins 80 7200 6100 14000
Bates 80 7300 6100 14000
7.LAST_VALUE
功能描述Q返回组中数据窗口的最后一个倹{?br />
SAMPLEQ下面例子计按部门分区按薪水排序的数据H口的最后一个值对应的名字Q如果薪水的最后一个值有多个Q则从多个对应的名字中取~省排序的最后一个名?br />
SELECT department_id, last_name, salary, LAST_VALUE(last_name)
OVER(PARTITION BY department_id ORDER BY salary) AS highest_sal
FROM employees
WHERE department_id in(20,30);
DEPARTMENT_ID LAST_NAME SALARY HIGHEST_SAL
------------- ------------------------- ---------- ------------
20 Fay 6000 Fay
20 Hartstein 13000 Hartstein
30 Colmenares 2500 Colmenares
30 Himuro 2600 Himuro
30 Tobias 2800 Tobias
30 Baida 2900 Baida
30 Khoo 3100 Khoo
30 Raphaely 11000 Raphaely
8.LAG
功能描述Q可以访问结果集中的其它行而不用进行自q接。它允许d理游标,好像游标是一个数l一栗在l定l中可参考当前行之前的行Q这样就可以从组中与当前行一起选择以前的行。Offset是一个正整数Q其默认gؓ(f)1Q若索引出H口的范_(d)p回默认|默认q回的是l中W一行)(j)Q其相反的函数是LEAD
SAMPLEQ下面的例子中列prev_salq回按hire_date排序的前1行的salary?
SELECT last_name, hire_date, salary,
LAG(salary, 1, 0) OVER (ORDER BY hire_date) AS prev_sal
FROM employees
WHERE job_id = 'PU_CLERK';
LAST_NAME HIRE_DATE SALARY PREV_SAL
------------------------- ---------- ---------- ----------
Khoo 18-5?-95 3100 0
Tobias 24-7?-97 2800 3100
Baida 24-12?97 2900 2800
Himuro 15-11?98 2600 2900
Colmenares 10-8?-99 2500 2600
9.LEAD
功能描述QLEAD与LAG相反QLEAD可以讉Kl中当前行之后的行。Offset是一个正整数Q其默认gؓ(f)1Q若索引出H口的范_(d)p回默认|默认q回的是l中W一行)(j)
SAMPLEQ下面的例子中每行的"NextHired"q回按hire_date排序的下一行的hire_date?
SELECT last_name, hire_date,
LEAD(hire_date, 1) OVER (ORDER BY hire_date) AS "NextHired"
FROM employees WHERE department_id = 30;
LAST_NAME HIRE_DATE NextHired
------------------------- --------- ---------
Raphaely 07-DEC-94 18-MAY-95
Khoo 18-MAY-95 24-JUL-97
Tobias 24-JUL-97 24-DEC-97
Baida 24-DEC-97 15-NOV-98
Himuro 15-NOV-98 10-AUG-99
Colmenares 10-AUG-99
10.SUM
功能描述Q该函数计算l中表达式的累积和?br />
SAMPLEQ下例计同一l理下员工的薪水累积?
SELECT manager_id, last_name, salary,
SUM (salary) OVER (PARTITION BY manager_id ORDER BY salary
RANGE UNBOUNDED PRECEDING) l_csum
FROM employees
WHERE manager_id in (101,103,108);
MANAGER_ID LAST_NAME SALARY L_CSUM
---------- ------------------------- ---------- ----------
101 Whalen 4400 4400
101 Mavris 6500 10900
101 Baer 10000 20900
101 Greenberg 12000 44900
101 Higgins 12000 44900
103 Lorentz 4200 4200
103 Austin 4800 13800
103 Pataballa 4800 13800
103 Ernst 6000 19800
108 Popp 6900 6900
108 Sciarra 7700 14600
108 Urman 7800 22400
108 Chen 8200 30600
108 Faviet 9000 39600
11.MAX
功能描述Q在一个组中的数据H口中查找表辑ּ的最大倹{?br />
SAMPLEQ下面例子中dept_maxq回当前行所在部门的最大薪水?
SELECT department_id, last_name, salary,
MAX(salary) OVER (PARTITION BY department_id) AS dept_max
FROM employees WHERE department_id in (10,20,30);
DEPARTMENT_ID LAST_NAME SALARY DEPT_MAX
------------- ------------------------- ---------- ----------
10 Whalen 4400 4400
20 Hartstein 13000 13000
20 Fay 6000 13000
30 Raphaely 11000 11000
30 Khoo 3100 11000
30 Baida 2900 11000
30 Tobias 2800 11000
30 Himuro 2600 11000
30 Colmenares 2500 11000
12.MIN
功能描述Q在一个组中的数据H口中查找表辑ּ的最倹{?br />
SAMPLEQ下面例子中dept_minq回当前行所在部门的最薪水?
SELECT department_id, last_name, salary,
MIN(salary) OVER (PARTITION BY department_id) AS dept_min
FROM employees WHERE department_id in (10,20,30);
DEPARTMENT_ID LAST_NAME SALARY DEPT_MIN
------------- ------------------------- ---------- ----------
10 Whalen 4400 4400
20 Hartstein 13000 6000
20 Fay 6000 6000
30 Raphaely 11000 2500
30 Khoo 3100 2500
30 Baida 2900 2500
30 Tobias 2800 2500
30 Himuro 2600 2500
30 Colmenares 2500 2500