Wednesday, December 30, 2009

Section 6.4 Oracle9








 

 












6.4 Oracle9i New DATETIME Features





With Oracle9i, Oracle introduced features to

enhance support for temporal data. These new features form the basis

of Oracle's support for:







  • Time zones



  • Date and time data with fractional seconds



  • Date and time intervals





In this section we discuss these enhancements and their uses.







6.4.1 Time Zones





In the Internet economy,



business is

carried out across geographical boundaries and time zones. Oracle

facilitates global e-business through its support for time zones.

With Oracle9i, a database and a session can now

be associated with time zones. Having database and session time zones

enables users in geographically distant regions to exchange temporal

data with the database without having to bother about the time

differences between their location and the server's

location.







6.4.1.1 Database time zone




We can set

the time

zone of a database when we create the database. After creating the

database, we can change the time zone using the

ALTER DATABASE command. Both CREATE

DATABASE and ALTER DATABASE take an optional SET TIME_ZONE clause.

Specify a time zone in one of the two ways:







  • By specifying a displacement from the Coordinated

    Universal Time (UTC).



  • By specifying a time zone region.





The displacement from the UTC is specified in hours and minutes with

a + or - sign. Every time zone region is given a region name. For

example, EST is the region name for Eastern Standard Time. We can

also use such a region name to set the time zone of a database.



















UTC was formerly known as Greenwich

Mean Time (GMT).











The syntax of SET TIME_ZONE clause is:





SET TIME_ZONE = '+ | - HH:MI' | 'time_zone_region'




The following examples use this clause to set the time zone of a

database:





CREATE DATABASE ... SET TIME_ZONE = '-05:00';



ALTER DATABASE ... SET TIME_ZONE = 'EST';




Both of the previous examples set the time zone to Eastern Standard

Time. The first example uses a displacement (-05:00) from the UTC.

The second example uses the region name (EST).



















If we do not explicitly set the

database time zone, Oracle defaults to the operating system time

zone. If the operating system time zone is not a valid Oracle time

zone, UTC is used as the default time zone.













6.4.1.2 Session time zone




Each session



can have

a time zone as well. The time zone of a session can be set by using

the ALTER SESSION SET TIME_ZONE clause. The syntax for the SET

TIME_ZONE clause in the ALTER SESSION statement is the same as that

in the CREATE DATABASE and ALTER DATABASE statements.





The following example shows two ways to set the time zone of a

session to Pacific Standard Time:





ALTER SESSION SET TIME_ZONE = '-08:00';



ALTER SESSION SET TIME_ZONE = 'PST';




To set the session time zone to the local operating system time zone

(e.g., the time zone of a PC initiating a remote user session), we

can use the LOCAL keyword in the SET TIME_ZONE clause, as in the

following example:





ALTER SESSION SET TIME_ZONE = LOCAL;




To set the session time zone to the database time zone, use the



DBTIMEZONE

keyword in the SET TIME_ZONE clause, as in the following example:





ALTER SESSION SET TIME_ZONE = DBTIMEZONE;




We will talk more about the DBTIMEZONE keyword later.



















If the session time zone has not been explicitly set, Oracle defaults

to the local operating system time zone. If the operating system time

zone is not a valid Oracle time zone, UTC is used as the default time

zone.













6.4.2 Date and Time Data with Fractional Seconds





To provide



support

for the fractional seconds along with date and time data,

Oracle9i introduced the following new temporal

datatypes:







  • TIMESTAMP



  • TIMESTAMP WITH TIMEZONE



  • TIMESTAMP WITH LOCAL TIMEZONE





These datatypes provide ways to handle time values resolved down to

the fraction of a second, and in different time zones. The following

sections discuss these datatypes.







6.4.2.1 TIMESTAMP




The TIMESTAMP datatype

extends the DATE type to support more

precise time values. A TIMESTAMP includes all the components of the

DATE datatype (century, year, month, day, hour, minute, second) plus

fractional seconds. A TIMESTAMP datatype is specified as:





TIMESTAMP [ (precision for fractional seconds) ]




