Please start any new threads on our new site at https://forums.sqlteam.com. We've got lots of great SQL Server experts to answer whatever question you can come up with.

 All Forums
 General SQL Server Forums
 Database Design and Application Architecture
 when is it time to have 2 tables instead of 1

Author  Topic 

mike123
Master Smack Fu Yak Hacker

1462 Posts

Posted - 2008-09-30 : 11:22:52
Hi,

I have a table that currently has 18 columns, and because of some application requirement changes, we have to make some modifications.

The items stored in each row of the current table are very similar to a new item we need to store. The new item we need to store, will use all of the 18 columns to store information about its properties, but we will need to add 2 more columns. (both just 2 char wide columns)

These 2 new columns will not be in use by the original items stored. One of these columns will be used to denote the row as a different type of item.

Hopefully this makes sense. To sum it up we are going to have 2 different types of items stored in this table. 1 item will use 18/20 columns to store stuff about it, the other will use 20/20.

I am debating whether this information should be stored in seperate tables for each completely unique type of row.

In the application, the information is selected and returned together, since both the items in this 1 table, or 2 tables, both belong to the same parentID.

What information should I take into account to make this decision ?

My other option aside from 1 table would be to create seperate tables for each item, since they are slightly different. This would leave us with 2 tables, one with 18 columns, and one with 19 columns as we wouldnt need that 1 extra column to denote what type of row it was, as its in its unique table already.

Since the results of both tables we be needed at the same time, we would have to likely union 2 queries together, or run 2 seperate queries, which would be a performance hit I think. Performance is a major issue.

How far is OK to denormalize my data ? I am guessing this is pretty light as far as denormalization goes. (If it classifies as that)


Any input is greatly appreciated. I am sure its pretty tough to make an exact call on this situation, so general input is very helpful too.



Thanks very much,
Mike123

visakh16
Very Important crosS Applying yaK Herder

52326 Posts

Posted - 2008-09-30 : 11:25:48
In future, are there chances of a new type coming which might require more than 20 columns for its properties?
Go to Top of Page

SwePeso
Patron Saint of Lost Yaks

30421 Posts

Posted - 2008-09-30 : 11:41:22
What are the 20 columns? Which datatypes and how many of each data type?
You normalize the 20 columns according to datatypes.

This is one way. It can also be discussed if this is some kind of EAV design.
-- Create the denormalized table
CREATE TABLE #Denormalized
(
RowID INT IDENTITY(1, 1) PRIMARY KEY,
Col1 DATETIME,
Col2 DATETIME,
Col3 DATETIME,
Col4 INT,
Col5 INT
)

-- Populate denormalized table
INSERT #Denormalized
SELECT 1, 2, 3, 4, 5

-- Show the denormalized table
SELECT *
FROM #Denormalized

-- Prepare datetime normalizing
CREATE TABLE #dt
(
RowID INT CONSTRAINT Fk_dt REFERENCES #Denormalized(RowID),
dt DATETIME,
tp TINYINT, -- Type 1,2 or 3 according to denormalized table DATETIMEs
PRIMARY KEY
(
RowID,
tp
)
)

-- Populate new datetime table
INSERT #dt
SELECT RowID,
Col1,
1
FROM #Denormalized

INSERT #dt
SELECT RowID,
Col2,
2
FROM #Denormalized

INSERT #dt
SELECT RowID,
Col3,
3
FROM #Denormalized

-- Prepare int normalizing
CREATE TABLE #int
(
RowID INT CONSTRAINT Fk_dt REFERENCES #Denormalized(RowID),
i INT,
tp TINYINT, -- Type 1 or 2 according to denormalized table for INTs
PRIMARY KEY
(
RowID,
tp
)
)

-- Populate new datetime table
INSERT #int
SELECT RowID,
Col4,
4
FROM #Denormalized

INSERT #int
SELECT RowID,
Col5,
5
FROM #Denormalized

-- Now drop redundant columns
ALTER TABLE #Denormalized
DROP COLUMN Col1,
Col2,
Col3,
Col4,
Col5

-- Show resultset
SELECT d.RowID,
q.Col1,
q.Col2,
q.Col3,
i.Col4,
i.Col5
FROM #Denormalized AS d
LEFT JOIN (
SELECT RowID,
MAX(CASE WHEN tp = 1 THEN dt ELSE NULL END) AS Col1,
MAX(CASE WHEN tp = 2 THEN dt ELSE NULL END) AS Col2,
MAX(CASE WHEN tp = 3 THEN dt ELSE NULL END) AS Col3
FROM #dt
GROUP BY RowID
) AS q ON q.RowID = d.RowID
LEFT JOIN (
SELECT RowID,
MAX(CASE WHEN tp = 4 THEN i ELSE NULL END) AS Col4,
MAX(CASE WHEN tp = 5 THEN i ELSE NULL END) AS Col5
FROM #int
GROUP BY RowID
) AS i ON i.RowID = d.RowID

-- Clean up
DROP TABLE #Denormalized,
#dt,
#int



E 12°55'05.63"
N 56°04'39.26"
Go to Top of Page

mike123
Master Smack Fu Yak Hacker

1462 Posts

Posted - 2008-09-30 : 12:02:39
quote:
Originally posted by visakh16

In future, are there chances of a new type coming which might require more than 20 columns for its properties?



No, at this point there is nothing that I can forsee.


Thanks,
Mike
Go to Top of Page

mike123
Master Smack Fu Yak Hacker

1462 Posts

Posted - 2008-09-30 : 12:17:16
Hi Peso,

The columns are pretty small in my opinion, this is the current structure not including the 2 columns that would be added. They are properties of another rowitem in another table. Ive shown the columns that would be added as a "_NEW" suffix.

I'm not exactly sure if this qualifies as an EAV design?

Again, your expertise is greatly appreciated.

Thanks,
Mike123


[1_ID] [int] IDENTITY(1,1) NOT NULL,
[2_ID] [int] NULL,
[3_ID] [nvarchar](50) NULL,
[4] [int] NULL,
[5] [int] NULL,
[6] [int] NULL,
[7] [int] NULL,
[varchar](500) NULL,
[9] [nvarchar](25) NULL,
[10] [nvarchar](50) NULL,
[11] [bit] NULL,
[12] [bit] NULL,
[13] [bit] NULL,
[14] [bit] NULL,
[15] [int] NULL,
[16] [varchar](5) NOT NULL,
[17] [datetime] NULL,
[18_NEW] [char](1) NULL,
[19_NEW] [char](1) NULL


Go to Top of Page
   

- Advertisement -