- MODEL
- DIMENSION BY
- DIMENSION и MEASURES
- RULES
- Основные правила
- FOR Loops
- UNIQUE SINGLE REFERENCE
- Функция CV()
- PARTITON BY
- Агрегатные и аналитические функции
MODEL
Конструкция MODEL появилась в версии Oracle 10g. Описывается как мощное средство, которое дает доступ к изменению любой ячейки запроса в результирующем наборе данных. И так же добавлены новые возможности, ранее доступные только через PL/SQL вызовы. MODEL – выражение позволяющее представлять результат запроса в виде многомерного куба и задавать выражения для расчета его произвольных ячеек. Например, с помощью MODEL, можно взять следующую таблицу:
SQL> select * from scott.emp t ; EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO ----- ---------- --------- ----- ----------- --------- --------- ------ 7369 SMITH CLERK 7902 17.12.1980 800,00 20 7499 ALLEN SALESMAN 7698 20.02.1981 1600,00 300,00 30 7521 WARD SALESMAN 7698 22.02.1981 1250,00 500,00 30 7566 JONES MANAGER 7839 02.04.1981 2975,00 20 7654 MARTIN SALESMAN 7698 28.09.1981 1250,00 1400,00 30 7698 BLAKE MANAGER 7839 01.05.1981 2850,00 30 7782 CLARK MANAGER 7839 09.06.1981 2450,00 10 7788 SCOTT ANALYST 7566 09.12.1982 3000,00 20 7839 KING PRESIDENT 17.11.1981 5000,00 10 7844 TURNER SALESMAN 7698 08.09.1981 1500,00 0,00 30 7876 ADAMS CLERK 7788 12.01.1983 1100,00 20 7900 JAMES CLERK 7698 03.12.1981 950,00 30 7902 FORD ANALYST 7566 03.12.1981 3000,00 20 7934 MILLER CLERK 7782 23.01.1982 1300,00 10 14 rows selected
и добавив ряд команд, создать новые строки с итогами:
select case when key like 'Итог%' then key end key, ename, job, hiredate, salfrom scott.emp t model dimension by ( cast (empno as varchar2(40)) as key, ename, job, hiredate )measures (sal)rules ( sal['Итог 1: ename like ''S%''' ,null,null,null] = sum(sal)[any,ename like 'S%',any,any], sal['Итог 2: salesman; сентябрь',null,null,null] = sum(sal)[any,any,'SALESMAN',extract(month from hiredate)=9], sal['Итог 3: length(ename)=5; декабрь',null,null,null] = sum(sal)[any,length(ename)=5,any,extract(month from hiredate)=12] )order by key NULLS FIRST, hiredate, ename; KEY ENAME JOB HIREDATE SAL --------------------------------- ---------- --------- ----------- ----- SMITH CLERK 17.12.1980 800 ALLEN SALESMAN 20.02.1981 1600 WARD SALESMAN 22.02.1981 1250 JONES MANAGER 02.04.1981 2975 BLAKE MANAGER 01.05.1981 2850 CLARK MANAGER 09.06.1981 2450 TURNER SALESMAN 08.09.1981 1500 MARTIN SALESMAN 28.09.1981 1250 KING PRESIDENT 17.11.1981 5000 FORD ANALYST 03.12.1981 3000 JAMES CLERK 03.12.1981 950 MILLER CLERK 23.01.1982 1300 SCOTT ANALYST 09.12.1982 3000 ADAMS CLERK 12.01.1983 1100 Итог 1: ename like 'S%' 3800 Итог 2: salesman; сентябрь 2750 Итог 3: length(ename)=5; декабрь 4750 17 rows selected
Можно использовать процедурные свойства MODEL для получения результата, который сложно, неэффективно или невозможно реализовать в SQL запросе (без PL/SQL).
select job , substr( str, 2 ) as strfrom scott.emp t model return updated rows partition by (job)dimension by ( row_number() over (partition by job order by job) as position)measures (cast(sal as varchar2(200)) as str)rules upsert iterate( 4 )until ( presentv(str[iteration_number+2],1,0) = 0 ) ( str[0] = str[0] || ',' || str[iteration_number+1] )order by job; JOB STR --------- ----------------------------------- ANALYST 3000,3000 CLERK 1300,950,800,1100 MANAGER 2850,2975,2450 PRESIDENT 5000 SALESMAN 1500,1250,1250,1600
Условия MODEL выполняются после всех условий запроса, исключая SELECT DISTINCT и ORDER BY. Далее рассмотрим возможности MODEL более подробно.
DIMENSION BY
DIMENSION BY определяет столбцы SQL запроса, с помощью которых для любой ячейки можно сопоставить единственную строку.В примерах ниже мы не будем манипулировать данными, а только покажем примеры использования DIMENSION BY для лучшего понимания. Посмотрим на таблицу EMP
SQL> select * from scott.emp t ; EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO ----- ---------- --------- ----- ----------- --------- --------- ------ 7369 SMITH CLERK 7902 17.12.1980 800,00 20 7499 ALLEN SALESMAN 7698 20.02.1981 1600,00 300,00 30 7521 WARD SALESMAN 7698 22.02.1981 1250,00 500,00 30 7566 JONES MANAGER 7839 02.04.1981 2975,00 20 7654 MARTIN SALESMAN 7698 28.09.1981 1250,00 1400,00 30 7698 BLAKE MANAGER 7839 01.05.1981 2850,00 30 7782 CLARK MANAGER 7839 09.06.1981 2450,00 10 7788 SCOTT ANALYST 7566 09.12.1982 3000,00 20 7839 KING PRESIDENT 17.11.1981 5000,00 10 7844 TURNER SALESMAN 7698 08.09.1981 1500,00 0,00 30 7876 ADAMS CLERK 7788 12.01.1983 1100,00 20 7900 JAMES CLERK 7698 03.12.1981 950,00 30 7902 FORD ANALYST 7566 03.12.1981 3000,00 20 7934 MILLER CLERK 7782 23.01.1982 1300,00 10 14 rows selected
В качестве уникального идентификатора используется EMPNO. Значит, это наш потенциальный столбец для dimension. Не обращаем пока внимание на MEASURES и RULES условия.
select empno, ename from scott.emp t model dimension by (empno)measures (ename)rules ()order by empno; EMPNO ENAME ---------- ---------- 7369 SMITH 7499 ALLEN 7521 WARD 7566 JONES 7654 MARTIN 7698 BLAKE 7782 CLARK 7788 SCOTT 7839 KING 7844 TURNER 7876 ADAMS 7900 JAMES 7902 FORD 7934 MILLER 14 rows selected
Если необходимо, можно определять более чем одну колонку.
select empno, job, ename from scott.emp t model dimension by (empno, job)measures (ename)rules ()order by empno; EMPNO JOB ENAME ---------- --------- ---------- 7369 CLERK SMITH 7499 SALESMAN ALLEN 7521 SALESMAN WARD 7566 MANAGER JONES 7654 SALESMAN MARTIN 7698 MANAGER BLAKE 7782 MANAGER CLARK 7788 ANALYST SCOTT 7839 PRESIDENT KING 7844 SALESMAN TURNER 7876 CLERK ADAMS 7900 CLERK JAMES 7902 ANALYST FORD 7934 CLERK MILLER 14 rows selected
Нельзя использовать алиасы из SELECT условия.
SQL> select empno as id, ename from scott.emp t model 2 dimension by (id) 3 measures (ename) 4 rules () 5 order by empno; ORA-00904: "ID": недопустимый идентификатор SQL> select empno * 10 as id, ename from scott.emp t model 2 dimension by (id) 3 measures (ename) 4 rules () 5 order by empno; ORA-00904: "ID": недопустимый идентификатор
Можно использовать алиасы напрямую в dimension by.
SQL> select id, ename from scott.emp t model 2 dimension by (empno * 10 as id) 3 measures (ename) 4 rules () 5 order by id; ID ENAME ---------- ---------- 73690 SMITH 74990 ALLEN 75210 WARD 75660 JONES 76540 MARTIN 76980 BLAKE 77820 CLARK 77880 SCOTT 78390 KING 78440 TURNER 78760 ADAMS 79000 JAMES 79020 FORD 79340 MILLER 14 rows selected
По умолчанию, если dimension by не дает уникального ключа для определения строки, то мы получаем ошибку.
SQL> select job, ename from scott.emp t model 2 dimension by (job) 3 measures (ename) 4 rules () 5 order by job;ORA-32638: Неуникальная адресация в измерениях MODEL
Но мы можем ослабить это правило, используя UNIQUE SINGLE REFERENCE
SQL> select job, ename from scott.emp t model UNIQUE SINGLE REFERENCE 2 dimension by (job) 3 measures (ename) 4 rules () 5 order by job; JOB ENAME --------- ---------- ANALYST SCOTT ANALYST FORD CLERK MILLER CLERK JAMES CLERK SMITH CLERK ADAMS MANAGER BLAKE MANAGER JONES MANAGER CLARK PRESIDENT KING SALESMAN TURNER SALESMAN MARTIN SALESMAN WARD SALESMAN ALLEN 14 rows selected
Но данное условие, накладывает ряд ограничений по доступу к ячейкам запроса. (рассмотрим далее)
MEASURES
Условие MEASURES определяет какие колонки из sql запроса мы будем использовать для доступа к данным. Количество столбцов может быть 1 или больше.
select empno, ename, sal from scott.emp t model dimension by (empno)measures (ename, sal)rules ()order by empno; EMPNO ENAME SAL ---------- ---------- ---------- 7369 SMITH 800 7499 ALLEN 1600 7521 WARD 1250 7566 JONES 2975 7654 MARTIN 1250 7698 BLAKE 2850 7782 CLARK 2450 7788 SCOTT 3000 7839 KING 5000 7844 TURNER 1500 7876 ADAMS 1100 7900 JAMES 950 7902 FORD 3000 7934 MILLER 1300 14 rows selected
Можно определять константы, выражения
select empno, ename, sal, date_now from scott.emp t model dimension by (empno)measures (ename, sal * 100 as sal, sysdate as date_now) rules () order by empno; EMPNO ENAME SAL DATE_NOW ---------- ---------- ---------- ----------- 7369 SMITH 80000 06.04.2010 7499 ALLEN 160000 06.04.2010 7521 WARD 125000 06.04.2010 7566 JONES 297500 06.04.2010 7654 MARTIN 125000 06.04.2010 7698 BLAKE 285000 06.04.2010 7782 CLARK 245000 06.04.2010 7788 SCOTT 300000 06.04.2010 7839 KING 500000 06.04.2010 7844 TURNER 150000 06.04.2010 7876 ADAMS 110000 06.04.2010 7900 JAMES 95000 06.04.2010 7902 FORD 300000 06.04.2010 7934 MILLER 130000 06.04.2010 14 rows selected
DIMENSION и MEASURES
Нельзя обращаться к столбцу, если он отсутствует в dimension by и measures
SQL> select empno, ename, sal from scott.emp t model 2 dimension by (empno) 3 measures (ename) 4 rules () 5 order by empno; ORA-32614: недопустимое выражение MODEL SELECT
Нельзя использовать колонку в двух условиях сразу
SQL> select empno, ename from scott.emp t model 2 dimension by (empno) 3 measures (empno, ename) 4 rules () 5 order by empno; ORA-00957: дублируется имя столбца
Константа NULL не разрешена
SQL> select empno, ename from scott.emp t model 2 dimension by (empno, null as test) 3 measures (ename) 4 rules () 5 order by empno; ORA-01723: столбец нулевой длины недопустим SQL> select empno, ename from scott.emp t model 2 dimension by (empno) 3 measures (ename, '' as test) 4 rules () 5 order by empno; ORA-01723: столбец нулевой длины недопустим
Вместо NULL следует использовать CAST
SQL> set null SQL> select empno, ename, test from scott.emp t model 2 dimension by (empno) 3 measures (ename, CAST( NULL AS VARCHAR2(10) ) as test) 4 rules () 5 order by empno; EMPNO ENAME TEST ---------- ---------- ---------- 7369 SMITH 7499 ALLEN 7521 WARD 7566 JONES 7654 MARTIN 7698 BLAKE 7782 CLARK 7788 SCOTT 7839 KING 7844 TURNER 7876 ADAMS 7900 JAMES 7902 FORD 7934 MILLER 14 rows selected
Если будет превышена допустимая длина поля, получим ошибку
SQL> select empno, ename, test from scott.emp t model 2 dimension by (empno) 3 measures (ename, CAST( NULL AS VARCHAR2(10) ) as test) 4 rules (test[any] = '12345678910') 5 order by empno; ORA-25137: Нарушен диапазон значений данных
RULES
Условие rules описывает расчёт значений для блока measures.
Основные правила
Условие rules может быть пустым
select empno, job, enamefrom scott.emp t model dimension by(empno, job)measures(ename)rules()order by empno; EMPNO JOB ENAME ---------- --------- ---------- 7369 CLERK SMITH 7499 SALESMAN ALLEN 7521 SALESMAN WARD 7566 MANAGER JONES 7654 SALESMAN MARTIN 7698 MANAGER BLAKE 7782 MANAGER CLARK 7788 ANALYST SCOTT 7839 PRESIDENT KING 7844 SALESMAN TURNER 7876 CLERK ADAMS 7900 CLERK JAMES 7902 ANALYST FORD 7934 CLERK MILLER 14 rows selected
Мы можем изменять любое значения колонок из measures
select empno, job, enamefrom scott.emp t model dimension by(empno)measures(job, ename)rules( ename[7839] ='YOU!!!', ename[empno < 7788] = 'Эй ты', ename[empno BETWEEN 7900 and 7902 ] = 'O-LO-LO' )order by empno; EMPNO JOB ENAME ---------- --------- ---------- 7369 CLERK Эй ты 7499 SALESMAN Эй ты 7521 SALESMAN Эй ты 7566 MANAGER Эй ты 7654 SALESMAN Эй ты 7698 MANAGER Эй ты 7782 MANAGER Эй ты 7788 ANALYST SCOTT 7839 PRESIDENT YOU!!! 7844 SALESMAN TURNER 7876 CLERK ADAMS 7900 CLERK O-LO-LO 7902 ANALYST O-LO-LO 7934 CLERK MILLER 14 rows selected
Условие ename[7839] называется «cell reference» и определяет значение колонки, для которой значение empno (ключ из dimension by) равно 7839. Cell reference может указывать только на колонку measures. Когда cell reference используется для присвоения некого значения, на левой стороне условия (относительно знака =) , то используется название «cell assignment». Для правой части условия cell reference не имеет ни каких спец. названий. Часть условия заключенная в квадратные скобки (7839, empno < 7788) называется «dimension reference». Dimension references для всех cell references может содержать как константы, так и различные условия. Для cell asignment можно использовать ключевое слово ANY — любое значение.
select empno, job, enamefrom scott.emp t model dimension by(empno)measures(job, ename)rules( ename[any] = 'QWERTY' )order by empno; EMPNO JOB ENAME ---------- --------- ---------- 7369 CLERK QWERTY 7499 SALESMAN QWERTY 7521 SALESMAN QWERTY 7566 MANAGER QWERTY 7654 SALESMAN QWERTY 7698 MANAGER QWERTY 7782 MANAGER QWERTY 7788 ANALYST QWERTY 7839 PRESIDENT QWERTY 7844 SALESMAN QWERTY 7876 CLERK QWERTY 7900 CLERK QWERTY 7902 ANALYST QWERTY 7934 CLERK QWERTY 14 rows selected
Можно использовать вложенные cell references, но только для определения одной ячейки
select empno, job, enamefrom scott.emp t model dimension by(empno)measures(job, ename, empno as empno2)rules( ename[ (empno2[7900] + 2) ] = null )order by empno; EMPNO JOB ENAME ---------- --------- ---------- 7369 CLERK SMITH 7499 SALESMAN ALLEN 7521 SALESMAN WARD 7566 MANAGER JONES 7654 SALESMAN MARTIN 7698 MANAGER BLAKE 7782 MANAGER CLARK 7788 ANALYST SCOTT 7839 PRESIDENT KING 7844 SALESMAN TURNER 7876 CLERK ADAMS 7900 CLERK JAMES 7902 ANALYST 7934 CLERK MILLER 14 rows selected
Если значение dimension is null, то оно будет попадать под следующие условия • [any] • [group_1 is any] • [null] • [group_1 is null] Условие типа «[group_1 = null]» не сработает
select id , using_any , using_is_any , using_null , using_is_null , using_equals_nullfrom (select 'A' id from dualunion all select null from dual) tmodel dimension by( id )measures ( 'N' as using_any , 'N' as using_is_any , 'N' as using_null , 'N' as using_is_null , 'N' as using_equals_null )rules ( using_any [ ANY ] = 'Y' , using_is_any [ id IS ANY ] = 'Y' , using_null [ NULL ] = 'Y' , using_is_null [ id IS NULL ] = 'Y' , using_equals_null[ id = NULL ] = 'Y' ) ; ID USING_ANY USING_IS_ANY USING_NULL USING_IS_NULL USING_EQUALS_NULL -- --------- ------------ ---------- ------------- ----------------- A Y Y N N N Y Y Y Y N
Если мы попробуем изменить dimension столбец, то получим ошибку
SQL> select empno, job, ename 2 from scott.emp t model 3 dimension by(empno) 4 measures(job, ename) 5 rules( 6 empno[7369] = null 7 ) 8 order by empno;ORA-00904: : недопустимый идентификатор
Если указано неверное количество значений для dimension references, то получим ошибку
SQL> select empno, job, ename 2 from scott.emp t model 3 dimension by(empno, job) 4 measures(ename) 5 rules( 6 ename[7499] = 'QWERTY' 7 ) 8 order by empno;ORA-00947: не хватает значений для данных
Использовать dimension столбец в правой части условия для dimension references нельзя
SQL> select empno, job, ename 2 from scott.emp t model 3 dimension by(empno, job) 4 measures(ename) 5 rules( 6 ename[7499,length(job) < empno ] = 'QWERTY' 7 ) 8 order by empno;ORA-32625: недопустимое измерение в предикате ссылки на ячейку
Если вложенные cell references определяют более чем одну ячейку мы получим ошибку
SQL> select empno, job, ename 2 from scott.emp t model 3 dimension by(empno) 4 measures(job, ename) 5 rules( 6 ename[ (job[any]) ] = null 7 ) 8 order by empno;ORA-32622: недопустимая ссылка на несколько ячеек
FOR Loops
Для dimension references возможно использование цикла.
Запрос без использования цикла.
select deptno, dname, locfrom scott.dept t model dimension by(deptno)measures(dname, loc)rules( loc[20] = 'SPB', loc[30] = 'SPB', loc[40] = 'SPB' )order by deptno; DEPTNO DNAME LOC ---------- -------------- ------------- 10 ACCOUNTING NEW YORK 20 RESEARCH SPB 30 SALES SPB 40 OPERATIONS SPB
С циклом
select deptno, dname, locfrom scott.dept t model dimension by(deptno)measures(dname, loc)rules( loc[FOR deptno FROM 20 TO 40 INCREMENT 10] = 'SPB' )order by deptno; DEPTNO DNAME LOC ---------- -------------- ------------- 10 ACCOUNTING NEW YORK 20 RESEARCH SPB 30 SALES SPB 40 OPERATIONS SPB
или
select deptno, dname, locfrom scott.dept t model dimension by(deptno)measures(dname, loc)rules( loc[FOR deptno in (20,30,40) ] = 'SPB' )order by deptno; DEPTNO DNAME LOC ---------- -------------- ------------- 10 ACCOUNTING NEW YORK 20 RESEARCH SPB 30 SALES SPB 40 OPERATIONS SPB
Можно использовать комбинирование строки со значением из цикла
with t as (select 'W-'||rownum as id, ename, jobfrom scott.emp)select * from t model dimension by(id)measures(ename, job)rules( job[FOR id LIKE 'W-%' FROM 2 TO 14 INCREMENT 2 ] = null ) ID ENAME JOB ------------------------- ---------- --------- W-1 SMITH CLERK W-2 ALLEN W-3 WARD SALESMAN W-4 JONES W-5 MARTIN SALESMAN W-6 BLAKE W-7 CLARK MANAGER W-8 SCOTT W-9 KING PRESIDENT W-10 TURNER W-11 ADAMS CLERK W-12 JAMES W-13 FORD ANALYST W-14 MILLER 14 rows selected
.
UNIQUE SINGLE REFERENCE
Данное свойство позволяет иметь дубликаты ключевых значений в запросе.
SQL> select * from scott.emp t model 2 dimension by (job) 3 measures (ename, sal) 4 rules () 5 order by job 6 ;ORA-32638: Неуникальная адресация в измерениях MODEL
Указываем UNIQUE SINGLE REFERENCE
SQL> select * from scott.emp t 2 model UNIQUE SINGLE REFERENCE 3 dimension by (job) 4 measures (ename, sal) 5 rules () 6 order by job; JOB ENAME SAL --------- ---------- ---------- ANALYST SCOTT 3000 ANALYST FORD 3000 CLERK MILLER 1300 CLERK JAMES 950 CLERK SMITH 800 CLERK ADAMS 1100 MANAGER BLAKE 2850 MANAGER JONES 2975 MANAGER CLARK 2450 PRESIDENT KING 5000 SALESMAN TURNER 1500 SALESMAN MARTIN 1250 SALESMAN WARD 1250 SALESMAN ALLEN 1600 14 rows selected
Можно задавать правила для все строк
SQL> select * from scott.emp t 2 model UNIQUE SINGLE REFERENCE 3 dimension by (job) 4 measures (ename, sal) 5 rules (sal[any]=9999) 6 order by job; JOB ENAME SAL --------- ---------- ---------- ANALYST SCOTT 9999 ANALYST FORD 9999 CLERK MILLER 9999 CLERK JAMES 9999 CLERK SMITH 9999 CLERK ADAMS 9999 MANAGER BLAKE 9999 MANAGER JONES 9999 MANAGER CLARK 9999 PRESIDENT KING 9999 SALESMAN TURNER 9999 SALESMAN MARTIN 9999 SALESMAN WARD 9999 SALESMAN ALLEN 9999 14 rows selected
Можно ограничивать левое условие rules
SQL> select * from scott.emp t 2 model UNIQUE SINGLE REFERENCE 3 dimension by (job) 4 measures (ename, sal) 5 rules (sal['CLERK']=9999) 6 order by job; JOB ENAME SAL --------- ---------- ---------- ANALYST SCOTT 3000 ANALYST FORD 3000 CLERK ADAMS 9999 CLERK MILLER 9999 CLERK SMITH 9999 CLERK JAMES 9999 MANAGER JONES 2975 MANAGER BLAKE 2850 MANAGER CLARK 2450 PRESIDENT KING 5000 SALESMAN ALLEN 1600 SALESMAN MARTIN 1250 SALESMAN WARD 1250 SALESMAN TURNER 1500 14 rows selected
Но нельзя указывать в правой части условия rules ссылку на неуникальную ячейку
SQL> select * from scott.emp t 2 model UNIQUE SINGLE REFERENCE 3 dimension by (job) 4 measures (ename, sal) 5 rules (sal[any]= sal['MANAGER']) 6 order by job;ORA-32638: Неуникальная адресация в измерениях MODEL
.
Функция CV()
Если нам необходимо получить значение ячейки из dimension, то использовать cell references мы не можем. Но мы можем использовать функцию CV() , которая дает доступ к текущему значению dimension.
select * from scott.emp tmodel dimension by (empno)measures (job,ename, 0 sub_empno)rules ( sub_empno[any] = cv(empno) * 10 ) order by empno; EMPNO JOB ENAME SUB_EMPNO ---------- --------- ---------- ---------- 7369 CLERK SMITH 73690 7499 SALESMAN ALLEN 74990 7521 SALESMAN WARD 75210 7566 MANAGER JONES 75660 7654 SALESMAN MARTIN 76540 7698 MANAGER BLAKE 76980 7782 MANAGER CLARK 77820 7788 ANALYST SCOTT 77880 7839 PRESIDENT KING 78390 7844 SALESMAN TURNER 78440 7876 CLERK ADAMS 78760 7900 CLERK JAMES 79000 7902 ANALYST FORD 79020 7934 CLERK MILLER 79340 14 rows selected
Можно использовать функцию CV() без аргумента для возврата текущего значения dimension относительно позиции в cell reference.
select * from scott.emp tmodel dimension by (empno, job)measures (ename, empno as sub_empno)rules ( sub_empno[any,any] = sub_empno[cv(),cv()] * 10 )order by empno; EMPNO JOB ENAME SUB_EMPNO ---------- --------- ---------- ---------- 7369 CLERK SMITH 73690 7499 SALESMAN ALLEN 74990 7521 SALESMAN WARD 75210 7566 MANAGER JONES 75660 7654 SALESMAN MARTIN 76540 7698 MANAGER BLAKE 76980 7782 MANAGER CLARK 77820 7788 ANALYST SCOTT 77880 7839 PRESIDENT KING 78390 7844 SALESMAN TURNER 78440 7876 CLERK ADAMS 78760 7900 CLERK JAMES 79000 7902 ANALYST FORD 79020 7934 CLERK MILLER 79340 14 rows selected
Для функции CV() нельзя использовать значение measures
SQL> select * from scott.emp t 2 model 3 dimension by (empno) 4 measures (job,ename, empno as sub_empno) 5 rules ( 6 sub_empno[any] = cv(sub_empno) * 10 7 ) 8 order by empno;ORA-00904: : недопустимый идентификатор
Нельзя использовать вне dimension references функцию CV() без аргумента
SQL> select * from scott.emp t 2 model 3 dimension by (empno) 4 measures (job,ename, 0 sub_empno) 5 rules ( 6 sub_empno[any] = cv() * 10 7 ) 8 order by empno;ORA-32611: некорректное использование оператора MODEL CV
.
PARTITON BY
Позволяет ускорить обработку данных на многопроцессорных системах и в некоторых случаях сокращает код в dimension references.
select * from scott.emp tmodel partition by (deptno)dimension by (job,ename)measures (sal, sal as new_sal)rules ( new_sal['CLERK' , any] = sal[cv(), cv()] * 2, new_sal['MANAGER' , any] = sal[cv(), cv()] * 3, new_sal['SALESMAN', any] = sal[cv(), cv()] * 4 )order by deptno,job,ename; DEPTNO JOB ENAME SAL NEW_SAL ---------- --------- ---------- ---------- ---------- 10 CLERK MILLER 1300 2600 10 MANAGER CLARK 2450 7350 10 PRESIDENT KING 5000 5000 20 ANALYST FORD 3000 3000 20 ANALYST SCOTT 3000 3000 20 CLERK ADAMS 1100 2200 20 CLERK SMITH 800 1600 20 MANAGER JONES 2975 8925 30 CLERK JAMES 950 1900 30 MANAGER BLAKE 2850 8550 30 SALESMAN ALLEN 1600 6400 30 SALESMAN MARTIN 1250 5000 30 SALESMAN TURNER 1500 6000 30 SALESMAN WARD 1250 5000 14 rows selected
.
.
Агрегатные и аналитические функции
При использовании условия model мы не можем определять агрегатные или аналитические функции в SELECT условии.
SQL> select empno, max(job), max(ename), max(sal) from scott.emp t 2 group by empno 3 model 4 dimension by (empno) 5 measures (job, ename, sal) 6 rules () 7 order by job; ORA-00979: выражение не является выражением GROUP BY
Но, можно использовать в PARTITION BY, DIMENSION BY, MEASURES или RULES условиях.
select empno, job, sal from scott.emp t group by empno model dimension by (empno, max(job) as job) measures (sum(sal) as sal) rules ( sal[any,'PRESIDENT'] = sal[cv(),'PRESIDENT']/2 ) order by job; EMPNO JOB SAL ---------- --------- ---------- 7788 ANALYST 3000 7902 ANALYST 3000 7876 CLERK 1100 7369 CLERK 800 7900 CLERK 950 7934 CLERK 1300 7698 MANAGER 2850 7566 MANAGER 2975 7782 MANAGER 2450 7839 PRESIDENT 2500 7654 SALESMAN 1250 7521 SALESMAN 1250 7499 SALESMAN 1600 7844 SALESMAN 1500 14 rows selected
Агрегатные и аналитические функции можно использовать в правой части условия rules, в левой части использовать нельзя.
select empno, job, sal from scott.emp t model dimension by (empno, job) measures (sal) rules ( sal[any,'PRESIDENT'] = sum(sal)[any,'CLERK'] ) order by job; EMPNO JOB SAL ---------- --------- ---------- 7788 ANALYST 3000 7902 ANALYST 3000 7876 CLERK 1100 7934 CLERK 1300 7900 CLERK 950 7369 CLERK 800 7698 MANAGER 2850 7782 MANAGER 2450 7566 MANAGER 2975 7839 PRESIDENT 4150 7521 SALESMAN 1250 7499 SALESMAN 1600 7654 SALESMAN 1250 7844 SALESMAN 1500
Дополнительную информацию можно посмотреть здесь www.sqlsnippets.com и здесь SQL for Modeling
Понятно написано, спасибо.
Только из текста выше, непонятно, а что model такого дает, чего нельзя достичь обычными средставами. Хотя бы 1-2 примера?
@Андрей
Спасибо за комментарий, обязательно добавлю пару примеров.