1 © 2005 Julian Dyke Reducing Redo Julian Dyke Independent Consultant Web Version juliandyke.com
© 2005 Julian Dyke juliandyke.com 2 Agenda Introduction Tests Indexes Number of columns processed SELECT FOR UPDATE Number of rows processed COMMIT Batch size Global temporary tables External tables Conclusion
© 2005 Julian Dyke juliandyke.com 3 Redo Records Redo Block Header 16 bytes Redo Block 512 or 1024 bytes Redo Block Body 496 bytes Redo Record 1 Redo Record 2 Wastage Redo Record 3 Wastage Header Body Header Spare Header Body Spare STOP
© 2005 Julian Dyke juliandyke.com 4 Change Vectors Redo Record Header Body Header Body Header Body Header Body Change Vectors Change Vector 3 Change Vector 1 Change Vector 2 STOP
© 2005 Julian Dyke juliandyke.com 5 Header Change Vector Header Body STOP
© 2005 Julian Dyke juliandyke.com 6 Example Examples in this presentation taken from Formula 1 database Contains full details of all races from 1961 to 2004 Updated annually in November (end of season) Currently 20 cars per race 19 races per season `Approximately 360 new rows per season juliandyke.net
© 2005 Julian Dyke juliandyke.com 7 Schema CLASSIFICATION SEASON GRANDPRIX RACETEAMDRIVER COUNTRYCIRCUIT ENGINE CAR
© 2005 Julian Dyke juliandyke.com 8 Cars Each season has up to 18 races (19 in 2005) Each race has up to 39 entrants (13 races in 1989) Each car has driver, team and engine laps completed (may be zero) optional notes Results are classified as follows CClassified DNFDid not finish DNSDid not start DNQDid not qualify DISDisqualified
© 2005 Julian Dyke juliandyke.com 9 Points Points basically awarded to driver and team as follows 1 st 2 nd 3 rd 4 th 5 th 6 th 7 th 8 th Pre onwards But... not always straightforward Half points awarded for incomplete races Split races (two half point races aggregated) Driver and / or team disqualifications e.g. Tyrrell in 1984 Up to 1980 only best scores counted for each half of season e.g. Best 5 results from first 7 races and best 5 results from last 7 races only best 11 results counted for drivers only first car to finish counted for each team
© 2005 Julian Dyke juliandyke.com 10 Input file - car.csv Comma separated file rows Fields are: season_key race_key position driver_key team_key engine_key laps_completed classification_key notes (optional) ZBAUMINFOR41DNFSpin DCOUMCLMER38DNFAccident RBARFER 38DNFAccident MWEBJAGFOR20DNFOverheated JMONWILBMW71C KRAIMCLMER71C RBARFER 71C FALOREN 71C RSCHWILBMW71C TSATBARHON71C MSCHFER 71C FMASSAUFER71C GFISSAUFER71C JVILREN 70C DCOUMCLMER70C JTRUTOY 70C RZONTOY 70C CKLIJAGFOR69C TGLOJORFOR69C ZBAUMINFOR67C GBRUMINFOR67C MWEBJAGFOR23DNFAccident NHEIJORFOR15DNFClutch JBUTBARHON3DNFEngine
© 2005 Julian Dyke juliandyke.com 11 Input file - points.csv Comma separated file rows Fields are: season_key race_key position driver_points team_point
© 2005 Julian Dyke juliandyke.com 12 CAR table CAR table and index definitions CREATE TABLE car ( season_keyNUMBERNOT NULL, race_keyNUMBERNOT NULL, positionNUMBERNOT NULL, driver_keyVARCHAR2(4)NOT NULL, team_keyVARCHAR2(3)NOT NULL, engine_keyVARCHAR2(3)NOT NULL, laps_completedNUMBERNOT NULL, classification_keyVARCHAR2(4)NOT NULL, notesVARCHAR2(100), driver_pointsNUMBERNOT NULL DEFAULT 0, team_pointsNUMBERNOT NULLDEFAULT 0 ); ALTER TABLE car ADD CONSTRAINT car_pk PRIMARY KEY (season_key,race_key,position); CREATE INDEX car_driver ON car (season_key,driver_key,driver_points);
© 2005 Julian Dyke juliandyke.com 13 CAR CAR table relational integrity definitions ALTER TABLE car ADD CONSTRAINT car_race FOREIGN KEY (season_key,race_key) REFERENCES race (season_key,race_key); ALTER TABLE car ADD CONSTRAINT car_driver FOREIGN KEY (driver_key) REFERENCES driver (driver_key); ALTER TABLE car ADD CONSTRAINT car_team FOREIGN KEY (team_key) REFERENCES team (team_key); ALTER TABLE car ADD CONSTRAINT car_engine FOREIGN KEY (engine_key) REFERENCES engine (engine_key); ALTER TABLE car ADD CONSTRAINT car_classification FOREIGN KEY (classification_key) REFERENCES classification (classification_key);
© 2005 Julian Dyke juliandyke.com 14 For each line in car.csv { read :season_key, :race_key, :position, :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes; INSERT INTO car (season_key, race_key, position, driver_key, team_key, engine_key, laps_completed, classification_key, notes) VALUES (:season_key,:race_key,:position, :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes) COMMIT; } Baseline - Insert
© 2005 Julian Dyke juliandyke.com 15 Baseline - Insert Redo Generation for each Insert Statement Header 5.2 Start Transaction 5.1 (11.1) Undo Undo insert row in CAR tableINSERT 11.2 Redo Insert row in CAR table INSERT UndoUndo insert row into CAR_PK index5.1 (10.22) INSERT Redo10.2Insert row into CAR_PK indexINSERT 5.1 (10.22)UndoUndo insert row into CAR_DRIVER index INSERT Redo 10.2 Insert row into CAR_DRIVER indexINSERT Commit 5.4 End Transaction COMMIT Oracle 9.2 and below
© 2005 Julian Dyke juliandyke.com 16 Insert Statement Redo Generation for each Insert Statement Header 5.2 Start Transaction 5.1 (11.1) Undo Undo insert row in CAR tableINSERT 11.2 Redo Insert row in CAR table INSERT UndoUndo insert row into CAR_PK index5.1 (10.22) INSERT Redo10.2Insert row into CAR_PK indexINSERT 5.1 (10.22)UndoUndo insert row into CAR_DRIVER index INSERT Redo 10.2 Insert row into CAR_DRIVER indexINSERT Commit 5.4 End Transaction COMMIT Oracle 10.1 and above
© 2005 Julian Dyke juliandyke.com 17 Baseline - Update For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; SELECT driver_key, team_key, engine_key, laps_completed, classification_key, notes INTO :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes FROM car WHERE season_key = :season_key AND race_key = :race_key AND position = :position FOR UPDATE; UPDATE car SET driver_key = :driver_key, team_key = :team_key,engine_key = :engine_key, laps_completed = :laps_completed,classification_key = :classification_key, notes = :notes, driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; COMMIT; }
© 2005 Julian Dyke juliandyke.com 18 Baseline - Update Redo Generation for each Update Statement Header 5.2 Start Transaction 5.1 (11.1) Undo Undo update row in CAR tableUPDATE 11.5 Redo Update row in CAR table UPDATE UndoUndo delete row from CAR_DRIVER index5.1 (10.22) UPDATE Redo10.4Delete row from CAR_DRIVER indexUPDATE 5.1 (10.22)UndoUndo insert row into CAR_DRIVER index UPDATE Redo 10.2 Insert row into CAR_DRIVER indexUPDATE 5.1 (11.1) Undo Undo lock row in CAR tableSELECT FOR UPDATE 11.4 Redo Lock row in CAR tableSELECT FOR UPDATE Commit 5.4 End Transaction COMMIT Oracle 9.2 and below
© 2005 Julian Dyke juliandyke.com 19 Baseline - Update Redo Generation Header 5.2 Start Transaction 5.1 (11.1) Undo Undo update row in CAR tableUPDATE 11.5 Redo Update row in CAR table UPDATE UndoUndo delete row from CAR_DRIVER index5.1 (10.22) UPDATE Redo10.4Delete row from CAR_DRIVER indexUPDATE 5.1 (10.22)UndoUndo insert row into CAR_DRIVER index UPDATE Redo 10.2 Insert row into CAR_DRIVER indexUPDATE 5.1 (11.1) Undo Undo lock row in CAR tableSELECT FOR UPDATE 11.4 Redo Lock row in CAR tableSELECT FOR UPDATE Commit 5.4 End Transaction COMMIT Oracle 10.1 and aboveRedo Generation for each Update Statement
© 2005 Julian Dyke juliandyke.com 20 Baseline - Results Redo Generation in Bytes OperationINSERT (car.csv) UPDATE (points.csv) Total Baseline Note Amount of redo generated by both INSERT and UPDATE can be variable due to Undo segment management Recursive DDL statements e.g. extent allocation Block cleanouts
© 2005 Julian Dyke juliandyke.com 21 Test 1 Check for unused indexes CAR_PK indexes columns SEASON_KEY RACE_KEY POSITION supports primary key therefore mandatory CAR_DRIVER indexes columns SEASON_KEY DRIVER_KEY DRIVER_POINTS no longer required by current version of application DROP INDEX car_driver;
© 2005 Julian Dyke juliandyke.com 22 Test 1 - Insert Redo Generation for each Insert Statement Header 5.2 Start Transaction 11.2 Redo Insert row in CAR table INSERT Redo10.2Insert row into CAR_PK indexINSERT 5.1 (10.22)UndoUndo insert row into CAR_DRIVER index INSERT Redo 10.2 Insert row into CAR_DRIVER indexINSERT 5.1 (11.1) Undo Undo insert row in CAR tableINSERT UndoUndo insert row into CAR_PK index5.1 (10.22) INSERT Commit 5.4 End Transaction COMMIT STOP
© 2005 Julian Dyke juliandyke.com 23 Test 1 - Update Redo Generation Header 5.2 Start Transaction 5.1 (11.1) Undo Undo update row in CAR tableUPDATE 11.5 Redo Update row in CAR table UPDATE UndoUndo delete row from CAR_DRIVER index5.1 (10.22) UPDATE Redo10.4Delete row from CAR_DRIVER indexUPDATE 5.1 (10.22)UndoUndo insert row into CAR_DRIVER index UPDATE Redo 10.2 Insert row into CAR_DRIVER indexUPDATE 5.1 (11.1) Undo Undo lock row in CAR tableSELECT FOR UPDATE 11.4 Redo Lock row in CAR tableSELECT FOR UPDATE Commit 5.4 End Transaction COMMIT Redo Generation for each Update Statement STOP
© 2005 Julian Dyke juliandyke.com 24 Test 1 - Results Redo Generation in Bytes OperationINSERT (car.csv) UPDATE (points.csv) Total Baseline Test Conclusion Eliminating redundant index reduced insert redo generation by bytes update redo generation by bytes
© 2005 Julian Dyke juliandyke.com 25 Test 2 In UPDATE statements For tables undo and redo is generated for all columns in SET clause For indexes undo and redo are only generated for index keys that have changed Statements often update all columns to reduce parsing e.g.: UPDATE car SET driver_key = :driver_key, team_key = :team_key, engine_key = :engine_key, laps_completed = :laps_completed, classification_key = :classification_key, notes = :notes, driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position;
© 2005 Julian Dyke juliandyke.com 26 Test 2 - Update Redo Generation Header 5.2 Start Transaction 5.1 (11.1) Undo Undo update row in CAR table UPDATE 11.5 Redo Update row in CAR table UPDATE 5.1 (11.1) Undo Undo lock row in CAR tableSELECT FOR UPDATE 11.4 Redo Lock row in CAR tableSELECT FOR UPDATE Commit 5.4 End Transaction COMMIT Redo Generation for each Update Statement Slot = 23 Col 3 = JMON Col 4 = WIL Col 5 = BMW Col 6 = 71 Col 7 = C Col 8 = Col 9 = 10 Col 10= 10 Slot = 23 Col 3 = JMON Col 4 = WIL Col 5 = BMW Col 6 = 71 Col 7 = C Col 8 = Col 9 = 0 Col 10= Redo 5.1 (11.1) Undo Slot = 23 Col 3 = JMON Col 4 = WIL Col 5 = BMW Col 6 = 71 Col 7 = C Col 8 = Col 9 = 10 Col 10= 10 Slot = 23 Col 3 = JMON Col 4 = WIL Col 5 = BMW Col 6 = 71 Col 7 = C Col 8 = Col 9 = 0 Col 10= 0 STOP
© 2005 Julian Dyke juliandyke.com 27 Test 2 Only update columns which can have new values DRIVER_POINTS TEAM_POINTS For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; SELECT... FOR UPDATE; UPDATE car SET driver_key = :driver_key, team_key = :team_key, engine_key = :engine_key, laps_completed = :laps_completed, classification_key = :classification_key, notes = :notes, driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; COMMIT; } For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; SELECT... FOR UPDATE; UPDATE car SET driver_key = :driver_key, team_key = :team_key, engine_key = :engine_key, laps_completed = :laps_completed, classification_key = :classification_key, notes = :notes, driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; COMMIT; }
© 2005 Julian Dyke juliandyke.com 28 Test 2 - Results Redo Generation in Bytes OperationINSERT (car.csv) UPDATE (points.csv) Total Baseline Test Test Conclusion Eliminating unnecessary columns from update statements reduced update redo generation by bytes Would be significantly more if unchanged columns included long fields e.g. CHAR, or VARCHAR2
© 2005 Julian Dyke juliandyke.com 29 Test 3 Eliminate unnecessary SELECT FOR UPDATE statements For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; SELECT driver_key, team_key, engine_key, laps_completed, classification_key, notes INTO :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes FROM car WHERE season_key = :season_key AND race_key = :race_key AND position = :position FOR UPDATE; UPDATE car SET driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; COMMIT; } For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; SELECT driver_key, team_key, engine_key, laps_completed, classification_key, notes INTO :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes FROM car WHERE season_key = :season_key AND race_key = :race_key AND position = :position FOR UPDATE; UPDATE car SET driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; COMMIT; }
© 2005 Julian Dyke juliandyke.com 30 Test 3 - Update Redo Generation Header 5.2 Start Transaction 5.1 (11.1) Undo Undo lock row in CAR tableSELECT FOR UPDATE 11.4 Redo Lock row in CAR tableSELECT FOR UPDATE Redo Generation for each Update Statement 11.5 Redo Update row in CAR table UPDATE 5.1 (11.1) Undo Undo update row in CAR tableUPDATE Commit 5.4 End Transaction COMMIT STOP
© 2005 Julian Dyke juliandyke.com 31 Test 3 - Results Redo Generation in Bytes OperationINSERT (car.csv) UPDATE (points.csv) Total Baseline Test Test Test Conclusion Eliminating SELECT FOR UPDATE statement reduced update redo generation by bytes
© 2005 Julian Dyke juliandyke.com 32 Test 4 Rows are inserted with default values of 0 for driver_points and team_points Points only scored by first eight cars onwards first six cars - pre 2003 Only update rows with non-zero rows for driver_points and/or team_points Team Driver PointsNo Points Points No Points DriverTeam STOP
© 2005 Julian Dyke juliandyke.com 33 Header Redo 5.1 (11.1) Undo Commit 5.4 Test 4 - Update Redo GenerationRedo Generation for each Update Statement Header Redo 5.1 (11.1) Undo Commit 5.4 UPDATE car SET driver_points = 1 team_points = 1 WHERE... col9 = 0 col10 = 0 col9 = 1 col10 = 1 UPDATE car SET driver_points = 0 team_points = 0 WHERE... col9 = 0 col10 = 0 UPDATE car SET driver_points = 0 team_points = 0 WHERE... col9 = 0 col10 = 0 UPDATE car SET driver_points = 9 team_points = 9 WHERE... col9 = 0 col10 = 0 col9 = 9 col10 = 9 Header Redo 5.1 (11.1) Undo Commit 5.4 Header Redo 5.1 (11.1) Undo Commit 5.4 Header Redo 5.1 (11.1) Undo Commit 5.4 UPDATE car SET driver_points = 9 team_points = 9 WHERE... col9 = 0 col10 = 0 col9 = 9 col10 = 9 STOP
© 2005 Julian Dyke juliandyke.com 34 Test 4 Only update rows with non-zero rows for driver_points and/or team_points For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; UPDATE car SET driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; COMMIT; } For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; IF driver_points != 0 OR team_points != 0 THEN { UPDATE car SET driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; COMMIT; } }
© 2005 Julian Dyke juliandyke.com 35 Test 4 - Results Redo Generation in Bytes OperationINSERT (car.csv) UPDATE (points.csv) Total Baseline Test Test Test Test Conclusions Eliminating unnecessary update statements reduced update redo generation by bytes
© 2005 Julian Dyke juliandyke.com 36 For each line in car.csv { read :season_key, :race_key, :position, :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes; INSERT INTO car (season_key, race_key, position, driver_key, team_key, engine_key, laps_completed, classification_key, notes) VALUES (:season_key,:race_key,:position, :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes) COMMIT; } For each line in car.csv { read :season_key, :race_key, :position, :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes; INSERT INTO car (season_key, race_key, position, driver_key, team_key, engine_key, laps_completed, classification_key, notes) VALUES (:season_key,:race_key,:position, :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes) COMMIT; } COMMIT; Test 5 Eliminate unnecessary COMMIT statements
© 2005 Julian Dyke juliandyke.com 37 For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; IF driver_points != 0 OR team_points != 0 THEN { UPDATE car SET driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; COMMIT; } } For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; IF driver_points != 0 OR team_points != 0 THEN { UPDATE car SET driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; COMMIT; } } COMMIT; Test 5 Eliminate unnecessary COMMIT statements (continued)
© 2005 Julian Dyke juliandyke.com 38 Test 5 - Insert Redo GenerationRedo Generation for each Insert Statement Header 5.2 Start Transaction 11.2 Redo Insert row in CAR table INSERT Redo10.2Insert row into CAR_PK indexINSERT 5.1 (11.1) Undo Undo insert row in CAR tableINSERT UndoUndo insert row into CAR_PK index5.1 (10.22) INSERT Commit 5.4 End Transaction COMMIT Header 5.2 Start Transaction Undo Undo insert row into CAR_PK index 5.1 (10.22) INSERT 11.2 Redo Insert row in CAR table INSERT Redo10.2Insert row into CAR_PK indexINSERT 5.1 (11.1) Undo Undo insert row in CAR table INSERT Commit 5.4 End Transaction COMMIT STOP
© 2005 Julian Dyke juliandyke.com 39 Test 5 - Results Redo Generation in Bytes OperationINSERT (car.csv) UPDATE (points.csv) Total Baseline Test Test Test Test Test Conclusion Eliminating COMMIT statements reduced insert redo generation by bytes update redo generation by bytes
© 2005 Julian Dyke juliandyke.com 40 Test 6 Default batch size is 1 Test INSERT and UPDATE with different batch sizes Batch SizeINSERT RedoUPDATE RedoTotal Redo
© 2005 Julian Dyke juliandyke.com 41 Test 6 - Results
© 2005 Julian Dyke juliandyke.com 42 Test 6 - Results Redo Generation in Bytes OperationINSERT (car.csv) UPDATE (points.csv) Total Baseline Test Test Test Test Test Test Conclusion Batch Size of 128 reduced insert redo generation by bytes update redo generation unaffected
© 2005 Julian Dyke juliandyke.com 43 Test 7 Create global temporary table CREATE GLOBAL TEMPORARY TABLE temporary_car ( season_keyVARCHAR2(4), race_keyVARCHAR2(2), positionNUMBER, driver_keyVARCHAR2(4), team_keyVARCHAR2(3), engine_keyVARCHAR2(3), laps_completedNUMBER, classification_keyVARCHAR2(4), notesVARCHAR2(100), driver_pointsNUMBER, team_pointsNUMBER ) ON COMMIT PRESERVE ROWS;
© 2005 Julian Dyke juliandyke.com 44 Test 7 Insert rows into global temporary table For each line in car.csv { read :season_key, :race_key, :position, :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes; INSERT INTO temporary_car (season_key, race_key, position, driver_key, team_key, engine_key, laps_completed, classification_key, notes) VALUES (:season_key,:race_key,:position, :driver_key, :team_key, :engine_key, :laps_completed, :classification_key, :notes) COMMIT; } Generated bytes of redo
© 2005 Julian Dyke juliandyke.com 45 Test 7 Update points in global temporary table For each line in points.csv { read :season_key, :race_key, :position, :driver_points, :team_points; IF driver_points != 0 OR team_points != 0 THEN { UPDATE temporary car SET driver_points = :driver_points, team_points = :team_points WHERE season_key = :season_key AND race_key = :race_key AND position = :position; } } COMMIT; Generated bytes of redo
© 2005 Julian Dyke juliandyke.com 46 Test 7 Copy rows from global temporary table to permanent table INSERT INTO car ( season_key, race_key, position, driver_key, team_key, engine_key, laps_completed, classification_key, notes, driver_points, team_points ) SELECT season_key, race_key, position, driver_key, team_key, engine_key, laps_completed, classification_key, notes, driver_points, team_points FROM temporary_car; Generated bytes of redo APPEND hint had no effect
© 2005 Julian Dyke juliandyke.com 47 Test 7 - Results Redo Generation in Bytes Conclusion Global Temporary Table reduced total redo generation by bytes OperationDescriptionTotal BaselineUpdate all rows Test 1Update affected rows Test 2Update affected columns Test 3Drop index Test 4SELECT FOR UPDATE Test 5COMMIT Test 6Increase Batch Size Test 7Global Temporary Table
© 2005 Julian Dyke juliandyke.com 48 Test 8 Create external tables CREATE OR REPLACE DIRECTORY external_dir AS '/u01/app/oracle/gp'; CREATE TABLE external_points ( season_keyVARCHAR2(4), race_keyVARCHAR2(2), positionNUMBER, driver_pointsNUMBER, team_pointsNUMBER ) ORGANIZATION EXTERNAL ( TYPE ORACLE_LOADER DEFAULT DIRECTORY external_dir ACCESS PARAMETERS ( RECORDS DELIMITED BY NEWLINE FIELDS TERMINATED BY ',' ) LOCATION ('points.csv') );
© 2005 Julian Dyke juliandyke.com 49 Test 8 CREATE TABLE external_car ( season_keyVARCHAR2(4), race_keyVARCHAR2(2), positionNUMBER, driver_keyVARCHAR2(4), team_keyVARCHAR2(3), engine_keyVARCHAR2(3), laps_completedNUMBER, classification_keyVARCHAR2(4), notesVARCHAR2(100) ) ORGANIZATION EXTERNAL ( TYPE ORACLE_LOADER DEFAULT DIRECTORY external_dir ACCESS PARAMETERS ( RECORDS DELIMITED BY NEWLINE FIELDS TERMINATED BY ',' MISSING FIELD VALUES ARE NULL ) LOCATION ('car.csv') );
© 2005 Julian Dyke juliandyke.com 50 Test 8 Insert directly into permanent table joining contents of both external tables INSERT INTO car ( season_key, race_key, position, driver_key, team_key, engine_key, laps_completed, classification_key, notes, driver_points, team_points ) SELECT c.season_key, c.race_key, c.position, c.driver_key, c.team_key, c.engine_key, c.laps_completed, c.classification_key, c.notes, p.driver_points, p.team_points FROM external_car c, external_points p WHERE c.season_key = p.season_key AND c.race_key = p.race_key AND c.position = p.position"; Generated bytes of redo
© 2005 Julian Dyke juliandyke.com 51 Test 8 - Results Redo Generation in Bytes Conclusion External Tables reduced total redo generation by bytes OperationDescriptionTotal BaselineUpdate all rows Test 1Update affected rows Test 2Update affected columns Test 3Drop index Test 4SELECT FOR UPDATE Test 5COMMIT Test 6Increase Batch Size Test 7Global Temporary Table Test 8External Table
© 2005 Julian Dyke juliandyke.com 52 Conclusion We have seen that the following techniques can be used to reduce the amount of redo generated: Eliminating redundant indexes Reducing the number of columns updated Eliminating redundant SELECT FOR UPDATE statements Reducing the number of rows processed Eliminating COMMIT statements Increasing the batch size Using Global Temporary Tables Using External Tables
© 2005 Julian Dyke juliandyke.com 53 Thank you for your interest For more information and to provide feedback please contact me My address is: My website address is: