Author |
Topic |
sqlbug
Posting Yak Master
201 Posts |
Posted - 2009-08-10 : 17:00:53
|
I am inserting data from one table to another and using case statements in my query like:SELECT...DATA_VALUE =(CASE SAMPLE_START_TIME WHEN '0' THEN CONT_HOUR1_VALUE WHEN '100'.... ....END),DATA_FLAG =((CASE SAMPLE_START_TIME WHEN '0' THEN CONT_HOUR1_FLAG WHEN '100'.... ....END) This is slowing down my query quite a bit, as 24 data and 24 flag columns are there on which the separate case statements are running.Is there any way I can combine these two together so I can use just one statement?Thanks. |
|
sqlbug
Posting Yak Master
201 Posts |
Posted - 2009-08-11 : 13:27:56
|
Oh, at least I got some readers. |
|
|
TG
Master Smack Fu Yak Hacker
6065 Posts |
Posted - 2009-08-11 : 13:46:13
|
I dont' think the CASE statements as you illustrated should slow the query down in any noticeable way. I suspect there is other things about your statement that is. Can you post the whole thing?Be One with the OptimizerTG |
|
|
sqlbug
Posting Yak Master
201 Posts |
Posted - 2009-08-11 : 15:18:27
|
Thanks TG. Here is it:DECLARE @sdate datetimeSET @sdate = '01-Jul-1988'WHILE (@sdate <= '31-Dec-1988')BEGIN INSERT INTO PLOT_DATA (DATA_SAMPLE_NUM,DATA_PARAMETER,DATA_METHOD, DATA_UNIT,DATA_DECIMAL,DATA_VALUE,DATA_FLAG) SELECT [TSAMPLE_NUM],[CONT_PARAMETER],[CONT_METHOD],[CONT_UNITS], [CONT_DECIMAL],TDATA_VALUE = (CASE TSAMPLE_START_TIME WHEN '0' THEN CONT_HOUR1_VALUE WHEN '100' THEN CONT_HOUR2_VALUE WHEN '200' THEN CONT_HOUR3_VALUE WHEN '300' THEN CONT_HOUR4_VALUE WHEN '400' THEN CONT_HOUR5_VALUE WHEN '500' THEN CONT_HOUR6_VALUE WHEN '600' THEN CONT_HOUR7_VALUE WHEN '700' THEN CONT_HOUR8_VALUE WHEN '800' THEN CONT_HOUR9_VALUE WHEN '900' THEN CONT_HOUR10_VALUE WHEN '1000' THEN CONT_HOUR11_VALUE WHEN '1100' THEN CONT_HOUR12_VALUE WHEN '1200' THEN CONT_HOUR13_VALUE WHEN '1300' THEN CONT_HOUR14_VALUE WHEN '1400' THEN CONT_HOUR15_VALUE WHEN '1500' THEN CONT_HOUR16_VALUE WHEN '1600' THEN CONT_HOUR17_VALUE WHEN '1700' THEN CONT_HOUR18_VALUE WHEN '1800' THEN CONT_HOUR19_VALUE WHEN '1900' THEN CONT_HOUR20_VALUE WHEN '2000' THEN CONT_HOUR21_VALUE WHEN '2100' THEN CONT_HOUR22_VALUE WHEN '2200' THEN CONT_HOUR23_VALUE WHEN '2300' THEN CONT_HOUR24_VALUE END), TDATA_FLAG = (CASE TSAMPLE_START_TIME WHEN '0' THEN CONT_HOUR1_FLAG WHEN '100' THEN CONT_HOUR2_FLAG WHEN '200' THEN CONT_HOUR3_FLAG WHEN '300' THEN CONT_HOUR4_FLAG WHEN '400' THEN CONT_HOUR5_FLAG WHEN '500' THEN CONT_HOUR6_FLAG WHEN '600' THEN CONT_HOUR7_FLAG WHEN '700' THEN CONT_HOUR8_FLAG WHEN '800' THEN CONT_HOUR9_FLAG WHEN '900' THEN CONT_HOUR10_FLAG WHEN '1000' THEN CONT_HOUR11_FLAG WHEN '1100' THEN CONT_HOUR12_FLAG WHEN '1200' THEN CONT_HOUR13_FLAG WHEN '1300' THEN CONT_HOUR14_FLAG WHEN '1400' THEN CONT_HOUR15_FLAG WHEN '1500' THEN CONT_HOUR16_FLAG WHEN '1600' THEN CONT_HOUR17_FLAG WHEN '1700' THEN CONT_HOUR18_FLAG WHEN '1800' THEN CONT_HOUR19_FLAG WHEN '1900' THEN CONT_HOUR20_FLAG WHEN '2000' THEN CONT_HOUR21_FLAG WHEN '2100' THEN CONT_HOUR22_FLAG WHEN '2200' THEN CONT_HOUR23_FLAG WHEN '2300' THEN CONT_HOUR24_FLAG END) FROM PLOT_DATA_TEMP,CONTINUOUS_DATA WHERE TSAMPLE_OLD_NUM = CONT_SAMPLE_NUM AND TSAMPLE_START_DATE = @sdate ORDER BY TSAMPLE_NUM,CONT_PARAMETER,CONT_METHOD SET @sdate = @sdate + 1END |
|
|
TG
Master Smack Fu Yak Hacker
6065 Posts |
Posted - 2009-08-11 : 15:39:27
|
Funny that you thought the slow performance was the CASE statements when you have a loop in there for 183 seperate selects from the same table :) try this non-looping method to see if there is an improvement:DECLARE @sdate_start datetime ,@sdate_end datetimeselect @sdate_start = '01-Jul-1988' ,@sdate_end = '31-Dec-1988'declare @dates table (sdate datetime)insert @dates (sdate)select dateadd(day, number, @sdate_start)from master..spt_valueswhere type = 'P'and number < datediff(day, @sdate_start, @sdate_end)INSERT INTO PLOT_DATA (DATA_SAMPLE_NUM ,DATA_PARAMETER ,DATA_METHOD ,DATA_UNIT ,DATA_DECIMAL ,DATA_VALUE ,DATA_FLAG)SELECT [TSAMPLE_NUM] ,[CONT_PARAMETER] ,[CONT_METHOD] ,[CONT_UNITS] ,[CONT_DECIMAL] ,TDATA_VALUE = CASE TSAMPLE_START_TIME WHEN '0' THEN CONT_HOUR1_VALUE WHEN '100' THEN CONT_HOUR2_VALUE WHEN '200' THEN CONT_HOUR3_VALUE WHEN '300' THEN CONT_HOUR4_VALUE WHEN '400' THEN CONT_HOUR5_VALUE WHEN '500' THEN CONT_HOUR6_VALUE WHEN '600' THEN CONT_HOUR7_VALUE WHEN '700' THEN CONT_HOUR8_VALUE WHEN '800' THEN CONT_HOUR9_VALUE WHEN '900' THEN CONT_HOUR10_VALUE WHEN '1000' THEN CONT_HOUR11_VALUE WHEN '1100' THEN CONT_HOUR12_VALUE WHEN '1200' THEN CONT_HOUR13_VALUE WHEN '1300' THEN CONT_HOUR14_VALUE WHEN '1400' THEN CONT_HOUR15_VALUE WHEN '1500' THEN CONT_HOUR16_VALUE WHEN '1600' THEN CONT_HOUR17_VALUE WHEN '1700' THEN CONT_HOUR18_VALUE WHEN '1800' THEN CONT_HOUR19_VALUE WHEN '1900' THEN CONT_HOUR20_VALUE WHEN '2000' THEN CONT_HOUR21_VALUE WHEN '2100' THEN CONT_HOUR22_VALUE WHEN '2200' THEN CONT_HOUR23_VALUE WHEN '2300' THEN CONT_HOUR24_VALUE END ,TDATA_FLAG = CASE TSAMPLE_START_TIME WHEN '0' THEN CONT_HOUR1_FLAG WHEN '100' THEN CONT_HOUR2_FLAG WHEN '200' THEN CONT_HOUR3_FLAG WHEN '300' THEN CONT_HOUR4_FLAG WHEN '400' THEN CONT_HOUR5_FLAG WHEN '500' THEN CONT_HOUR6_FLAG WHEN '600' THEN CONT_HOUR7_FLAG WHEN '700' THEN CONT_HOUR8_FLAG WHEN '800' THEN CONT_HOUR9_FLAG WHEN '900' THEN CONT_HOUR10_FLAG WHEN '1000' THEN CONT_HOUR11_FLAG WHEN '1100' THEN CONT_HOUR12_FLAG WHEN '1200' THEN CONT_HOUR13_FLAG WHEN '1300' THEN CONT_HOUR14_FLAG WHEN '1400' THEN CONT_HOUR15_FLAG WHEN '1500' THEN CONT_HOUR16_FLAG WHEN '1600' THEN CONT_HOUR17_FLAG WHEN '1700' THEN CONT_HOUR18_FLAG WHEN '1800' THEN CONT_HOUR19_FLAG WHEN '1900' THEN CONT_HOUR20_FLAG WHEN '2000' THEN CONT_HOUR21_FLAG WHEN '2100' THEN CONT_HOUR22_FLAG WHEN '2200' THEN CONT_HOUR23_FLAG WHEN '2300' THEN CONT_HOUR24_FLAG ENDFROM PLOT_DATA_TEMPinner join CONTINUOUS_DATA on TSAMPLE_OLD_NUM = CONT_SAMPLE_NUMinner join @dates d on d.sdate = TSAMPLE_START_DATEORDER BY TSAMPLE_NUM ,CONT_PARAMETER,CONT_METHOD Be One with the OptimizerTG |
|
|
sqlbug
Posting Yak Master
201 Posts |
Posted - 2009-08-11 : 16:06:14
|
I didn't think that I can get rid of the loop. So was looking at the other things. I'll test it and let you know.Thanks so much. |
|
|
TG
Master Smack Fu Yak Hacker
6065 Posts |
Posted - 2009-08-11 : 16:25:21
|
You're welcome. If TSAMPLE_START_DATE only has one row per day as opposed to several rows with different times. then you could remove the @dates table variable and just add a WHERE clause:where TSAMPLE_START_DATE between @sdate_start and @sdate_endBe One with the OptimizerTG |
|
|
sqlbug
Posting Yak Master
201 Posts |
Posted - 2009-08-11 : 16:31:16
|
Hi TG, Its 184 days, not 183 days right?So, should it be like:and number <= datediff(day, @sdate_start, @sdate_end)orand number < datediff(day, @sdate_start, @sdate_end + 1)And yes, it was pretty fast - just 47 seconds.Thanks again. |
|
|
TG
Master Smack Fu Yak Hacker
6065 Posts |
Posted - 2009-08-11 : 16:35:57
|
Yes, you're right. Good catch.How long was it taking previously?Be One with the OptimizerTG |
|
|
sqlbug
Posting Yak Master
201 Posts |
Posted - 2009-08-11 : 17:31:39
|
Over an hour most of the times! |
|
|
|