SQL Cookbook

1,463 views

Published on

0 Comments
3 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total views
1,463
On SlideShare
0
From Embeds
0
Number of Embeds
2
Actions
Shares
0
Downloads
43
Comments
0
Likes
3
Embeds 0
No embeds

No notes for slide

SQL Cookbook

  1. 1. SQL Cookbook Graeme Birchall 29-Nov-2006
  2. 2. DB2 9 Cookbook © Introduction These overhead slides can be used in conjunction my SQL Cookbook to teach basic DB2 SQL to a small audience. Based on my own teaching experiences, the class should take about two days to complete, but if might be better to do it over three days. There are no exercises. As much as possible, I have tried to make every slide self-contained. Thus, it should have some sample SQL, the input data, and the answer. And with very few exceptions, I've laid out the slides in the same sequence as the examples in the related SQL Cookbook. Disclaimer & Copyright DISCLAIMER: What can I say, there are bound to be errors, use at your own risk. COPYRIGHT: COPYRIGHT: You can make as many copies of these class notes as you wish. And I en- courage you to teach them to others. But you cannot sell them, nor change for them (other than to recover reproduction costs), nor claim the material as your own, nor replace my name with another. Secondary distribution for gain is not allowed. When used for teaching, you can charge for your time and materials (and your expertise). But you cannot charge any licensing fee, nor claim an exclusive right of use. TRADEMARKS: Lots of words in this document, like "DB2", are registered trademarks of the IBM Corporation. And lots and lots of other words, like "Windows", are registered trademarks of the Microsoft Corporation. Adobe Acrobat is a registered trademark of the Adobe Corporation. Author Author: Graeme Birchall © Email: Graeme_Birchall@verizon.net Web: http://mysite.verizon.net/Graeme_Birchall/ Title: DB2 9 SQL Cookbook © Date: 29-Nov-2006 Introduction to SQL 2
  3. 3. DB2 9 Cookbook © Document History Course Editions This document is a work in progress. So far, it has been updated as follows: 2000-12-04: Initial edition. Included chapters on: Joins, Sub-queries, Unions, Recursive SQL, Fun with SQL, and Quirks in SQL. 2001-01-03: Two new chapters added: Introduction to SQL, and Column Functions. 2001-02-06: Added new chapter on Scalar Functions (selected). 2001-04-11: Replace chapter on sub-queries. 2001-11-21: Update for DB2 V7.2. Also added chapter on Identity Columns. 2001-12-07: Added chapter on OLAP Functions and GROUP BY. 2002-03-11: Minor changes, mostly to section on precedence rules.. 2002-08-20: V8.1 (beta) edition. Lots of changes in lots of places. 2003-01-02: V8.1 (final) edition. Very minor changes. 2003-07-11: Added section on DML and chapter on Compound SQL. 2003-09-04: Few minor updates. 2003-12-31: Tidied up some SQL, and added section on MERGE. 2004-07-21: Added section of SELECT from DML. Tidied up some code. 2004-11-03: Reissued for V8.2. No major changes. 2006-09-13: Reissued for V9.1. No major changes. 2006-11-06: Removed all references to "UDB". 2006-11-29: Changed all "DB2 V9" to "DB2 9". Please Share The more people that use this material, the more inclined I am to do more work keeping it up to date. If you like what you have, please tell other people about it. Introduction to SQL 3
  4. 4. DB2 9 Cookbook © Table of Contents Introduction to SQL .......................................................................................................................... 5 DML Statements.............................................................................................................................. 48 Compound SQL .............................................................................................................................. 63 Column Functions .......................................................................................................................... 75 OLAP Functions.............................................................................................................................. 92 Scalar Functions........................................................................................................................... 117 User-Defined Functions ............................................................................................................... 138 Order By, Group By, and Having................................................................................................. 151 Joins .............................................................................................................................................. 165 Sub-Query ..................................................................................................................................... 189 Union, Intersect, and Except ....................................................................................................... 219 Union, Intersect, and Except ....................................................................................................... 228 Identity Columns and Sequences ............................................................................................... 237 Temporary Tables......................................................................................................................... 259 Recursive SQL .............................................................................................................................. 278 Fun with SQL................................................................................................................................. 302 Quirks in SQL................................................................................................................................ 323 Introduction to SQL 4
  5. 5. DB2 9 Cookbook © Introduction to SQL Introduction to SQL 5
  6. 6. DB2 9 Cookbook © Syntax Diagram Conventions Start , Continue Default ALL SELECT an item DISTINCT * Resume Repeat End , FROM table name view name WHERE expression and / or Mandatory Optional Notes • Upper case text is a SQL keyword • Italic text is a placeholder, or explained elsewhere • Backward arrows enable one to repeat phrases • Branch line going above main line is default • Branch line going below main line is optional Introduction to SQL 6
  7. 7. DB2 9 Cookbook © Statement Delimiters --#SET DELIMITER ! SELECT name FROM staff WHERE id = 10! --#SET DELIMITER ; SELECT name FROM staff WHERE id = 20; Notes • DB2 does not come with an "official" statement delimiter • Most people, most of the time, use the semi-colon • The semi-colon does not work for compound SQL • In DB2BATCH, you can set the value (see above) Introduction to SQL 7
  8. 8. DB2 9 Cookbook © Table Definitions CREATE TABLE employee (empno CHARACTER (00006) NOT NULL ,firstnme VARCHAR (00012) NOT NULL ,midinit CHARACTER (00001) NOT NULL ,lastname VARCHAR (00015) NOT NULL ,workdept CHARACTER (00003) ,phoneno CHARACTER (00004) ,hiredate DATE ,job CHARACTER (00008) ,edlevel SMALLINT NOT NULL ,sex CHARACTER (00001) ,birthdate DATE ,salary DECIMAL (00009,02) ,bonus DECIMAL (00009,02) ,comm DECIMAL (00009,02) ) DATA CAPTURE NONE; DB2 Sample Tables • Supplied by IBM • See SAMPLE Database • Used throughout this course Introduction to SQL 8
  9. 9. DB2 9 Cookbook © View Definitions Queries Data Table CREATE VIEW employee_view AS SELECT a.empno, a.firstnme, a.salary, a.workdept FROM employee a WHERE a.salary >= (SELECT AVG(b.salary) FROM employee b WHERE a.workdept = b.workdept); Makes 3 rows - Using VALUES Clause CREATE VIEW silly (c1, c2, c3) AS VALUES (11, 'AAA', SMALLINT(22)) ,(12, 'BBB', SMALLINT(33)) ,(13, 'CCC', NULL); Makes 10,000 rows - Using Recursion CREATE VIEW test_data AS WITH temp1 (num1) AS (VALUES (1) UNION ALL SELECT num1 + 1 FROM temp1 WHERE num1 < 10000) SELECT * FROM temp1; Introduction to SQL 9
  10. 10. DB2 9 Cookbook © DB2 Default Data Types Standard DB2 Data Types • SMALLINT, INT, and BIGINT (i.e. integer numbers). • FLOAT, REAL, and DOUBLE (i.e. floating point numbers). • DECIMAL and NUMERIC (i.e. decimal numbers). • CHAR, VARCHAR, and LONG VARCHAR (i.e. character values). • GRAPHIC, VARGRAPHIC, and LONG VARGRAPHIC (i.e. graphical values). • BLOB, CLOB, and DBCLOB (i.e. binary and character long object values). • DATE, TIME, and TIMESTAMP (i.e. date/time values). • DATALINK (i.e. link to external object). Numeric Data - Recommended Uses • Monetary data - use DECIMAL • Non-fractional numbers - use SMALLINT, INTEGER, or BIGINT • Absolute precision not required - use FLOAT Introduction to SQL 10
  11. 11. DB2 9 Cookbook © DB2 Special Registers SPECIAL REGISTER UPDATE DATA-TYPE =============================================== ====== ============= CURRENT CLIENT_ACCTNG no VARCHAR(255) CURRENT CLIENT_APPLNAME no VARCHAR(255) CURRENT CLIENT_USERID no VARCHAR(255) CURRENT CLIENT_WRKSTNNAME no VARCHAR(255) CURRENT DATE no DATE CURRENT DBPARTITIONNUM no INTEGER CURRENT DEFAULT TRANSFORM GROUP yes VARCHAR(18) CURRENT DEGREE yes CHAR(5) CURRENT EXPLAIN MODE yes VARCHAR(254) CURRENT EXPLAIN SNAPSHOT yes CHAR(8) CURRENT ISOLATION yes CHAR(2) CURRENT LOCK TIMEOUT yes INTEGER CURRENT MAINTAINED TABLE TYPES FOR OPTIMIZATION yes VARCHAR(254) CURRENT PACKAGE PATH yes VARCHAR(4096) CURRENT PATH yes VARCHAR(254) CURRENT QUERY OPTIMIZATION yes INTEGER CURRENT REFRESH AGE yes DECIMAL(20,6) CURRENT SCHEMA yes VARCHAR(128) CURRENT SERVER no VARCHAR(18) CURRENT TIME no TIME CURRENT TIMESTAMP no TIMESTAMP CURRENT TIMEZONE no DECIMAL(6,0) CURRENT USER no VARCHAR(128) SESSION_USER yes VARCHAR(128) SYSTEM_USER no VARCHAR(128) USER yes VARCHAR(128) Introduction to SQL 11
  12. 12. DB2 9 Cookbook © DB2 Distinct Data Types (1 of 2) Syntax CREATE DISTINCT TYPE type-name source-type WITH COMPARISONS Example CREATE DISTINCT TYPE USA_DOLLARS AS DECIMAL(9,2) WITH COMPARISONS; CREATE DISTINCT TYPE EUR_DOLLARS AS DECIMAL(9,2) WITH COMPARISONS; Notes • User-defined data types • Based on existing DB2 data types • Used to limit certain types of usage (e.g. addition) • Creation of distinct type also creates two functions: - To convert data from base type to distinct type - To convert data from distinct type to base type • Distinct type supports following comparison operators: =, <>, <, <=, >, and >= Introduction to SQL 12
  13. 13. DB2 9 Cookbook © DB2 Distinct Data Types (2 of 2) Syntax CREATE DISTINCT TYPE type-name source-type WITH COMPARISONS Example CREATE DISTINCT TYPE USA_DOLLARS AS DECIMAL(9,2) WITH COMPARISONS; CREATE DISTINCT TYPE EUR_DOLLARS AS DECIMAL(9,2) WITH COMPARISONS; Usage CREATE TABLE customer (id INTEGER NOT NULL ,fname VARCHAR(00010) NOT NULL WITH DEFAULT '' ,lname VARCHAR(00015) NOT NULL WITH DEFAULT '' ,date_of_birth DATE ,citizenship CHAR(03) ,usa_sales USA_DOLLARS ,eur_sales EUR_DOLLARS ,sales_office# SMALLINT ,last_updated TIMESTAMP ,PRIMARY KEY(id)); Introduction to SQL 13
  14. 14. DB2 9 Cookbook © SELECT Statement Syntax General SELECT statement , WITH common table expression ORDER BY clause FIRST FETCH clause READ-ONLY clause FOR UPDATE clause OPTIMIZE FOR clause SELECT Statement , SELECT an item * , FROM table name view name correlation name alias name AS ( full select ) WHERE expression and /or Introduction to SQL 14
  15. 15. DB2 9 Cookbook © Sample SELECT Statements (1 of 2) Select Specific Columns SELECT deptno ANSWER ,admrdept =================== ,'ABC' AS abc DEPTNO ADMRDEPT ABC FROM department ------ -------- --- WHERE deptname LIKE '%ING%' B01 A00 ABC ORDER BY 1; D11 D01 ABC Select all Columns SELECT * ANSWER (part of) FROM department ================ WHERE deptname LIKE '%ING%' DEPTNO etc... ORDER BY 1; ------ ------>>> B01 PLANNING D11 MANUFACTU Notes • SELECT "*" implies select all columns Introduction to SQL 15
  16. 16. DB2 9 Cookbook © Sample SELECT Statements (2 of 2) Select an Individual Column, and all Columns SELECT deptno ANSWER (part of) ,department.* ======================= FROM department DEPTNO DEPTNO etc... WHERE deptname LIKE '%ING%' ------ ------ ------>>> ORDER BY 1; B01 B01 PLANNING D11 D11 MANUFACTU Select all Columns Twice SELECT department.* ANSWER (part of) ,department.* ================ FROM department DEPTNO etc... WHERE deptname LIKE '%NING%' ------ ------>>> ORDER BY 1; B01 PLANNING Introduction to SQL 16
  17. 17. DB2 9 Cookbook © Fetch First Clause 1 FETCH FIRST ROW ONLY integer ROWS Sample SQL, No ORDER BY, Gets Random Rows SELECT years ANSWER ,name ===================== ,id YEARS NAME ID FROM staff ------ --------- ---- FETCH FIRST 3 ROWS ONLY; 7 Sanders 10 8 Pernal 20 5 Marenghi 30 Notes • Stops fetching after "n" rows • If no ORDER BY, gets first "n" random rows • If ORDER BY not on unique field, also random results • See other pages for more on this subject Introduction to SQL 17
  18. 18. DB2 9 Cookbook © FIRST FETCH and Unique Fields ORDER BY not on unique field(s), Random rows returned SELECT years ANSWER ,name ===================== ,id YEARS NAME ID FROM staff ------ --------- ---- WHERE years IS NOT NULL 13 Graham 310 ORDER BY years DESC 12 Jones 260 FETCH FIRST 3 ROWS ONLY; 10 Hanes 50 ORDER BY on unique field(s) SELECT years ANSWER ,name ===================== ,id YEARS NAME ID FROM staff ------ --------- ---- WHERE years IS NOT NULL 13 Graham 310 ORDER BY years DESC 12 Jones 260 ,id DESC 10 Quill 290 FETCH FIRST 3 ROWS ONLY; Notes • There is no unique index on YEARS field Introduction to SQL 18
  19. 19. DB2 9 Cookbook © Correlation Name In Nested Table Expression SELECT a.empno ANSWER ,a.lastname ================= FROM employee A EMPNO LASTNAME ,(SELECT MAX(empno)AS empno ------ ---------- FROM employee) AS b 000340 GOUNOT WHERE a.empno = b.empno; In Join SELECT a.empno ANSWER ,a.lastname ====================== ,b.deptno AS dept EMPNO LASTNAME DEPT FROM employee A ------ ---------- ---- ,department b 000090 HENDERSON E11 WHERE a.workdept = b.deptno 000280 SCHNEIDER E11 AND a.job <> 'SALESREP' 000290 PARKER E11 AND b.deptname = 'OPERATIONS' 000300 SMITH E11 AND a.sex IN ('M','F') 000310 SETRIGHT E11 AND b.location IS NULL ORDER BY 1; Notes • If same table is accessed twice, correlation names are essential Introduction to SQL 19
  20. 20. DB2 9 Cookbook © Renaming Fields Using AS SELECT Statement SELECT empno AS e_num ANSWER ,midinit AS "m int" =================== ,phoneno AS "..." E_NUM M INT ... FROM employee ------ ----- ---- WHERE empno < '000030' 000010 I 3978 ORDER BY 1; 000020 L 3476 VIEW Definition CREATE view emp2 AS SELECT empno AS e_num ,midinit AS "m int" ,phoneno AS "..." FROM employee; ANSWER =================== SELECT * E_NUM M INT ... FROM emp2 ------ ----- ---- WHERE "..." = '3978'; 000010 I 3978 Notes • Renamed fields can be referred to in ORDER BY, and outside of full-select • Renamed fields cannot be referred to in GROUP BY, WHERE, HAVING Introduction to SQL 20
  21. 21. DB2 9 Cookbook © Null Values AVG of Field Containing Null Values SELECT AVG(comm) AS a1 ANSWER ,SUM(comm) / COUNT(*) AS a2 =============== FROM staff A1 A2 WHERE id < 100; ------- ------ 796.025 530.68 AVG of Field - Excluding Null Rows SELECT AVG(comm) AS a1 ANSWER ,SUM(comm) / COUNT(*) AS a2 =============== FROM staff A1 A2 WHERE id < 100; ------- ------ 796.025 530.68 Getting NULL result from field defined NOT NULL SELECT COUNT(*) AS num ANSWER ,MAX(lastname) AS max ======== FROM employee NUM MAX WHERE firstnme = 'FRED'; --- --- 0 - Introduction to SQL 21
  22. 22. DB2 9 Cookbook © Quotes and Double-Quotes Quotes SELECT 'JOHN' AS J1 ,'JOHN''S' AS J2 ANSWER ,'''JOHN''S''' AS J3 ============================= ,'"JOHN''S"' AS J4 J1 J2 J3 J4 FROM staff ---- ------ -------- -------- WHERE id = 10; JOHN JOHN'S 'JOHN'S' "JOHN'S" Double-quotes SELECT id AS "USER ID" ANSWER ,dept AS "D#" =============================== ,years AS "#Y" USER ID D# #Y 'TXT' "quote" fld ,'ABC' AS "'TXT'" ------- -- -- ----- ----------- ,'"' AS """quote"" fld" 10 20 7 ABC " FROM staff s 20 20 8 ABC " WHERE id < 40 30 38 5 ABC " ORDER BY "USER ID"; Notes • Use quotes to bound text • Use double-quotes to give non-standard names to objects • Two quotes or double-quotes together represent the value Introduction to SQL 22
  23. 23. DB2 9 Cookbook © Basic Predicate Syntax expresion = expression NOT <> < > <= >= Sample SQL SELECT id, job, dept ANSWER FROM staff =============== WHERE job = 'Mgr' ID JOB DEPT AND NOT job <> 'Mgr' --- ---- ---- AND NOT job = 'Sales' 10 Mgr 20 AND id <> 100 30 Mgr 38 AND id >= 0 50 Mgr 15 AND id <= 150 140 Mgr 51 AND NOT dept = 50 ORDER BY id; Introduction to SQL 23
  24. 24. DB2 9 Cookbook © Quantified Predicate (1 of 3) Syntax expression = SOME ( fullselect ) NOT <> ANY < ALL > <= >= , ( expression ) = SOME ANY Notes • Basic Predicate: Compares two values • Quantified Predicate: Compares "n" values with a collection of values (i.e. uses sub-query) Introduction to SQL 24
  25. 25. DB2 9 Cookbook © Quantified Predicate (2 of 3) Two Single-value Checks SELECT id, job ANSWER FROM staff ======== WHERE job = ANY (SELECT job FROM staff) ID JOB AND id <= ALL (SELECT id FROM staff) --- ---- ORDER BY id; 10 Mgr Multi-value Check SELECT id, dept, job ANSWER FROM staff ============== WHERE (id,dept) = ANY ID DEPT JOB (SELECT dept, id --- ---- ----- FROM staff) 20 20 Sales ORDER BY 1; Introduction to SQL 25
  26. 26. DB2 9 Cookbook © Quantified Predicate (3 of 3) , , ( expression ) = ( expression ) NOT Multi-value Check, 1 of 2 SELECT id, dept, job ANSWER FROM staff =========== WHERE (id,dept) = (30,28) ID DEPT JOB OR (id,years) = (90, 7) -- ---- --- OR (dept,job) = (38,'Mgr') 30 38 Mgr ORDER BY 1; Multi-value Check, 2 of 2 SELECT id, dept, job ANSWER FROM staff =========== WHERE (id = 30 AND dept = 28) ID DEPT JOB OR (id = 90 AND years = 7) -- ---- --- OR (dept = 38 AND job = 'Mgr') 30 38 Mgr ORDER BY 1; Introduction to SQL 26
  27. 27. DB2 9 Cookbook © BETWEEN Predicate Syntax exprsn. BETWEEN low val. AND high val. NOT NOT Sample SQL SELECT id, job ANSWER FROM staff ========= WHERE id BETWEEN 10 AND 30 ID JOB AND id NOT BETWEEN 30 AND 10 --- ----- AND NOT id NOT BETWEEN 10 AND 30 10 Mgr ORDER BY id; 20 Sales 30 Mgr Notes • Always check between LOW and HIGH Introduction to SQL 27
  28. 28. DB2 9 Cookbook © EXISTS Predicate Syntax EXISTS ( fullselect ) NOT • Sample SQL SELECT id, job ANSWER FROM staff a ========= WHERE EXISTS ID JOB (SELECT * --- ----- FROM staff b 10 Mgr WHERE b.id = a.id 20 Sales AND b.id < 50) 30 Mgr ORDER BY id; 40 Sales Notes • See Sub-Query chapter for more details Introduction to SQL 28
  29. 29. DB2 9 Cookbook © IN Predicate exprsn. IN ( fullselect ) NOT NOT , ( expression ) , expression ( expression ) IN ( fullselect ) NOT Single Value SELECT id, job ANSWER FROM staff a ========= WHERE id IN (10,20,30) ID JOB AND id IN (SELECT id --- ----- FROM staff) 10 Mgr AND id NOT IN 99 20 Sales ORDER BY id; 30 Mgr Multiple Values SELECT empno, lastname ANSWER FROM employee =============== WHERE (empno, 'AD3113') IN EMPNO LASTNAME (SELECT empno, projno ------ ------- FROM emp_act 000260 JOHNSON WHERE emptime > 0.5) 000270 PEREZ ORDER BY 1; Introduction to SQL 29
  30. 30. DB2 9 Cookbook © LIKE Predicate (1 of 2) Syntax exprsn. LIKE pattern NOT NOT ESCAPE pattern LIKE Usage SELECT id, name ANSWER FROM staff ============== WHERE name LIKE 'S%n' ID NAME OR name LIKE '_a_a%' --- --------- OR name LIKE '%r_%a' 130 Yamaguchi ORDER BY id; 200 Scoutten LIKE and ESCAPE Usage SELECT id ANSWER FROM staff ====== WHERE id = 10 ID AND 'ABC' LIKE 'AB%' --- AND 'A%C' LIKE 'A/%C' ESCAPE '/' 10 AND 'A_C' LIKE 'A_C' ESCAPE '' AND 'A_$' LIKE 'A$_$$' ESCAPE '$'; Introduction to SQL 30
  31. 31. DB2 9 Cookbook © LIKE Predicate (2 of 2) LIKE STATEMENT TEXT WHAT VALUES MATCH =========================== ====================== LIKE 'AB%' Finds AB, any string LIKE 'AB%' ESCAPE '+' Finds AB, any string LIKE 'AB+%' ESCAPE '+' Finds AB% LIKE 'AB++' ESCAPE '+' Finds AB+ LIKE 'AB+%%' ESCAPE '+' Finds AB%, any string LIKE 'AB++%' ESCAPE '+' Finds AB+, any string LIKE 'AB+++%' ESCAPE '+' Finds AB+% LIKE 'AB+++%%' ESCAPE '+' Finds AB+%, any string LIKE 'AB+%+%%' ESCAPE '+' Finds AB%%, any string LIKE 'AB++++' ESCAPE '+' Finds AB++ LIKE 'AB+++++%' ESCAPE '+' Finds AB++% LIKE 'AB++++%' ESCAPE '+' Finds AB++, any string LIKE 'AB+%++%' ESCAPE '+' Finds AB%+, any string Notes • Use escape character to search for "%" or "_" • Repeat escape character to search for itself Introduction to SQL 31
  32. 32. DB2 9 Cookbook © NULL Predicate exprsn. IS NULL NOT NOT Sample SQL SELECT id, comm ANSWER FROM staff ========= WHERE id < 100 ID COMM AND id IS NOT NULL --- ---- AND comm IS NULL 10 - AND NOT comm IS NOT NULL 30 - ORDER BY id; 50 - Notes • Can't use "=" to check for nulls • Use COALESCE function to convert null values to something else Introduction to SQL 32
  33. 33. DB2 9 Cookbook © Precedence Rules (1 of 2) Basic Arithmetic Example: 555 + -22 / (12 - 3) * 66 ANSWER ^ ^ ^ ^ ^ ====== 5th 2nd 3rd 1st 4th 423 Integer Example SELECT (12 - 3) AS int1 => 9 , -22 / (12 - 3) AS int2 => -2 , -22 / (12 - 3) * 66 AS int3 => -132 ,555 + -22 / (12 - 3) * 66 AS int4 => 432 FROM sysibm.sysdummy1; Decimal Example SELECT (12.0 - 3) AS dec1 => 9.0 , -22 / (12.0 - 3) AS dec2 => -2.4 , -22 / (12.0 - 3) * 66 AS dec3 => -161.3 ,555 + -22 / (12.0 - 3) * 66 AS dec4 => 393.6 FROM sysibm.sysdummy1; Notes • MULTIPLICATION and DIVISION before ADDITION and SUBTRACTION • INTEGER arithmetic truncates fractional results Introduction to SQL 33
  34. 34. DB2 9 Cookbook © Precedence Rules (2 of 2) And vs. OR SELECT * ANSWER>> COL1 col2 TABLE1 FROM table1 ---- ---- +---------+ WHERE col1 = 'C' A AA |COL1|COL2| AND col1 >= 'A' B BB |----|----| OR col2 >= 'AA' C CC |A |AA | ORDER BY col1; |B |BB | |C |CC | SELECT * ANSWER>> COL1 col2 +---------+ FROM table1 ---- ---- WHERE (col1 = 'C' A AA AND col1 >= 'A') B BB OR col2 >= 'AA' C CC ORDER BY col1; SELECT * ANSWER>> COL1 col2 FROM table1 ---- ---- WHERE col1 = 'C' C CC AND (col1 >= 'A' OR col2 >= 'AA') ORDER BY col1; Notes • AND operations done before OR operations • Parenthesis can be used to alter precedence Introduction to SQL 34
  35. 35. DB2 9 Cookbook © CAST Expression (1 of 2) CAST ( expression AS data-type ) NULL parameter maker Notes • Converts one data type to another • Defines field type of temporary field Convert Decimal to Integer SELECT id ANSWER ,salary ================= ,CAST(salary AS INTEGER) AS sal2 ID SALARY SAL2 FROM staff -- -------- ----- WHERE id < 30 10 18357.50 18357 ORDER BY id; 20 18171.25 18171 Introduction to SQL 35
  36. 36. DB2 9 Cookbook © CAST Expression (2 of 2) Truncate Char field SELECT id ANSWER ,job ============= ,CAST(job AS CHAR(3)) AS job2 ID JOB JOB2 FROM staff -- ----- ---- WHERE id < 30 10 Mgr Mgr ORDER BY id; 20 Sales Sal Define SMALLINT field with null values SELECT id ANSWER ,CAST(NULL AS SMALLINT) AS junk ======= FROM staff ID JUNK WHERE id < 30 -- ---- ORDER BY id; 10 - 20 - Introduction to SQL 36
  37. 37. DB2 9 Cookbook © VALUES Expression (1 of 5) Syntax , expression VALUES , , ( expression ) NULL Notes • Define one or more rows of temporary data Examples VALUES 6 <= 1 row, 1 column VALUES (6) <= 1 row, 1 column VALUES 6, 7, 8 <= 1 row, 3 columns VALUES (6), (7), (8) <= 3 rows, 1 column VALUES (6,66), (7,77), (8,NULL) <= 3 rows, 2 columns Introduction to SQL 37
  38. 38. DB2 9 Cookbook © VALUES Expression (2 of 5) Define a temporary table #1 WITH temp1 (col1, col2) AS ANSWER (VALUES ( 0, 'AA') ========= ,( 1, 'BB') COL1 COL2 ,( 2, NULL) ---- ---- ) 0 AA SELECT * 1 BB FROM temp1; 2 - Define a temporary table #2 WITH temp1 (col1, col2) AS ANSWER (VALUES (DECIMAL(0 ,3,1), 'AA') ========= ,(DECIMAL(1 ,3,1), 'BB') COL1 COL2 ,(DECIMAL(2 ,3,1), NULL) ---- ---- ) 0.0 AA SELECT * 1.0 BB FROM temp1; 2.0 - Introduction to SQL 38
  39. 39. DB2 9 Cookbook © VALUES Expression (3 of 5) Define a temporary table #3 WITH temp1 (col1, col2) AS ANSWER (VALUES ( 0, CAST('AA' AS CHAR(1))) ========= ,( 1, CAST('BB' AS CHAR(1))) COL1 COL2 ,( 2, CAST(NULL AS CHAR(1))) ---- ---- ) 0 a SELECT * 1 b FROM temp1; 2 - Define a temporary table #4 WITH temp1 (col1, col2) AS ANSWER (VALUES ( 0, CHAR('AA',1)) ========= ,( 1, CHAR('BB',1)) COL1 COL2 ,( 2, NULL) ---- ---- ) 0 a SELECT * 1 b FROM temp1; 2 - Introduction to SQL 39
  40. 40. DB2 9 Cookbook © VALUES Expression (4 of 5) Derive one temporary table from another WITH temp1 (col1, col2, col3) AS ANSWER (VALUES ( 0, 'AA', 0.00) ========== ,( 1, 'BB', 1.11) COL1B COLX ,( 2, 'CC', 2.22) ----- ---- ) 0 0.00 ,temp2 (col1b, colx) AS 1 2.11 (SELECT col1 2 4.22 ,col1 + col3 FROM temp1 ) SELECT * FROM temp2; Define a view using a VALUES clause CREATE VIEW silly (c1, c2, c3) AS VALUES (11, 'AAA', SMALLINT(22)) ,(12, 'BBB', SMALLINT(33)) ,(13, 'CCC', NULL); COMMIT; Introduction to SQL 40
  41. 41. DB2 9 Cookbook © VALUES Expression (5 of 5) Seed a recursive SQL statement WITH temp1 (col1) AS ANSWER (VALUES 0 ====== UNION ALL COL1 SELECT col1 + 1 ---- FROM temp1 0 WHERE col1 + 1 < 100 1 ) 2 SELECT * 3 FROM temp1; etc Define a (Stupid) Table with no Column Names SELECT * ANSWER FROM (VALUES (123,'ABC') ====== ,(234,'DEF') --- --- )AS ttt 234 DEF ORDER BY 1 DESC; 123 ABC Introduction to SQL 41
  42. 42. DB2 9 Cookbook © CASE Expression (1 of 6) Syntax WHEN search-condition THEN result NULL CASE expression WHEN expression THEN result NULL ELSE NULL END ELSE result Notes • Lets one have "if then else" logic in a SQL statement • First CASE that matches is the one used • If none matches, result is null (default) • Two syntax styles - see next page Introduction to SQL 42
  43. 43. DB2 9 Cookbook © CASE Expression (2 of 6) Use CASE (type 1) to expand a value SELECT Lastname ANSWER ,sex AS sx ==================== ,CASE sex LASTNAME SX SEXX WHEN 'F' THEN 'FEMALE' ---------- -- ------ WHEN 'M' THEN 'MALE' JEFFERSON M MALE ELSE NULL JOHNSON F FEMALE END AS sexx JONES M MALE FROM employee WHERE lastname LIKE 'J%' ORDER BY 1; Use CASE (type 2) to expand a value SELECT lastname ANSWER ,sex AS sx ==================== ,CASE LASTNAME SX SEXX WHEN sex = 'F' THEN 'FEMALE' ---------- -- ------ WHEN sex = 'M' THEN 'MALE' JEFFERSON M MALE ELSE NULL JOHNSON F FEMALE END AS sexx JONES M MALE FROM employee WHERE lastname LIKE 'J%' ORDER BY 1; Introduction to SQL 43
  44. 44. DB2 9 Cookbook © CASE Expression (3 of 6) Use CASE to display the higher of two values SELECT lastname ANSWER ,midinit AS mi =================== ,sex AS sx LASTNAME MI SX MX ,CASE ---------- -- -- -- WHEN midinit > sex JEFFERSON J M M THEN midinit JOHNSON P F P ELSE sex JONES T M T END AS mx FROM employee WHERE lastname LIKE 'J%' ORDER BY 1; Use CASE to get multiple counts in one pass SELECT COUNT(*) AS tot ANSWER ,SUM(CASE sex WHEN 'F' THEN 1 ELSE 0 END) AS #f ========= ,SUM(CASE sex WHEN 'M' THEN 1 ELSE 0 END) AS #m TOT #F #M FROM employee --- -- -- WHERE lastname LIKE 'J%'; 3 1 2 Introduction to SQL 44
  45. 45. DB2 9 Cookbook © CASE Expression (4 of 6) Use CASE in a predicate SELECT lastname ANSWER ,sex ============== FROM employee LASTNAME SEX WHERE lastname LIKE 'J%' ---------- --- AND CASE sex JEFFERSON M WHEN 'F' THEN '' JOHNSON F WHEN 'M' THEN '' JONES M ELSE NULL END IS NOT NULL ORDER BY 1; Use CASE inside a function SELECT lastname ANSWER ,LENGTH(RTRIM(lastname)) AS len ===================== ,SUBSTR(lastname,1, LASTNAME LEN LASTNM CASE ---------- --- ------ WHEN LENGTH(RTRIM(lastname)) JEFFERSON 9 JEFFER > 6 THEN 6 JOHNSON 7 JOHNSO ELSE LENGTH(RTRIM(lastname)) JONES 5 JONES END ) AS lastnm FROM employee WHERE lastname LIKE 'J%' ORDER BY 1; Introduction to SQL 45
  46. 46. DB2 9 Cookbook © CASE Expression (5 of 6) UPDATE statement with nested CASE expressions UPDATE staff SET comm = CASE dept WHEN 15 THEN comm * 1.1 WHEN 20 THEN comm * 1.2 WHEN 38 THEN CASE WHEN years < 5 THEN comm * 1.3 WHEN years >= 5 THEN comm * 1.4 ELSE NULL END ELSE comm END WHERE comm IS NOT NULL AND dept < 50; Use CASE to avoid divide by zero WITH temp1 (c1,c2) AS ANSWER (VALUES (88,9),(44,3),(22,0),(0,1)) ======== SELECT c1 C1 C2 C3 ,c2 -- -- -- ,CASE c2 88 9 9 WHEN 0 THEN NULL 44 3 14 ELSE c1/c2 22 0 - END AS c3 0 1 0 FROM temp1; Introduction to SQL 46
  47. 47. DB2 9 Cookbook © CASE Expression (6 of 6) Use CASE to derive a value (correct) SELECT lastname ANSWER ,sex ================= ,CASE LASTNAME SX SXX WHEN sex >= 'M' THEN 'MAL' ---------- -- --- WHEN sex >= 'F' THEN 'FEM' JEFFERSON M MAL END AS sxx JOHNSON F FEM FROM employee JONES M MAL WHERE lastname LIKE 'J%' ORDER BY 1; Use CASE to derive a value (incorrect) ELECT lastname ANSWER ,sex ================= ,CASE LASTNAME SX SXX WHEN sex >= 'F' THEN 'FEM' ---------- -- --- WHEN sex >= 'M' THEN 'MAL' JEFFERSON M FEM END AS sxx JOHNSON F FEM FROM employee JONES M FEM WHERE lastname LIKE 'J%' ORDER BY 1; Introduction to SQL 47
  48. 48. DB2 9 Cookbook © DML Statements DML Statements 48
  49. 49. DB2 9 Cookbook © INSERT (1 of 5) Syntax Diagram INSERT INTO table-name view-name , (full-select) ( column-name ) , INCLUDE ( column-name data-type ) , VALUES ( expression ) full-select WITH common-table-expression Notes • Used to insert one or more rows into a table • Can either insert values directly, or insert from SELECT result • See also the MERGE statement DML Statements 49
  50. 50. DB2 9 Cookbook © INSERT (2 of 5) Sample Table CREATE TABLE emp_act (empno CHARACTER (00006) NOT NULL ,projno CHARACTER (00006) NOT NULL ,actno SMALLINT NOT NULL ,emptime DECIMAL (05,02) ,emstdate DATE ,emendate DATE); Insert One Row INSERT INTO emp_act VALUES ('100000' ,'ABC' ,10 ,1.4 ,'2003-10-22', '2003-11-24'); Insert Multiple Rows INSERT INTO emp_act VALUES ('200000' ,'ABC' ,10 ,1.4 ,'2003-10-22', '2003-11-24') ,('200000' ,'DEF' ,10 ,1.4 ,'2003-10-22', '2003-11-24') ,('200000' ,'IJK' ,10 ,1.4 ,'2003-10-22', '2003-11-24'); Note • If multiple rows are inserted, and any one violates unique index - all are rejected DML Statements 50
  51. 51. DB2 9 Cookbook © INSERT (3 of 5) Sample Table CREATE TABLE emp_act (empno CHARACTER (00006) NOT NULL ,projno CHARACTER (00006) NOT NULL ,actno SMALLINT NOT NULL ,emptime DECIMAL (05,02) ,emstdate DATE ,emendate DATE); Using Null and Default values INSERT INTO emp_act VALUES ('400000' ,'ABC' ,10 ,NULL ,DEFAULT, CURRENT DATE) Explicitly Listing Columns INSERT INTO emp_act (projno, emendate, actno, empno) VALUES ('ABC' ,DATE(CURRENT TIMESTAMP) ,123 ,'500000'); Note • If not all columns are provided (in data), the names have be explicitly listed DML Statements 51
  52. 52. DB2 9 Cookbook © INSERT (4 of 5) Sample Table CREATE TABLE emp_act (empno CHARACTER (00006) NOT NULL ,projno CHARACTER (00006) NOT NULL ,actno SMALLINT NOT NULL ,emptime DECIMAL (05,02) ,emstdate DATE ,emendate DATE); Insert from Select INSERT INTO emp_act SELECT LTRIM(CHAR(id + 600000)) ,SUBSTR(UCASE(name),1,6) ,salary / 229 ,123 ,CURRENT DATE ,'2003-11-11' FROM staff WHERE id < 50; Note • All matching rows inserted in one unit of work DML Statements 52
  53. 53. DB2 9 Cookbook © INSERT (5 of 5) Sample Table (1 of 2) CREATE TABLE us_customer CREATE TABLE intl_customer (cust# INTEGER NOT NULL (cust# INTEGER NOT NULL ,cname CHAR(10) NOT NULL ,cname CHAR(10) NOT NULL ,country CHAR(03) NOT NULL ,country CHAR(03) NOT NULL ,CHECK (country = 'USA') ,CHECK (country <> 'USA') ,PRIMARY KEY (cust#)); ,PRIMARY KEY (cust#)); Insert into Multiple Tables INSERT INTO (SELECT * FROM us_customer UNION ALL SELECT * FROM intl_customer) VALUES (111,'Fred','USA') ,(222,'Dave','USA') ,(333,'Juan','MEX'); Notes • All tables referenced in UNION ALL must have CHECK constraints such that a new row will go to one table, or another, but not more than one, and not none DML Statements 53
  54. 54. DB2 9 Cookbook © UPDATE Update Columns - set values UPDATE emp_act SET emptime = NULL ,emendate = DEFAULT ,emstdate = CURRENT DATE + 2 DAYS ,actno = ACTNO / 2 ,projno = 'ABC' WHERE empno = '100000'; Update Columns - use Select UPDATE emp_act SET actno = (SELECT MAX(salary) FROM staff) WHERE empno = '200000'; UPDATE emp_act SET (actno ,emstdate ,projno) = (SELECT MAX(salary) ,CURRENT DATE + 2 DAYS ,MIN(CHAR(id)) FROM staff WHERE id <> 33) WHERE empno LIKE '600%'; DML Statements 54
  55. 55. DB2 9 Cookbook © DELETE Single-row Delete ELETE FROM emp_act WHERE empno = '000010' AND projno = 'MA2100' AND actno = 10; Mass Delete DELETE FROM emp_act; Correlated Delete DELETE FROM staff s1 WHERE id NOT IN (SELECT MAX(id) FROM staff s2 WHERE s1.dept = s2.dept); Warning • Delete with care DML Statements 55
  56. 56. DB2 9 Cookbook © Select DML Changes (1 of 4) Syntax Diagram SELECT column-list FROM OLD TABLE ( DML stmt ) NEW FINAL WHERE predicates ORDER BY sort-columns INPUT SEQUENCE Notes • Embed DML in a SELECT stmt to get results of change • Cannot join results, nor use in a nested table expression • Useful when the DML creates unknown values (e.g. current timestamp) Tables • OLD: Returns data values prior to stmt run (for UPDATE and DELETE) • NEW: Returns data values after stmt run (for UPDATE and INSERT), and before any AFTER triggers or R.I. rules are applied. • FINAL: Returns state final state of data values (for UPDATE and INSERT). If there are any AFTER triggers or R.I. rules that affect the data, an error is returned. DML Statements 56
  57. 57. DB2 9 Cookbook © Select DML Changes (2 of 4) SELECT From INSERT ANSWER ============== SELECT empno EMPNO PRJ ACT ,projno AS prj ------ --- --- ,actno AS act 200000 ABC 10 FROM FINAL TABLE 200000 DEF 10 (INSERT INTO emp_act VALUES ('200000','ABC',10 ,1,'2003-10-22','2003-11-24') ,('200000','DEF',10 ,1,'2003-10-22','2003-11-24')) ORDER BY 1,2,3; SELECT From INSERT That Creates Unknown Values SELECT empno ANSWER ,projno AS prj ================= ,actno AS act EMPNO PRJ ACT R# ,ROW_NUMBER() OVER() AS r# ------ --- -- -- FROM NEW TABLE 600010 1 59 1 (INSERT INTO emp_act (empno, actno, projno) 600020 563 59 2 SELECT LTRIM(CHAR(id + 600000)) 600030 193 59 3 ,SECOND(CURRENT TIME) ,CHAR(SMALLINT(RAND(1) * 1000)) FROM staff WHERE id < 40) ORDER BY INPUT SEQUENCE; DML Statements 57
  58. 58. DB2 9 Cookbook © Select DML Changes (3 of 4) SELECT From UPDATE SELECT projno AS prj ANSWER ,old_t AS old_t =============== ,emptime AS new_t PRJ OLD_T NEW_T FROM NEW TABLE --- ----- ----- (UPDATE emp_act ABC 2.00 0.02 INCLUDE (old_t DECIMAL(5,2)) DEF 2.00 11.27 SET emptime = emptime * RAND(1) * 10 ,old_t = emptime WHERE empno = '200000') ORDER BY 1; Notes • In the above UPDATE, both old and new values are obtained • Old value got by making a temp column, insert old value, then selecting • New value got by selecting from NEW table DML Statements 58
  59. 59. DB2 9 Cookbook © Select DML Changes (4 of 4) SELECT From DELETE SELECT empno ANSWER ,projno ==================== ,actno AS act EMPNO PROJNO ACT R# ,row# AS r# ------ ------ --- -- FROM OLD TABLE 000260 AD3113 70 2 (DELETE 000260 AD3113 80 4 FROM emp_act 000260 AD3113 180 6 INCLUDE (row# SMALLINT) SET row# = ROW_NUMBER() OVER() WHERE empno = '000260') WHERE row# = row# / 2 * 2 ORDER BY 1,2,3; Notes • The above query selects every second row that was deleted • The predicate in the query has no impact of the set of rows deleted DML Statements 59
  60. 60. DB2 9 Cookbook © MERGE (1 of 3) Syntax MERGE INTO table-name or view-name or (full-select) corr-name USING table-name or view-name or (full-select) corr-name ON search-conditions WHEN MATCHED THEN UPDATE SET... AND search-c DELETE SIGNAL... WHEN NOT MATCHED THEN INSERT... AND search-c SIGNAL... ELSE IGNORE Notes • Used to transfer rows from one table to another. • Update or delete (optional) if source row in target. • Insert (optional) if source row not in target DML Statements 60
  61. 61. DB2 9 Cookbook © MERGE (2 of 3) MERGE INTO old_staff oo OLD_STAFF NEW_STAFF USING new_staff nn +-----------------+ +----------+ ON oo.id = nn.id |ID|JOB |SALARY | |ID|SALARY | WHEN MATCHED THEN |--|-----|--------| |--|-------| UPDATE |20|Sales|18171.25| |30|1750.67| SET oo.salary = nn.salary |30|Mgr |17506.75| |40|1800.60| WHEN NOT MATCHED THEN |40|Sales|18006.00| |50|2065.98| INSERT +-----------------+ +----------+ VALUES (nn.id,'?',nn.salary); AFTER-MERGE ================= ID JOB SALARY -- ----- -------- 20 Sales 18171.25 30 Mgr 1750.67 40 Sales 1800.60 50 ? 2065.98 Notes • ON statement must identify unique row in target • If row matches - update • If no match - insert DML Statements 61
  62. 62. DB2 9 Cookbook © MERGE (3 of 3) MERGE INTO old_staff oo OLD_STAFF NEW_STAFF USING new_staff nn +-----------------+ +----------+ ON oo.id = nn.id |ID|JOB |SALARY | |ID|SALARY | WHEN MATCHED |--|-----|--------| |--|-------| AND oo.salary < 18000 THEN |20|Sales|18171.25| |30|1750.67| UPDATE |30|Mgr |17506.75| |40|1800.60| SET oo.salary = nn.salary |40|Sales|18006.00| |50|2065.98| WHEN MATCHED +-----------------+ +----------+ AND oo.salary > 18000 THEN DELETE AFTER-MERGE WHEN NOT MATCHED ================= AND nn.id > 10 THEN ID JOB SALARY INSERT -- ----- -------- VALUES (nn.id,'?',nn.salary) 20 Sales 18171.25 WHEN NOT MATCHED THEN 30 Mgr 1750.67 SIGNAL SQLSTATE '70001' 50 ? 2065.98 SET MESSAGE_TEXT = 'New ID <= 10'; Notes • If row matches & SALARY < 18K - update • If row matches & SALARY > 18K - delete • If no match and ID > 10 - insert • If no match then - error DML Statements 62
  63. 63. DB2 9 Cookbook © Compound SQL Compound SQL 63
  64. 64. DB2 9 Cookbook © Compound SQL - Introduction (1 of 3) Syntax Diagram BEGIN ATOMIC label: , DEFAULT NULL DECLARE var-name data type ; DEFAULT default value VALUE SQLSTATE DECLARE cond-name string constant SQL procedure statement ; END label: Notes • Used to group multiple independent SQL statements • Can be embedded in Triggers, Functions, Methods, and Dynamic SQL • Need to set statement delimiter to something other than semi-colon Compound SQL 64
  65. 65. DB2 9 Cookbook © Compound SQL - Introduction (2 of 3) Sample Code BEGIN ATOMIC DECLARE cntr SMALLINT DEFAULT 1; FOR V1 AS SELECT id as idval FROM staff WHERE id < 80 ORDER BY id DO UPDATE staff SET comm = cntr WHERE id = idval; SET cntr = cntr + 1; END FOR; END Notes (on above) • Declares variable - sets to 1 • Opens a cursor • For every row fetched does an update of current row • Net result is to set the COMM field equal to the fetch number Compound SQL 65
  66. 66. DB2 9 Cookbook © Compound SQL - Introduction (3 of 3) Control Statements Supported • FOR statement • GET DIAGNOSTICS statement • IF statement • ITERATE statement • LEAVE statement • SIGNAL statement • WHILE statement SQL Statements Supported • full-select • UPDATE • DELETE • INSERT • SET variable statement Compound SQL 66
  67. 67. DB2 9 Cookbook © DECLARE Variables Example BEGIN ATOMIC DECLARE aaa, bbb, ccc SMALLINT DEFAULT 1; DECLARE ddd CHAR(10) DEFAULT NULL; DECLARE eee INTEGER; SET eee = aaa + 1; UPDATE staff SET comm = aaa ,salary = bbb ,years = eee WHERE id = 10; END Notes • Used to define control variables that are used in statement • Default value can be provided (optional) • Standard DB2 data types supported Compound SQL 67
  68. 68. DB2 9 Cookbook © FOR Statement Syntax FOR for-loop-name AS label: cursor-name DEFAULT select-stmt DO SQL-procedure-stmt ; END FOR label: Example BEGIN ATOMIC FOR V1 AS SELECT dept AS dname ,max(id) AS max_id FROM staff GROUP BY dept HAVING COUNT(*) > 1 ORDER BY dept DO Notes UPDATE staff SET id = id * -1 • Executes a group of state- WHERE id = max_id; ments for each row fetched UPDATE staff from a query set dept = dept / 10 • In this example, does two WHERE dept = dname separate updates for each AND dept < 30; row fetched END FOR; END Compound SQL 68
  69. 69. DB2 9 Cookbook © GET DIAGNOSTICS Statement Syntax GET DIAGNOSTICS SQL-var-name = ROW_COUNT RETURN_COUNT Example BEGIN ATOMIC DECLARE numrows INT DEFAULT 0; UPDATE staff SET salary = 12345 WHERE id < 100; GET DIAGNOSTICS numrows = ROW_COUNT; UPDATE staff SET salary = numrows WHERE id = 10; END Notes • Returns information about most recently run SQL statement • In above example, used to get number of rows updated in UPDATE Compound SQL 69
  70. 70. DB2 9 Cookbook © IF Statement Syntax IF seach condition THEN SQL procedure statement ; ELSEIF seach condition THEN SQL procedure statement ; END IF ELSE SQL procedure statement ; Example BEGIN ATOMIC DECLARE cur INT; SET cur = MICROSECOND(CURRENT TIMESTAMP); IF cur > 600000 THEN UPDATE staff SET name = CHAR(cur) WHERE id = 10; Notes ELSEIF cur > 300000 THEN UPDATE staff • Used to do basic IF-THEN- SET name = CHAR(cur) WHERE id = 20; ELSE logic ELSE UPDATE staff • In this example, does one of SET name = CHAR(cur) three updates, depending on WHERE id = 30; current timestamp END IF; END Compound SQL 70
  71. 71. DB2 9 Cookbook © ITERATE Statement Syntax ITERATE label Example BEGIN ATOMIC DECLARE cntr INT DEFAULT 0; whileloop: WHILE cntr < 60 DO SET cntr = cntr + 10; UPDATE staff SET salary = cntr WHERE id = cntr; ITERATE whileloop; UPDATE staff SET comm = cntr + 1 WHERE id = cntr; END WHILE; END Notes • Causes the program to return to the beginning of the labeled loop • In the above example, the second update never gets performed Compound SQL 71
  72. 72. DB2 9 Cookbook © LEAVE Statement Syntax LEAVE label Example BEGIN ATOMIC DECLARE cntr INT DEFAULT 1; whileloop: WHILE 1 <> 2 DO SET cntr = cntr + 1; IF RAND() > 0.99 THEN LEAVE whileloop; END IF; END WHILE; UPDATE staff SET salary = cntr WHERE id = 10; END Notes • Exits the labeled loop • In above example, does random number of iterations, then leaves loop Compound SQL 72
  73. 73. DB2 9 Cookbook © SIGNAL Statement Syntax VALUE SIGNAL SQLSTATE sqlstate string condition-name SET MESSAGE_TEXT = variable-name diagnostic-string Example BEGIN ATOMIC DECLARE cntr INT DEFAULT 1; DECLARE emsg CHAR(20); whileloop: WHILE RAND() < .99 DO SET cntr = cntr + 1; END WHILE; SET emsg = '#loops: ' || CHAR(cntr); SIGNAL SQLSTATE '75001' SET MESSAGE_TEXT = emsg; END Notes • Issues error or warning message Compound SQL 73
  74. 74. DB2 9 Cookbook © WHILE Statement Syntax WHILE seach-condition DO SQL-procedure-stmt ; label: END WHILE label: Example BEGIN ATOMIC DECLARE c1, C2 INT DEFAULT 1; WHILE c1 < 10 DO WHILE c2 < 20 DO SET c2 = c2 + 1; END WHILE; SET c1 = c1 + 1; END WHILE; UPDATE staff SET salary = c1 ,comm = c2 WHERE id = 10; END Notes • Repeats one or more statements while condition is true Compound SQL 74
  75. 75. DB2 9 Cookbook © Column Functions Column Functions 75
  76. 76. DB2 9 Cookbook © AVG Function (1 of 3) Syntax ALL AVG ( expression ) DISTINCT Notes • Gets the average (mean) of a set of non-null rows • If now rows match, null returned • Beware of loss of precision (see A4 vs. A5 below) Sample SQL SELECT AVG(dept) AS a1 ANSWER ,AVG(ALL dept) AS a2 ============== ,AVG(DISTINCT dept) AS a3 A1 A2 A3 A4 A5 ,AVG(dept/10) AS a4 -- -- -- -- -- ,AVG(dept)/10 AS a5 41 41 40 3 4 FROM staff HAVING AVG(dept) > 40; Column Functions 76
  77. 77. DB2 9 Cookbook © AVG Function (2 of 3) Convert zero to null before doing AVG SELECT AVG(salary) AS salary ANSWER ,AVG(comm) AS comm1 =================== ,AVG(CASE comm SALARY COMM1 COMM2 WHEN 0 THEN NULL ------- ----- ----- ELSE comm 16675.6 351.9 513.3 END) AS comm2 FROM staff; Convert null output (from AVG) to zero SELECT COUNT(*) AS c1 ANSWER ,AVG(salary) AS a1 =========== ,COALESCE(AVG(salary),0) AS a2 C1 A1 A2 A3 ,CASE -- -- -- -- WHEN AVG(salary) IS NULL THEN 0 0 - 0 0 ELSE AVG(salary) END AS a3 FROM staff WHERE id < 10; Column Functions 77
  78. 78. DB2 9 Cookbook © AVG Function (3 of 3) AVG of Date Column SELECT AVG(DAYS(birthdate)) ANSWER ,DATE(AVG(DAYS(birthdate))) ================= FROM employee; 1 2 ------ ---------- 709113 06/27/1942 • Warning - can get silly answer Select Average of Average SELECT AVG(avg_sal) AS avg_avg ANSWER FROM (SELECT dept ================ ,AVG(salary) AS avg_sal <Overflow error> FROM staff GROUP BY dept )AS xxx; Column Functions 78
  79. 79. DB2 9 Cookbook © CORRELATION Function Syntax CORRELATION ( expression , expression ) CORR Sample SQL WITH temp1(col1, col2, col3, col4) AS ANSWER (VALUES (0 =========================== ,0 COR11 COR12 COR23 COR34 ,0 ------ ------ ------ ------ ,RAND(1)) 1.000 -1.000 -0.017 -0.005 UNION ALL SELECT col1 + 1 ,col2 - 1 ,RAND() ,RAND() FROM temp1 WHERE col1 <= 1000 ) SELECT DEC(CORRELATION(col1,col1),5,3) AS cor11 ,DEC(CORRELATION(col1,col2),5,3) AS cor12 ,DEC(CORRELATION(col2,col3),5,3) AS cor23 ,DEC(CORRELATION(col3,col4),5,3) AS cor34 FROM temp1; Column Functions 79
  80. 80. DB2 9 Cookbook © COUNT Function (1 of 2) Syntax ALL COUNT ( expression ) DISTINCT * Notes • COUNT(*) counts matching rows • COUNT(expression) counts rows with a non-null expression values • COUNT(ALL expression) is the same as COUNT(expression) statement • COUNT(DISTINCT expression) counts distinct non-null expression values Sample SQL SELECT COUNT(*) AS c1 ANSWER ,COUNT(INT(comm/10)) AS c2 ================= ,COUNT(ALL INT(comm/10)) AS c3 C1 C2 C3 C4 C5 C6 ,COUNT(DISTINCT INT(comm/10)) AS c4 -- -- -- -- -- -- ,COUNT(DISTINCT INT(comm)) AS c5 35 24 24 19 24 2 ,COUNT(DISTINCT INT(comm))/10 AS c6 FROM staff; Column Functions 80
  81. 81. DB2 9 Cookbook © COUNT Function (2 of 2) COUNT function with and without GROUP BY SELECT 'NO GP-BY' AS c1 ANSWER ,COUNT(*) AS c2 ============ FROM staff C1 C2 WHERE id = -1 -------- -- UNION NO GP-BY 0 SELECT 'GROUP-BY' AS c1 ,COUNT(*) AS c2 FROM staff WHERE id = -1 GROUP BY dept; Column Functions 81
  82. 82. DB2 9 Cookbook © COUNT_BIG Function Syntax ALL COUNT_BIG ( expression ) DISTINCT * Notes • Same COUNT function, but returns BIGINT value Sample SQL SELECT COUNT_BIG(*) AS c1 ANSWER ,COUNT_BIG(dept) AS c2 =================== ,COUNT_BIG(DISTINCT dept) AS C3 C1 C2 C3 C4 C5 ,COUNT_BIG(DISTINCT dept/10) AS C4 --- --- --- --- --- ,COUNT_BIG(DISTINCT dept)/10 AS C5 35. 35. 8. 7. 0. FROM staff; Column Functions 82
  83. 83. DB2 9 Cookbook © COVARIANCE Function Syntax COVARIANCE ( expression , expression ) COVAR Sample SQL WITH temp1(c1, c2, c3, c4) AS ANSWER (VALUES (0 =============================== ,0 COV11 COV12 COV23 COV34 ,0 ------- ------- ------- ------- ,RAND(1)) 83666. -83666. -1.4689 -0.0004 UNION ALL SELECT c1 + 1 ,c2 - 1 ,RAND() ,RAND() FROM temp1 WHERE c1 <= 1000 ) SELECT DEC(COVARIANCE(c1,c1),6,0) AS cov11 ,DEC(COVARIANCE(c1,c2),6,0) AS cov12 ,DEC(COVARIANCE(c2,C3),6,4) AS cov23 ,DEC(COVARIANCE(C3,C4),6,4) AS cov34 FROM temp1; Column Functions 83
  84. 84. DB2 9 Cookbook © GROUPING Function GROUPING ( expression ) Notes • Used in CUBE, ROLLUP, and GROUPING SETS statements • Identifies what rows came from which grouping set Sample SQL SELECT dept ANSWER ,AVG(salary) AS salary ================ ,GROUPING(dept) AS df DEPT SALARY DF FROM staff ---- -------- -- GROUP BY ROLLUP(dept) 10 20865.86 0 ORDER BY dept; 15 15482.33 0 20 16071.52 0 38 15457.11 0 42 14592.26 0 51 17218.16 0 66 17215.24 0 84 16536.75 0 - 16675.64 1 Column Functions 84
  85. 85. DB2 9 Cookbook © MAX Function (1 of 2) Syntax ALL MAX ( expression ) DISTINCT Notes • Gets max value from a set of rows • The DISTINCT option has no affect • If no rows match, null returned Sample SQL SELECT MAX(dept) ANSWER ,MAX(ALL dept) =============== ,MAX(DISTINCT dept) 1 2 3 4 ,MAX(DISTINCT dept/10) --- --- --- --- FROM staff; 84 84 84 8 Column Functions 85
  86. 86. DB2 9 Cookbook © MAX Function (2 of 2) MAX Function with Dates SELECT MAX(hiredate) ANSWER ,CHAR(MAX(hiredate),USA) ================================ ,MAX(CHAR(hiredate,USA)) 1 2 3 FROM employee; ---------- ---------- ---------- 09/30/1980 09/30/1980 12/15/1976 MAX Function with Numbers, 1 of 2 SELECT MAX(id) AS id ANSWER ,MAX(CHAR(id)) AS chr =================== ,MAX(DIGITS(id)) AS dig ID CHR DIG FROM staff; ------ ------ ----- 350 90 00350 MAX Function with Numbers, 2 of 2 SELECT MAX(id - 250) AS id ANSWER ,MAX(CHAR(id - 250)) AS chr ===================== ,MAX(DIGITS(id - 250)) AS dig ID CHR DIG FROM staff; ----- ---- ---------- 100 90 0000000240 Column Functions 86
  87. 87. DB2 9 Cookbook © MIN Function Syntax ALL MIN ( expression ) DISTINCT Sample SQL SELECT MIN(dept) ANSWER ,MIN(ALL dept) =============== ,MIN(DISTINCT dept) 1 2 3 4 ,MIN(DISTINCT dept/10) --- --- --- --- FROM staff; 10 10 10 1 Column Functions 87
  88. 88. DB2 9 Cookbook © REGRESSION Functions REGR_AVGX ( expression , expression ) REGR_AVGY REGR_COUNT REGR_INTERCEPT REGR_ICPT REGR_R2 REGR_SLOPE REGR_SXX REGR_SXY REGR_SYY Sample SQL SELECT REGR_SLOPE(bonus,salary) AS r_slope ,REGR_INTERCEPT(bonus,salary) AS r_icpt ,REGR_COUNT(bonus,salary) AS r_count ,REGR_AVGX(bonus,salary) AS r_avgx ,REGR_AVGY(bonus,salary) AS r_avgy ,REGR_SXX(bonus,salary) AS r_sxx ,REGR_SXY(bonus,salary) AS r_sxy ,REGR_SYY(bonus,salary) AS r_syy FROM employee WHERE workdept = 'A00'; Column Functions 88
  89. 89. DB2 9 Cookbook © STDDEV Function Syntax ALL STDDEV ( expression ) DISTINCT Sample SQL ANSWER =============================== A1 S1 S2 S3 S4 -- ------------- ---- ---- ---- SELECT AVG(dept) AS a1 41 +2.3522355E+1 23.5 23.5 24.1 ,STDDEV(dept) AS s1 ,DEC(STDDEV(dept),3,1) AS s2 ,DEC(STDDEV(ALL dept),3,1) AS s3 ,DEC(STDDEV(DISTINCT dept),3,1) AS s4 FROM staff; Column Functions 89
  90. 90. DB2 9 Cookbook © SUM Function Syntax ALL SUM ( expression ) DISTINCT Notes • Gets the SUM of a set of numeric values (null if no rows match) • If DISTINCT used, duplicate values are ignored • Nulls values always ignored • Beware loss of precision (see S4 vs. S5 below) Sample SQL SELECT SUM(dept) AS s1 ANSWER ,SUM(ALL dept) AS s2 ======================== ,SUM(DISTINCT dept) AS s3 S1 S2 S3 S4 S5 ,SUM(dept/10) AS s4 ---- ---- ---- ---- ---- ,SUM(dept)/10 AS s5 1459 1459 326 134 145 FROM staff; Column Functions 90
  91. 91. DB2 9 Cookbook © VARIANCE Function Syntax ALL VARIANCE ( expression ) DISTINCT VAR Sample SQL ANSWER ============================== A1 V1 V2 V3 V4 -- --------------- --- --- --- SELECT AVG(dept) AS a1 41 +5.533012244E+2 553 553 582 ,VARIANCE(dept) AS s1 ,DEC(VARIANCE(dept),4,1) AS s2 ,DEC(VARIANCE(ALL dept),4,1) AS s3 ,DEC(VARIANCE(DISTINCT dept),4,1) AS s4 FROM staff; Column Functions 91
  92. 92. DB2 9 Cookbook © OLAP Functions OLAP Functions 92
  93. 93. DB2 9 Cookbook © OLAP Functions • RANK() Returns number of preceding rows + 1 (for given value) If >1 row has same value - all get same rank - next row counts all prior rows - can have gaps in sequence • DENSE_RANK() Returns number of distinct preceding values + 1 (for value) If >1 row has same value - all get same rank - next row counts prior values - no gaps in sequence • ROW_NUMBER() Returns row number Use ORDER BY to get row number within field(s) • Col. function OVER() Uses standard DB2 column functions Gets cumulative totals, and/or running averages Example SELECT s1.job, s1.id, s1.salary ,SUM(salary) OVER(ORDER BY job, id) AS sumsal ,ROW_NUMBER() OVER(ORDER BY job, id) AS r FROM staff s1 ANSWER WHERE s1.name LIKE '%s%' ============================ AND s1.id < 90 JOB ID SALARY SUMSAL R ORDER BY s1.job ----- -- -------- -------- - ,s1.id; Clerk 80 13504.60 13504.60 1 Mgr 10 18357.50 31862.10 2 Mgr 50 20659.80 52521.90 3 OLAP Functions 93
  94. 94. DB2 9 Cookbook © Ranking Functions Syntax RANK() OVER( DENSE_RANK() , PARTITION BY partitioning expression , asc option ORDER BY sort-key expression ) desc option asc option NULLS LAST ASC NULLS FIRST desc option NULLS FIRST DESC NULLS LAST Note • "OVER( ... ORDER BY field(s) )" is mandatory OLAP Functions 94
  95. 95. DB2 9 Cookbook © Ranking Functions Example SELECT id ,years ,salary ,RANK() OVER(ORDER BY years) AS rank# ,DENSE_RANK() OVER(ORDER BY years) AS dense# ,ROW_NUMBER() OVER(ORDER BY years) AS row# FROM staff WHERE id < 100 AND years IS NOT NULL ANSWER ORDER BY years; =================================== ID YEARS SALARY RANK# DENSE# ROW# -- ----- -------- ----- ------ ---- 30 5 17506.75 1 1 1 40 6 18006.00 2 2 2 90 6 18001.75 2 2 3 10 7 18357.50 4 3 4 70 7 16502.83 4 3 5 20 8 18171.25 6 4 6 50 10 20659.80 7 5 7 Notes • ORDER BY is mandatory • ORDER BY indicates ranking sequence • ORDER BY in function has no relationship to ORDER BY in query OLAP Functions 95
  96. 96. DB2 9 Cookbook © ORDER BY Usage SELECT job ,years ,id ,name ,SMALLINT(RANK() OVER(ORDER BY job ASC)) AS asc1 ,SMALLINT(RANK() OVER(ORDER BY job ASC ,years ASC)) AS asc2 ,SMALLINT(RANK() OVER(ORDER BY job ASC ,years ASC ,id ASC)) AS asc3 ,SMALLINT(RANK() OVER(ORDER BY job DESC)) AS dsc1 ,SMALLINT(RANK() OVER(ORDER BY job DESC ,years DESC)) AS dsc2 ,SMALLINT(RANK() OVER(ORDER BY job DESC ,years DESC ,id DESC)) AS dsc3 ,SMALLINT(RANK() OVER(ORDER BY job ASC ,years DESC ,id ASC)) AS mix1 ,SMALLINT(RANK() OVER(ORDER BY job DESC ,years ASC ,id DESC)) AS mix2 FROM staff WHERE id < 150 AND years IN (6,7) AND job > 'L' ORDER BY job ANSWER ,years =========================================================== ,id; JOB Y ID NAME ASC1 ASC2 ASC3 DSC1 DSC2 DSC3 MIX1 MIX2 ----- - --- ------- ---- ---- ---- ---- ---- ---- ---- ---- Mgr 6 140 Fraye 1 1 1 4 6 6 3 4 Mgr 7 10 Sanders 1 2 2 4 4 5 1 6 Mgr 7 100 Plotz 1 2 3 4 4 4 2 5 Sales 6 40 O'Brien 4 4 4 1 2 3 5 2 Sales 6 90 Koonitz 4 4 5 1 2 2 6 1 Sales 7 70 Rothman 4 6 6 1 1 1 4 3 OLAP Functions 96

×