The precision for the fractional seconds is specified in the

parentheses. We can specify integer values between 0 and 9 for

fractional precision. A precision of 9 means that we can have 9

digits to the right of the decimal. As you can see from the syntax

notation, the precision field is optional. If we

don't specify the precision, it defaults to 6; i.e.,

TIMESTAMP is the same as TIMESTAMP(6).





The following example creates a table with a TIMESTAMP column:





CREATE TABLE TRANSACTION (

TRANSACTION_ID NUMBER(10),

TRANSACTION_TIMESTAMP TIMESTAMP,

STATUS VARCHAR2(12));



Table created.



DESC TRANSACTION

Name Null? Type

--------------------------- -------- ---------------

TRANSACTION_ID NUMBER(10)

TRANSACTION_TIMESTAMP TIMESTAMP(6)

STATUS VARCHAR2(12)




Note that even though we specified just TIMESTAMP as the datatype of

the column TRANSACTION_TIMESTAMP, it appears as TIMESTAMP(6) when we

describe the table. To insert data into this column, we can use a

TIMESTAMP literal in the following format:





TIMESTAMP 'YYYY-MM-DD HH:MI:SS.xxxxxxxxx'




A TIMESTAMP literal can have up to 9 digits of fractional seconds.

The fractional part is optional, but the date and time elements are

mandatory and must be provided in the specified format.

Here's an example in which data is inserted into a

table with a TIMESTAMP column:





INSERT INTO TRANSACTION 

VALUES (1001, TIMESTAMP '1998-12-31 08:23:46.368', 'OPEN');



1 row created.



SELECT * FROM TRANSACTION;



TRANSACTION_ID TRANSACTION_TIMESTAMP STATUS

-------------- --------------------------------- ---------

1001 31-DEC-98 08.23.46.368000 AM OPEN










6.4.2.2 TIMESTAMP WITH TIME ZONE




The TIMESTAMP WITH TIME ZONE

datatype further extends the TIMESTAMP type to include a time zone

displacement. A TIMESTAMP WITH TIME ZONE datatype is specified as:





TIMESTAMP [ (precision for fractional seconds) ] WITH TIME ZONE




The precision for fractional seconds is the same as that for the

TIMESTAMP datatype. The time zone displacement is the time difference

in hours and minutes, between the local time and GMT (Greenwich Mean

Time, also known as Coordinated Universal Time or UTC). We supply

such displacements when we store values in the column, and the

database retains the displacements so that those values can later be

translated into any target time zone desired by the user.





The following example creates a table with a TIMESTAMP column:





CREATE TABLE TRANSACTION_TIME_ZONE (

TRANSACTION_ID NUMBER(10),

TRANSACTION_TIMESTAMP TIMESTAMP(3) WITH TIME ZONE,

STATUS VARCHAR2(12));



Table created.



DESC TRANSACTION_TIME_ZONE

Name Null? Type

------------------------------- -------- ------------------------

TRANSACTION_ID NUMBER(10)

TRANSACTION_TIMESTAMP TIMESTAMP(3) WITH TIME ZONE

STATUS VARCHAR2(12)




To insert data into the TRANSACTION_TIMESTAMP column, we can use a

TIMESTAMP literal with a time zone displacement, which takes the

following form:





TIMESTAMP 'YYYY-MM-DD HH:MI:SS.xxxxxxxxx {+|-} HH:MI'




Here is an example showing how to insert data into a table with a

TIMESTAMP WITH TIME ZONE column:





INSERT INTO TRANSACTION_TIME_ZONE 

VALUES (1002, TIMESTAMP '1998-12-31 08:23:46.368 -10:30', 'NEW');



1 row created.



SELECT * FROM TRANSACTION_TIME_ZONE;



TRANSACTION_ID TRANSACTION_TIMESTAMP STATUS

-------------- ----------------------------------- -------

1002 31-DEC-98 08.23.46.368 AM -10:30 NEW




Note that even though the datatype is called TIMESTAMP WITH TIME

ZONE, the literal still uses just the TIMESTAMP keyword. Also note

