Tài liệu hạn chế xem trước, để xem đầy đủ mời bạn chọn Tải xuống
1
/ 42 trang
THÔNG TIN TÀI LIỆU
Thông tin cơ bản
Định dạng
Số trang
42
Dung lượng
624,05 KB
Nội dung
Which gives: EMPNO NAME ADDRESS(STREET, CITY, STATE, ZIP) 101 Adam ADDRESS_OBJ('1 A St.', 'Mobile', 'AL', '36608') 102 Baker ADDRESS_OBJ('2 B St.', 'Pensacola', 'FL', '32504') 103 Charles ADDRESS_OBJ('3 C St.', 'Bradenton', 'FL', '34209') Addressing specific columns works as well. Specific col- umns including the composite are addressed by their name in the result set: SELECT empno, name, address you can use discrete attribute names FROM emp Gives: EMPNO NAME ADDRESS(STREET, CITY, STATE, IP) 101 Adam ADDRESS_OBJ('1 A St.', 'Mobile', 'AL', '36608') 102 Baker ADDRESS_OBJ('2 B St.', 'Pensacola', 'FL', '32504') 103 Charles ADDRESS_OBJ('3 C St.', 'Bradenton', 'FL', '34209') 276 Collection and OO SQL in Oracle COLUMN Formatting in SELECTCOLUMN Formatting in SELECT Since the above output looks sloppy, some column for - matting is in order: SQL> COLUMN name FORMAT a9 SQL> COLUMN empno FORMAT 999999 SQL> COLUMN address FORMAT a50 SQL> / Now the above query would give: EMPNO NAME ADDRESS(STREET, CITY, STATE, ZIP) 101 Adam ADDRESS_OBJ('1 A St.', 'Mobile', 'AL', '36608') 102 Baker ADDRESS_OBJ('2 B St.', 'Pensacola', 'FL', '32504') 103 Charles ADDRESS_OBJ('3 C St.', 'Bradenton', 'FL', '34209') Note that here we formatted the entire address field and not the individual attributes of the column objects. SELECTing Only One Column inSELECTing Only One Column in the Compositethe Composite Fields within the column object may be addressed indi - vidually. A query that recalls names and cities in our example might look like this: SELECT name, e.address.city FROM emp e Giving: NAME ADDRESS.CITY Adam Mobile Baker Pensacola Charles Bradenton 277 Chapter | 8 You must use a table alias and the qualifier “ADDRESS” with the alias. If the alias is not used, the query will fail with a syntax error. SELECT with a WHERE ClauseSELECT with a WHERE Clause In a WHERE clause, alias and qualifier are also used: SELECT name, e.address.city FROM emp e WHERE e.address.state = 'FL' Gives: NAME ADDRESS.CITY Baker Pensacola Charles Bradenton Using UPDATE with TYPEedUsing UPDATE with TYPEed Columns To use UPDATE, the alias must also be used: UPDATE emp SET address.zip = '34210' WHERE address.city like 'Brad%' Gives: UPDATE emp set address.zip = '34210' WHERE address.city like 'Brad%' * ERROR at line 1: ORA-00904: invalid column name 278 Collection and OO SQL in Oracle Now type, UPDATE emp e SET e.address.zip = '34210' WHERE e.address.city LIKE 'Brad%' And, SELECT * FROM emp Gives: EMPNO NAME ADDRESS(STREET, CITY, STATE, ZIP) 101 Adam ADDRESS_OBJ('1 A St.', 'Mobile', 'AL', '36608') 102 Baker ADDRESS_OBJ('2 B St.', 'Pensacola', 'FL', '32504') 103 Charles ADDRESS_OBJ('3 C St.', 'Bradenton', 'FL', '34210') Create Row Objects — REF TYPECreate Row Objects — REF TYPE What are “row objects”? They are tables containing rows of objects of a defined class that will be refer- enced using addresses to point to another table. Why would you want to use “row objects”? The rea - son is that a table containing row objects is easier to maintain than objects that are embedded into another table. We can create a table of rows of a defined type and then reference the rows in this object table using the REF predicate. The following example illustrates this. Create a table that contains only the address objects: CREATE TABLE address_table OF ADDRESS_OBJ 279 Chapter | 8 Note that the syntax of this CREATE TABLE is dif - ferent from an ordinary CREATE TABLE command in that the keyword OF plus the object type is used. So far, the newly created table of column objects is empty: SELECT * FROM address_table Gives: no rows selected Now: DESC address_table Gives: Name Null? Type STREET VARCHAR2(20) CITY VARCHAR2(20) STATE CHAR(2) ZIP CHAR(5) The fact that Address_table contains an object type is hidden; the table and its structure look like an ordinary table when SELECTing and DESCribing. 280 Collection and OO SQL in Oracle Loading the “row object” TableLoading the “row object” Table How do we load the Address_table with row objects? One way is to use the existing ADDRESS_OBJ values in some other table (e.g., Emp) like this: INSERT INTO Address_table SELECT e.address FROM emp e Actually, the table alias is not necessary in this com - mand, but to be consistent, it is better to use the table alias when it seems that it is required in some state - ments and not required in others. Now: SELECT * FROM address_table Gives: STREET CITY ST ZIP 1 A St. Mobile AL 36608 2 B St. Pensacola FL 32504 3 C St. Bradenton FL 34210 And Address_table (although it was created using a defined type) functions just like an ordinary table. For example: SELECT city FROM address_table 281 Chapter | 8 Gives: CITY Mobile Pensacola Bradenton A second way to add data to Address_table is to insert just as one would ordinarily do with a common SQL table: INSERT INTO address_table VALUES ('4 D St.', 'Gulf Breeze','FL','32563') Thus: SELECT * FROM address_table Would give: STREET CITY ST ZIP 1 A St. Mobile AL 33608 2 B St. Pensacola FL 32504 3 C St. Bradenton FL 34209 4 D St. Gulf Breeze FL 32563 282 Collection and OO SQL in Oracle UPDATE Data in a Table of RowUPDATE Data in a Table of Row Objects Updating data in the Address_table table of row objects is also straightforward: UPDATE address_table SET zip = 32514 WHERE zip = 32504 UPDATE address_table SET street = '11 A Dr' WHERE city LIKE 'Mob%' Now: SELECT * FROM address_table Would give: STREET CITY ST ZIP 11 A Dr Mobile AL 33608 2 B St. Pensacola FL 32514 3 C St. Bradenton FL 34209 4 D St. Gulf Breeze FL 32563 In these examples note that no special syntax is required for inserts or updates. 283 Chapter | 8 CREATE a Table that ReferencesCREATE a Table that References Our Row ObjectsOur Row Objects Now, suppose we create a table that references our table of row objects. The syntax is a little different from other ordinary CREATE TABLE commands: CREATE TABLE client (name VARCHAR2(20), address REF address_obj scope is address_table) Now, if you type: DESC client You get: Name Null? Type NAME VARCHAR2(20) ADDRESS REF OF ADDRESS_OBJ In the CREATE TABLE command, we defined the column address as referencing address_obj, which is contained in an object table, Address_table. INSERT Values into a Table thatINSERT Values into a Table that Contains Row Objects (TCRO)Contains Row Objects (TCRO) How do we get values into this table that contains row objects? One way to begin is to insert into the client table and null the address_obj: INSERT INTO client VALUES ('Jones',null) Now, SELECT * FROM client 284 Collection and OO SQL in Oracle Will give: NAME ADDRESS Jones UPDATE a Table that ContainsUPDATE a Table that Contains Row Objects (TCRO)Row Objects (TCRO) Then, having created a row with nulls for address, you can update the client table by referencing the Address_table of row objects using a REF function like this: UPDATE client SET address = (SELECT REF(aa) FROM address_table aa WHERE aa.city LIKE 'Mob%') WHERE name = 'Jones' In this query, we find an appropriate row in the Address_table by constraining the subquery to some row (here we used aa.city LIKE 'Mob%'). Then, we constrained the UPDATE to the Client table by using a filter (WHERE name = 'Jones') in the outer query. The inner query must return only one row/value. If the subquery were written so that more than one row were returned, an error would result: UPDATE client set address = (SELECT REF(aa) FROM address_table aa WHERE aa.zip like '3%') WHERE name = 'Jones' SQL> / 285 Chapter | 8 [...]... 00002202 089 4 986 5D61CEA4 586 86C25DFE27E28A2B1F4DF5 480 22F434BAE 584 6A01A4C74BB Smith 0000220208C3F 689 D219D24EA2A39D418A593968B71F4DF5 480 22F434BAE 584 6A01A4C74BB Kelly 00002202 080 B1E9F84B6EA44C 981 573524372C49991F4DF5 480 22F434BAE 584 6A01A4C74BB Walsh 00002202 088 2FD946C58C940F2B7ECD94C 688 FD04C1F4DF5 480 22F434BAE 584 6A01A4C74BB Although the entry in Address_table was deleted, the reference to the deleted row still exists in the Client table But looking at the dereferenced address... VARRAY in It — INSERT VALUEs with Constants A VARRAY is actually more than just a defined type Oracle s VARRAYs behave like classes in object-oriented programming Classes are instantiated into objects using constructors In Oracle s VARRAYs, the constructor defaults to being named the name of the declared type and may be used in an INSERT statement like this: INSERT INTO '222-2222', INSERT INTO '333-3333',... first tell Oracle which object you are 294 Chapter | 8 referencing To show how this comes together in a table containing objects, we first created a table (above) that uses our defined class, aobj We may then insert some values into our table like this (note the use of the constructor aobj): INSERT INTO aobjtable VALUES (aobj('FL',25)) INSERT INTO aobjtable VALUES (aobj('AL',35)) INSERT INTO aobjtable... FROM club c SQL> / Gives: SELECT name, c.members(3) FROM club c * ERROR at line 1: ORA-00904: "C"."MEMBERS": invalid identifier 302 Chapter | 8 So, how do we get at individual members of the VARRAY members? You can access VARRAY elements in several ways: by using the TABLE function, by using a VARRAY self-join, by using the THE function, or by using PL /SQL We will explain each of these ways in the next... ZIP) Jones ADDRESS_OBJ('1 A St.', 'Mobile', 'AL', '366 08' ) One-step INSERTs into a TCRO There is another way to insert data into the table We can use a reference to Address_table in the insert without going through the INSERT-null-UPDATE sequence we introduced in the last section: INSERT INTO client SELECT 'Walsh', REF(aa) FROM address_table aa WHERE zip = '32563' Now, SELECT... ZIP 336 08 32514 34209 32563 Now delete a row from Address_table: DELETE FROM address_table WHERE zip = '32563' 289 Collection and OO SQL in Oracle And now, SELECT from the Client table that contains a reference to the Address_table: SELECT * FROM client Gives: NAME -ADDRESS Jones 00002202 089 4 986 5D61CEA4 586 86C25DFE27E28A2B1F4DF5 480 22F434BAE 584 6A01A4C74BB... reverse-casting the collection of names (n) from the table Newnames using MULTISET, and then we’re CASTing these names into our Club table as the expected type 310 Chapter | 8 Also, we can insert values into our Club table by casting a MULTISET version of Newnames directly: INSERT INTO club VALUES('MD',null, null,null, CAST(MULTISET(SELECT * FROM newnames) as mem_type)) Using PL /SQL to Create Functions. .. to indirectly access data in the VARRAY by using an IN predicate: SELECT name "Clubname" FROM club WHERE 'Gen' IN (SELECT * FROM TABLE(club.members)) This gives: Clubname -FL To try to help this query by using a table alias inconsistently will cause an error, as shown by: SELECT c.name "Clubname" FROM club c WHERE 'Gen' IN (SELECT * FROM TABLE(club.members)) SQL> / 303 Collection and OO SQL in Oracle. .. elements of the array An example could look like this: SQL> CREATE OR REPLACE TYPE mem_type IS VARRAY(10) of VARCHAR2(15); 2 / Giving: Type created (Note the semicolon and slash are used in the SQL* Plus syntax.) In ordinary programming we have the ability to define types that are later used in the declaration of variables A data type defines the kinds of operations and the range of values that declared... on For example, if we defined a variable to be of type NUMBER(3,0), we expect to be 299 Collection and OO SQL in Oracle able to perform the operations of addition, multiplication, etc., and we would define our range of variables to be –999 to 999 In the “mem_type” definition, we are defining our type to be a VARRAY with 10 elements, where each element is a varying character string of up to 15 characters . Jones 00002202 089 4 986 5D61CEA4 586 86C25DFE27E28A2B1F4DF5 480 22F434BAE 584 6A01A4C74BB Smith 0000220208C3F 689 D219D24EA2A39D418A593968B71F4DF5 480 22F434BAE 584 6A01A4C74BB Kelly 00002202 080 B1E9F84B6EA44C 981 573524372C49991F4DF5 480 22F434BAE 584 6A01A4C74BB Walsh 00002202 088 2FD946C58C940F2B7ECD94C 688 FD04C1F4DF5 480 22F434BAE 584 6A01A4C74BB Although. '34209') 276 Collection and OO SQL in Oracle COLUMN Formatting in SELECTCOLUMN Formatting in SELECT Since the above output looks sloppy, some column for - matting is in order: SQL& gt; COLUMN name FORMAT a9 SQL& gt;. '366 08& apos;) One-step INSERTs into a TCROOne-step INSERTs into a TCRO There is another way to insert data into the table. We can use a reference to Address_table in the insert with- out going