Avatar of -Polak
-Polak
Flag for United States of America asked on

Use Variable to Identify a Column Name for update

Hi Experts,
I have data in Table1:
id     | mission # | category | category2| salary
1      | 12345     | flying A  | aircraft| $1000.00
2      | 54321     | flying B  | aircraft| $500.00

Open in new window

I have 2 columns in Table2 named "Salaries for flying A - aircraft" and "Salaries for flying B - aircraft" and a Mission # Column.
mission # | "Salaries for flying A - aircraft" | "Salaries for flying B - aircraft"|

Open in new window

I would like $1000.00 to go to the Flying A column and $500.00 go to the flying B column for the matching Mission #.

NOTE: Mission #s in Table1 are not unique; therefore, salaries for records with the same Mission # will be need to be summed in a temporary table before moving to Table2 (unless you have a better approach).

Thus Far I have the following code(using a temporary table to sum by Mission#):
DECLARE @ID INT 
DECLARE @Mission# NVARCHAR(100) 
DECLARE @Category NVARCHAR(100) 
DECLARE @Category2 NVARCHAR(100) 
DECLARE @Salary MONEY 
DECLARE @ColumnName NVARCHAR(1000) 

SET @ID = 1 
--While @ID < 167921 
--Begin 
SET @Mission# = (SELECT mission# 
                 FROM   temporarytable 
                 WHERE  id = @ID) 
SET @Category = (SELECT category 
                 FROM   temporarytable
                 WHERE  id = @ID) 
SET @Category2 = (SELECT category2 
                  FROM   temporarytable
                  WHERE  id = @ID) 
SET @Salary = (SELECT salary 
               FROM   temporarytable
               WHERE  id = @ID) 
SET @ColumnName = 'Base Salaries for ' + @Category + ' - ' 
                  + @Category2 

EXECUTE ('update Table2 set @ColumnName = ''' + @Salary + 
''' where [Mission#] = ''' + @Mission# + '''') 
--Set @ID = @ID + 1 
--End 

Open in new window

However, I can't seem to get the @ColumnName variable into the execute statement unless is is hard coded as the actual column name (eg. "Salaries for flying A - aircraft"). When I try and use @ColumnName I get a "must declare scalar variable "@ColumnName" error. If I mess around with the syntax a bit and use  
EXECUTE ('update Table2 set ' + @ColumnName +  ' = ''' + @Salary + 
''' where [Mission#] = ''' + @Mission# + '''') 

Open in new window

I get an "incorrect sytanx near 'Salaries' error.

Am I missing something? Is there a better approach?
Microsoft SQL Server

Avatar of undefined
Last Comment
-Polak

8/22/2022 - Mon
Éric Moreau

since your column name is multiple words, you need to surround it with []

EXECUTE ('update Table2 set [' + @ColumnName +  ' = ''' + @Salary + 
'''] where [Mission#] = ''' + @Mission# + '''') 

Open in new window

-Polak

ASKER
With that I get an  Incorrect syntax near the keyword 'where' error.
SOLUTION
Daniel Van Der Werken

THIS SOLUTION ONLY AVAILABLE TO MEMBERS.
View this solution by signing up for a free trial.
Members can start a 7-Day free trial and enjoy unlimited access to the platform.
See Pricing Options
Start Free Trial
GET A PERSONALIZED SOLUTION
Ask your own question & get feedback from real experts
Find out why thousands trust the EE community with their toughest problems.
-Polak

ASKER
Thanks Daniel, the Dynamic SQL syntax is pretty confusing. Both your methods work wonderfully.

Do any tips on speeding up this loop? I'm running SQL server locally on my laptop and this executes at a speed of about .17 seconds per record and will take about 8 Hours to complete..? Most of the time is being spent on Index Seek and RID Lookup (Heat).
This is the best money I have ever spent. I cannot not tell you how many times these folks have saved my bacon. I learn so much from the contributors.
rwheeler23
Scott Pletcher

If I understand correctly, you don't need a temp table.  


INSERT INTO table2 ( mission#, [Salaries for flying A - aircraft], [Salaries for flying B - aircraft] )
SELECT mission#,
    SUM(CASE WHEN category = 'flying A' /*AND category2 = 'aircraft'*/ THEN salary ELSE 0 END) AS [Salaries for flying A - aircraft],
    SUM(CASE WHEN category = 'flying B' /*AND category2 = 'aircraft'*/ THEN salary ELSE 0 END) AS [Salaries for flying B - aircraft]
FROM table1
WHERE
    category IN ('flying A', 'flying B') /*AND category2 = 'aircraft'*/
GROUP BY mission#
-Polak

ASKER
@Scott, if i understand you correctly. Yes, transposing the data would likely run quicker; however, what's not completely clear in my example (my fault) is that Table2 already has mission # data in it and what needs to be brought over from Table1 is the salary information depending on category and category2.
SOLUTION
Scott Pletcher

THIS SOLUTION ONLY AVAILABLE TO MEMBERS.
View this solution by signing up for a free trial.
Members can start a 7-Day free trial and enjoy unlimited access to the platform.
See Pricing Options
Start Free Trial
⚡ FREE TRIAL OFFER
Try out a week of full access for free.
Find out why thousands trust the EE community with their toughest problems.
Daniel Van Der Werken

Not sure I can help with the speed issue. A couple things that might help, This:

SET @Mission# = (SELECT mission# 
                 FROM   temporarytable 
                 WHERE  id = @ID) 
SET @Category = (SELECT category 
                 FROM   temporarytable
                 WHERE  id = @ID) 
SET @Category2 = (SELECT category2 
                  FROM   temporarytable
                  WHERE  id = @ID) 
SET @Salary = (SELECT salary 
               FROM   temporarytable
               WHERE  id = @ID) 

Open in new window


Can easily be:

SELECT 
             @Mission# = mission#,
             @Category = category,
             @Category2 = category2,
             @Salary = salary
FROM temporarytable
WHERE id = @ID

Open in new window


I doubt that'll save much time, but typing, yes.
⚡ FREE TRIAL OFFER
Try out a week of full access for free.
Find out why thousands trust the EE community with their toughest problems.
ASKER CERTIFIED SOLUTION
-Polak

THIS SOLUTION ONLY AVAILABLE TO MEMBERS.
View this solution by signing up for a free trial.
Members can start a 7-Day free trial and enjoy unlimited access to the platform.
See Pricing Options
Start Free Trial
⚡ FREE TRIAL OFFER
Try out a week of full access for free.
Find out why thousands trust the EE community with their toughest problems.
-Polak

ASKER
Thanks for the help gents