that the literal specifies a date/time displacement using the

{+|-}hour:minute notation.





If we are specifying a time zone displacement with a TIMESTAMP

literal, we must specify the sign of the displacement (i.e., + or -).

The range of the hour in a time zone displacement is -12 through +13,

and the range of a minute is 0 through 59. A displacement outside

these ranges will generate an error.





When we don't specify a time zone displacement, the

displacement is not assumed to be zero; instead, the timestamp is

assumed to be in the local time zone, and the value of the

displacement defaults to the displacement of the local time zone. In

the following example, the input data doesn't

specify any time zone. Therefore, Oracle assumes the timestamp to be

in the local time zone, and stores the local time zone along with the

timestamp in the database column.





INSERT INTO TRANSACTION_TIME_ZONE 

VALUES (1003, TIMESTAMP '1999-12-31 08:23:46.368', 'NEW');



1 row created.



SELECT * FROM TRANSACTION_TIME_ZONE;



TRANSACTION_ID TRANSACTION_TIMESTAMP STATUS

-------------- ------------------------------------- -------

1003 31-DEC-99 08.23.46.368 AM -05:00 NEW










6.4.2.3 TIMESTAMP WITH LOCAL TIME ZONE




The TIMESTAMP WITH LOCAL

TIME ZONE datatype is a variant of the TIMESTAMP WITH TIME ZONE

datatype. A TIMESTAMP WITH LOCAL TIME ZONE datatype is specified as:





TIMESTAMP [ (precision for fractional seconds) ] WITH LOCAL TIME ZONE




The precision for the fractional seconds is the same as that in the

TIMESTAMP datatype. TIMESTAMP WITH LOCAL TIME ZONE differs from

TIMESTAMP WITH TIME ZONE in the following ways:







  • The time zone displacement is not stored as part of the column data.



  • The data stored in the database is normalized to the time zone of the

    database. To normalize an input date to the database time zone, the

    input time is converted to a time in the database time zone.



  • When the data is retrieved, Oracle returns the data in the time zone

    of the user session.





The following example creates a table with a TIMESTAMP column:





CREATE TABLE TRANSACTION_LOCAL_TIME_ZONE (

TRANSACTION_ID NUMBER(10),

TRANSACTION_TIMESTAMP TIMESTAMP(3) WITH LOCAL TIME ZONE,

STATUS VARCHAR2(12));



Table created.



DESC TRANSACTION_LOCAL_TIME_ZONE

Name Null? Type

------------------------ -------- ------------------------

TRANSACTION_ID NUMBER(10)

TRANSACTION_TIMESTAMP TIMESTAMP(3) WITH LOCAL TIME ZONE

STATUS VARCHAR2(12)




There is no literal for the TIMESTAMP WITH LOCAL TIME ZONE datatype.

To insert data into this column, we use a TIMESTAMP literal. For

example:





INSERT INTO TRANSACTION_LOCAL_TIME_ZONE VALUES (

2001, TIMESTAMP '1998-12-31 10:00:00 -3:00', 'NEW');



1 row created.



SELECT * FROM TRANSACTION_LOCAL_TIME_ZONE;



TRANSACTION_ID TRANSACTION_TIMESTAMP STATUS

-------------- -------------------------- -------

2001 31-DEC-98 08.00.00 AM NEW




Note that the time zone displacement is not stored in the database.

The data is stored in the database in the normalized form with

respect to the database time zone. What this means is that the input

time is converted into a time in the database time zone before being

storing in the database. The database time zone is -5:00. Therefore,

-3:00 is 2 hours ahead of the database time zone, and 10:00:00 - 3:00

is the same as 08:00:00 - 5:00. Since the time is normalized with

respect to the database time zone, the displacement does not need to

be stored in the database.











6.4.3 Date and Time Intervals





Date and time interval data are an integral part of

our day-to-day life. Common examples of interval data are the age of

a person, the maturity period of a bond or certificate of deposit,

and the warranty period of your car. Prior to

Oracle9i, we all used the NUMBER datatype to

represent such data, and the logic needed to deal with interval data

