Skip to Main Content

Breadcrumb

Warning

Before you submit your comment...

Remember - this is about feedback to the original question. AskTOM is about building a strong Oracle community, not stealing time away from others needing assistance by sneaking in a brand new question under the guise of "Comment".

If your comment requires a response that might include a query, please supply very simple CREATE TABLE and INSERT statements. Nice simple scripts so we can replicate your issue simply.

Remember to take a look at Legal Notices and Terms of Use before supplying a comment...

Don't forget, your comments are public. If you want to send a comment to just the AskTOM team, please use the feedback option

Comment

Highlight any SQL, PL/SQL, or fixed-width text and click the <code> button
 (will never be published or used to spam you)

Question and Answer

Chris Saxon

Thanks for the question, Ricardo.

Asked: April 20, 2010 - 5:13 pm UTC

Last updated: June 29, 2022 - 11:06 am UTC

Version: 10.2

Viewed 100K+ times! This question is

You Asked

Tom, I have a doubt about adding columns with default values to a table. Recently, I have stumble upon an Arup Nanda article on it where he states the following

"When a user selects the column for an existing record, Oracle gets the fact about the default value from the data dictionary and returns it to the user" he further says "you can define a new column as not null and with a default value and still not incur any penalty for redo and undo generation."

which actually caught my attention. Reading through the documentation I see this "When you specify a default value, the database immediately updates each row with the default value. Note that this can take some time, and that during the update, there is an exclusive DML lock on the table." It makes no mention of Oracle getting the fact about the default value of the column of the table from the dictionary. I do see, however, that a new sentece has been added to the 11g documentation regarding this and this is it "For some types of tables (for example, tables without LOB columns), if you specify both a NOT NULL constraint and a default value, the database can optimize the column add operation and greatly reduce the amount of time that the table is locked for DML." but again, it doesn't mention what KIND of optimization Oracle does. I have done very light test adding the column with the default value and not null constraint straight, as opposing of doing it step by step (add the column, update to the default value, then add the not null constraint) and whereas redo generation (according to v$mystat) is reduced, there is no significant reduction in undo generation (this is on 10gR2).

So my question is: Is it correct to assume what Arup Nanda says about Oracle getting the fact about the default value of the column at "query time" or Oracle still has to update all the rows when you specify a default value to a column and a not null constraint ?

For your reference, here are the links to Arup Nanda article and 11g documentation

http://www.oracle.com/technology/pub/articles/oracle-database-11g-top-features/11g-schemamanagement.html
http://download.oracle.com/docs/cd/B28359_01/server.111/b28310/tables006.htm#sthref1856

Thanks!

and Tom said...

Arup is talking about 11g - a new feature.

You posted that your version is 10g Release 2, you do not have the fast add column yet.


If a new column is added to a table, the column is initially NULL unless you specify the DEFAULT clause. When you specify a default value, the database immediately updates each row with the default value. Note that this can take some time, and that during the update, there is an exclusive DML lock on the table. For some types of tables (for example, tables without LOB columns), if you specify both a NOT NULL constraint and a default value, the database can optimize the column add operation and greatly reduce the amount of time that the table is locked for DML.

The documentation is correct for 11g - the 11g documentation would not be correct when discussing 10g.

Your testing in 10g is completely invalid since - in 10g - this feature DID NOT EXIST.

ops$tkyte%ORA11GR1> create table t pctfree 50 as select * from all_objects;

Table created.

ops$tkyte%ORA11GR1>
ops$tkyte%ORA11GR1> column redo new_val R
ops$tkyte%ORA11GR1> column undo new_val U
ops$tkyte%ORA11GR1>
ops$tkyte%ORA11GR1> select max(decode( a.name, 'redo size', b.value )) redo,
  2         max(decode( a.name, 'undo change vector size', b.value )) undo
  3  from v$statname a, v$mystat b
  4  where a.statistic# = b.statistic#
  5  and a.name in ( 'redo size', 'undo change vector size' );

      REDO       UNDO
---------- ----------
 112138396   31140348

ops$tkyte%ORA11GR1> alter table t add y char(80) default 'x' not null;

Table altered.

ops$tkyte%ORA11GR1> select max(decode( a.name, 'redo size', b.value )) redo,
  2         max(decode( a.name, 'redo size', b.value )) -&R redo_diff,
  3         max(decode( a.name, 'undo change vector size', b.value )) undo,
  4         max(decode( a.name, 'undo change vector size', b.value ))-&U undo_diff
  5  from v$statname a, v$mystat b
  6  where a.statistic# = b.statistic#
  7  and a.name in ( 'redo size', 'undo change vector size' );

      REDO  REDO_DIFF       UNDO  UNDO_DIFF
---------- ---------- ---------- ----------
 112147868       9472   31143192       2844

ops$tkyte%ORA11GR1> alter table t add x char(80) default 'x' null;

Table altered.

ops$tkyte%ORA11GR1> select max(decode( a.name, 'redo size', b.value )) redo,
  2         max(decode( a.name, 'redo size', b.value )) -&R redo_diff,
  3         max(decode( a.name, 'undo change vector size', b.value )) undo,
  4         max(decode( a.name, 'undo change vector size', b.value ))-&U undo_diff
  5  from v$statname a, v$mystat b
  6  where a.statistic# = b.statistic#
  7  and a.name in ( 'redo size', 'undo change vector size' );

      REDO  REDO_DIFF       UNDO  UNDO_DIFF
---------- ---------- ---------- ----------
 148759788   36611920   41369292   10226100



In 11g you can see there is a vast difference between adding a NOT NULL column with a default and a NULLable column with a default.

Rating

  (34 ratings)

Is this answer out of date? If it is, please let us know via a Comment