Friday, 2 November 2012

Columns Without Data Type

Introduction
 "Can you make a table with CREATE TABLE statement, where there are 4 columns and 1 of   the columns  is without data type?"
If we heard this above statement, we definitely think for 2 to 3 seconds. That the columns without data type?
The fact is not like that. The columns without data type are not possible. If we look at the above statement carefully it says CREATE TABLE statement… some kind of syntax.
It is taking about COMPUTED COLUMNS.
Here in this article, I am not going to discuss about the COMPUTED COLUMNS. Here I am trying to discuss about the DATA TYPE, PRECISION and SCALE of the computed columns.
Example -1
First we take an example of COMPUTED COLUMNS with CREATE TABLE statement to understand the data type of computed columns.
IF OBJECT_ID('TBL_EMPLOYEE') IS NOT NULL
   BEGIN
     DROP TABLE TBL_EMPLOYEE;
   END
GO  
CREATE TABLE TBL_EMPLOYEE
       (
          EMPID    INT           IDENTITY(1,1) PRIMARY KEY,
          EMPSAL   DECIMAL(20,2) NOT NULL,
          EMPGRADE AS (CASE WHEN EMPSAL>=20000 THEN  'A'
                            WHEN EMPSAL>=10000 AND EMPSAL<20000 THEN  'B'
                            WHEN EMPSAL>=1 AND EMPSAL<10000 THEN  'C' END)
       );
GO      
-- Insert Some record
INSERT INTO  TBL_EMPLOYEE                          
       (EMPSAL)
VALUES (5000),(10000),(12000),(15000),(2000),(22000)   

-- Dispaly records
SELECT * FROM TBL_EMPLOYEE;
Result set:
EMPID       EMPSAL                                  EMPGRADE
----------- --------------------------------------- --------
1           5000.00                                 C
2           10000.00                                B
3           12000.00                                B
4           15000.00                                B
5           2000.00                                 C
6           22000.00                                A

(6 row(s) affected)
Now we type to find the Data type of COMPUTED COLUMNS named "EMPGRADE".
SELECT COLUMN_NAME, DATA_TYPE, CHARACTER_MAXIMUM_LENGTH,
       NUMERIC_PRECISION, NUMERIC_SCALE
FROM   INFORMATION_SCHEMA.COLUMNS
WHERE  TABLE_NAME = 'TBL_EMPLOYEE'
Result set:
COLUMN_NAME
DATA_TYPE
CHARACTER_MAXIMUM_LENGTH
NUMERIC_PRECISION                       
NUMERIC_SCALE
EMPID
int
NULL
10
0
EMPSAL
decimal
NULL
20
2
EMPGRADE
varchar
1
NULL
NULL


So for the COMPUTED COLUMNS named "EMPGRADE" the data type is VARCHAR and the size is 1. So it the DATA TYPE of COMPUTED COLUMNS depends on what it stores. Please have a look of the CREATE TABLE syntax example again.

CREATE TABLE TBL_EMPLOYEE
       (
          EMPID    INT           IDENTITY(1,1) PRIMARY KEY,
          EMPSAL   DECIMAL(20,2) NOT NULL,
          EMPGRADE AS (CASE WHEN EMPSAL>=20000 THEN  'A'
                            WHEN EMPSAL>=10000 AND EMPSAL<20000 THEN  'B'
                            WHEN EMPSAL>=1 AND EMPSAL<10000 THEN  'C' END)
       );

Please look at the marked line. In columns named "EMPGRADE" is CASE statement the input value is one character length. So it takes VARCHAR(1) as data types.


Example -2

To understand it properly, we are taken an little bit complex example to understand data type and width.

IF OBJECT_ID('TBL_EMPLOYEE') IS NOT NULL
   BEGIN
     DROP TABLE TBL_EMPLOYEE;
   END
GO  
CREATE TABLE dbo.TBL_COLUMNSPLEX
(
       COLUMNS1 DECIMAL(20,2),
       COLUMNS2 NVARCHAR(10),
       COLUMNS3 DATETIME,
       COLUMNS4 DECIMAL(10,2),
       COLUMNS5 AS COLUMNS1 + COLUMNS4,
       COLUMNS6 AS '1 ST COLUMNS :' + CAST(COLUMNS1 AS NVARCHAR(10)) +
                   '2 ND COLUMNS :' + COLUMNS2 +
                   '3 RD COLUMNS :' + CONVERT(NVARCHAR(20), COLUMNS3, 120),
       COLUMNS7 AS COLUMNS2 + ' : ' + CAST(COLUMNS4 AS NVARCHAR(36))
)
GO 


-- Insert Some record
INSERT INTO TBL_COLUMNSPLEX
       (COLUMNS1, COLUMNS2, COLUMNS3, COLUMNS4)
VALUES (100, 'JOYDEEP', GETDATE(), 200.22)      
GO
-- Dispaly records
SELECT * FROM TBL_COLUMNSPLEX

Now we type to find the Data type of COMPUTED COLUMNS.

SELECT COLUMN_NAME, DATA_TYPE, CHARACTER_MAXIMUM_LENGTH,
       NUMERIC_PRECISION, NUMERIC_SCALE
FROM   INFORMATION_SCHEMA.COLUMNS
WHERE  TABLE_NAME = 'TBL_COLUMNSPLEX'


COLUMN_NAME
DATA_TYPE
CHARACTER_MAXIMUM_LENGTH
NUMERIC_PRECISION                       
NUMERIC_SCALE
COLUMNS1
decimal
NULL
20
2
COLUMNS2
nvarchar
10
NULL
NULL
COLUMNS3
datetime
NULL
NULL
NULL
COLUMNS4
decimal
NULL
10
2
COLUMNS5
decimal
NULL
21
2
COLUMNS6
nvarchar
82
NULL
NULL
COLUMNS7
nvarchar
49
NULL
NULL


Now discuss about DATATYPE and size of the COMPUTED COLUMNS.
Here are the computed columns are "COLUMNS5", "COLUMNS6", "COLUMNS7".

Here "COLUMNS5" Data type is DECIMAL.  Precision is 21 and the Scale is 2.  To understand it properly, how the precision and scale is set, we aging make a closer look of CREATE TABLE statement.

 CREATE TABLE dbo.TBL_COLUMNSPLEX
(
       COLUMNS1 DECIMAL(20,2),
       COLUMNS2 NVARCHAR(10),
       COLUMNS3 DATETIME,
       COLUMNS4 DECIMAL(10,2),
       COLUMNS5 AS COLUMNS1 + COLUMNS4,
       COLUMNS6 AS '1 ST COLUMNS :' + CAST(COLUMNS1 AS NVARCHAR(10)) +
                   '2 ND COLUMNS :' + COLUMNS2 +
                   '3 RD COLUMNS :' + CONVERT(NVARCHAR(20), COLUMNS3, 120),
       COLUMNS7 AS COLUMNS2 + ' : ' + CAST(COLUMNS4 AS NVARCHAR(36))
)
GO 



Here we are taking Precision and P, Scale as S and Expression E.

Precision Calculation

Here the COLUMNS5 = COLUMNS1(20,2) + COLUMNS4(10,2)
So    the COLUMNS5 = E1 + E2
Formula COLUMNS5 = MAX(S1, S2) + MAX(P1 – S1, P2 – S2) + 1
Putting the Values     = MAX(2, 2) + MAX(20 - 2 , 10 – 2) + 1
                                = MAX(2, 2) + MAX(18 , 8) + 1
                                = 2 + 18 +1
                                = 21 

Scale Calculation


Here the COLUMNS5 = COLUMNS1(20,2) + COLUMNS4(10,2)
So    the COLUMNS5 = E1 + E2
Formula COLUMNS5  = MAX(S1, S2)
Putting the Values      = MAX(2, 2)
                                 = 2
               
             
When two char, varchar, binary, or varbinary expressions are concatenated, the length of the resulting expression is the sum of the lengths of the two source expressions or 8,000 characters, whichever is less.
When two nchar or nvarchar expressions are concatenated, the length of the resulting expression is the sum of the lengths of the two source expressions or 4,000 characters, whichever is less.

The numeric operations chart for computed columns are mentioned bellow

Operation
Precision
Scale
e1 + e2
MAX(S1, S2) + MAX(P1-S1, P2-S2) + 1
MAX(S1, S2)
e1 - e2
MAX(S1, S2) + MAX(P1-S1, P2-S2) + 1
MAX(S1, S2)
e1 * e2
P1 + P2 + 1
S1 + S2
e1 / e2
P1 - S1 + S2 + MAX(6, S1 + P2 + 1)
MAX(6, S1 + P2 + 1)
e1 { UNION | EXCEPT | INTERSECT } e2
MAX(S1, S2) + MAX(P1-S1, P2-S2)
MAX(S1, S2)
e1 % e2
MIN(P1-S1, P2 -S2) + MAX( S1,S2 )
MAX(S1, S2)



References



Related tropics



Hope you like it.


Posted by: MR. JOYDEEP DAS

8 comments:

  1. Another thing that is important.
    ----------------------------------
    IF OBJECT_ID('TBL_CONVERSION') IS NOT NULL
    BEGIN
    DROP TABLE TBL_CONVERSION;
    END
    GO
    CREATE TABLE dbo.TBL_CONVERSION
    (
    COLUMNS1 TINYINT,
    COLUMNS2 TINYINT,
    COLUMNS3 AS COLUMNS1 * COLUMNS2
    );
    GO
    CREATE INDEX IX_TBL_CONVERSION ON TBL_CONVERSION (COLUMNS3);
    GO

    In this case if we try to insert some records
    ----------------------------------------------
    INSERT INTO TBL_CONVERSION
    (COLUMNS1, COLUMNS2)
    VALUES (255, 255);

    It gives and error

    Msg 8115, Level 16, State 2, Line 1
    Arithmetic overflow error converting expression to data type tinyint.
    The statement has been terminated.

    To Solve it
    ------------
    IF OBJECT_ID('TBL_CONVERSION') IS NOT NULL
    BEGIN
    DROP TABLE TBL_CONVERSION;
    END
    GO
    CREATE TABLE dbo.TBL_CONVERSION
    (
    COLUMNS1 TINYINT,
    COLUMNS2 TINYINT,
    COLUMNS3 AS CONVERT(INT, COLUMNS1) * CONVERT(INT, COLUMNS2)
    );

    GO
    CREATE INDEX IX_TBL_CONVERSION ON TBL_CONVERSION (COLUMNS3);
    GO

    INSERT INTO TBL_CONVERSION
    (COLUMNS1, COLUMNS2)
    VALUES (255, 255);

    Thank you.

    ReplyDelete
    Replies
    1. Dear readers,

      Please provide the Feedback and your valuable opinion that we can learn a lot for you.

      Thanking you.

      Delete
  2. It’s really nice article. Specially the Precision Calculation and Scale Calculation.

    ReplyDelete
  3. It is excellent one. Specially the Precision Calculation and Scale Calculation. Thanks to bring this knowledge in-front of us.

    ReplyDelete
  4. is the data stored physically for the computed column?

    ReplyDelete
    Replies
    1. Thanks "Sridhar" for your Interest.

      Question:
      is the data stored physically for the computed column?

      Answer:
      The Database Engine uses the PERSISTED keyword in the CREATE TABLE and ALTER TABLE statements to physically store computed columns in the table.

      Web References:
      You can find it in my previous post listed in Related Tropics
      http://sqlknowledgebank.blogspot.in/2012/05/computed-columns.html


      If have you any query please mail me at me.mr.sqlsercer@gmail.com

      I try my best to solve it.

      Delete