had to be coded at the application level.

Oracle9i provides two new datatypes to handle

interval data:







  • INTERVAL YEAR TO MONTH



  • INTERVAL DAY TO SECOND





The following sections discuss the use of these datatypes.







6.4.3.1 INTERVAL YEAR TO MONTH




The INTERVAL YEAR TO MONTH type

stores a period of time expressed as a number of years and months. An

INTERVAL YEAR TO MONTH datatype is specified as:





INTERVAL YEAR [ (precision for year) ] TO MONTH




The precision specifies the number of digits in the year field. The

precision can range from 0 to 9, and the default value is 2. The

default precision of two allows for a maximum interval of 99 years,

11 months.





The following example creates a table with INTERVAL YEAR TO MONTH

datatype:





CREATE TABLE EVENT_HISTORY (

EVENT_ID NUMBER(10),

EVENT_DURATION INTERVAL YEAR TO MONTH);



Table created.



DESC EVENT_HISTORY

Name Null? Type

---------------------------- -------- ------------------------

EVENT_ID NUMBER(10)

EVENT_DURATION INTERVAL YEAR(2) TO MONTH




The next example uses the NUMTOYMINTERVAL (NUM-TO-YM-INTERVAL)

function to insert data into a database column of type INTERVAL YEAR

TO MONTH. This function converts a NUMBER value into a value of type

INTERVAL YEAR TO MONTH, and is discussed later in this chapter in Section 6.5.3.





INSERT INTO EVENT_HISTORY VALUES (5001, NUMTOYMINTERVAL(2,'YEAR'));



1 row created.



INSERT INTO EVENT_HISTORY VALUES (5002, NUMTOYMINTERVAL(2.5,'MONTH'));



1 row created.



SELECT * FROM EVENT_HISTORY;



EVENT_ID EVENT_DURATION

---------- ------------------

5001 +02-00

5002 +00-02




The second argument to the NUMTOYMINTERVAL function specifies the

unit of the first argument. Therefore, in the first example, the

number 2 is treated as 2 years, and in the second example, the number

2.5 is treated as 2 months. Note that the fractional part of a month

is ignored. An INTERVAL YEAR TO MONTH value is only in terms of years

and months, not fractional months. Any fractional values of a month

are truncated.











6.4.3.2 INTERVAL DAY TO SECOND




The INTERVAL DAY TO SECOND type

stores a period of time expressed as a number of days, hours,

minutes, seconds, and fractions of a second. An INTERVAL DAY TO

SECOND datatype is specified as:





INTERVAL DAY [(precision for day)] 

TO SECOND [(precision for fractional seconds)]




The precision for day specifies the number of digits in the day

field. This precision can range from 0 to 9, and the default value is

2. The precision for fractional seconds is the number of digits in

the fractional part of second. It can range from 0 to 9, and the

default value is 6.





The following example creates a table with INTERVAL DAY TO SECOND

datatype:





CREATE TABLE BATCH_JOB_HISTORY (

JOB_ID NUMBER(6),

JOB_DURATION INTERVAL DAY(3) TO SECOND(6));



Table created.



DESC BATCH_JOB_HISTORY

Name Null? Type

----------------------- -------- -----------------------------

JOB_ID NUMBER(6)

JOB_DURATION INTERVAL DAY(3) TO SECOND(6)




Here's how to insert data into a table with an

INTERVAL DAY TO SECOND column:





INSERT INTO BATCH_JOB_HISTORY VALUES

(6001, NUMTODSINTERVAL(5369.2589,'SECOND'));



1 row created.



SELECT * FROM BATCH_JOB_HISTORY;



JOB_ID JOB_DURATION

---------- ----------------------------------------

6001 +00 01:29:29.258900




To insert into a database column of type INTERVAL DAY TO SECOND, we

used a function NUMTODSINTERVAL (NUM-TO-DS-INTERVAL). This function

converts a NUMBER value into a value of type INTERVAL DAY TO SECOND,

and is discussed in Section 6.5.3 later in this chapter.




















     

     


    No comments: