【问题标题】:How do I CREATE TABLE with dynamic column names (saved in variables)?如何使用动态列名(保存在变量中)创建表?
【发布时间】:2014-11-12 09:53:17
【问题描述】:

我想创建一个列名称为Members_2014Spend_2014 的表。我尝试将年份设置为变量并连接Member_ + @year,以便@year 减少,但我编写的代码似乎不起作用:

declare @li_year    int
declare @li_year2   int
declare @li_year3   int
declare @li_year4   int
declare @li_year5   int

set @li_year = datepart(year, GETDATE())
set @li_year2 = @li_year-1
set @li_year3 = @li_year-2
set @li_year4 = @li_year-3
set @li_year5 = @li_year-4

drop table [scratchdb].[dbo].results_test
create table [scratchdb].[dbo].results_test (RDesc varchar(30), 
   'Members_' + @li_year int, 
   'Spend_' + @li_year money,
   'Members_' + @li_year2  int, 
   'Spend_' + @li_year2 money,
   'Members_' + @li_year3  int, 
   'Spend_' + @li_year3 money,
   'Members_' + @li_year4  int, 
   'Spend_' + @li_year4 money,
   'Members_' + @li_year5 int, 
   'Spend_' + @li_year5 money)

【问题讨论】:

  • 对于大多数查询处理(现在您可能不需要全部作为动态 SQL 执行),然后在您实际向用户呈现数据的位置应用实际年份名称。

标签: tsql sql-server-2012 dynamic-sql create-table


【解决方案1】:

我想从个人观察开始:从长远来看,这很可能是个坏主意。理想情况下,数据库模式是固定的。但是,您的脚本会根据您运行它的年份产生不同的数据库模式(如果它有效,那就是)。这意味着,例如:

  • 您将无法使用您的脚本重新创建曾经在一、两年前工作的架构。
  • 您必须每年重写针对该数据库运行的所有查询和应用程序。

所以在短期内,你正在做的事情可能没问题,但最好简单地标准化你的架构并将年份作为一个额外的列:

CREATE TABLE dbo.results_test
(
    RDesc   VARCHAR(30),
    Year    SMALLINT NOT NULL UNIQUE, -- UNIQUE to enforce at most one record per year
    Members INT,
    Spend   MONEY
);

如果您决定反对这个并支持您当前的解决方案,那么您需要将整个 SQL 语句放在一个字符串变量中,而不仅仅是它的一部分:

DECLARE @sql NVARCHAR(MAX) =
     'CREATE TABLE … Members_' + CAST(@li_year AS NVARCHAR) + ' INT, …' + …
--                           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^       ^^^^
--                              regular string concatenation

EXECUTE sp_executesql @sql;

包含在字符串变量中的 SQL 语句称为动态 SQLsp_executesql system stored procedure 可帮助您运行这样的语句。

【讨论】:

  • 感谢您的建议。有道理。
猜你喜欢
  • 2011-02-23
  • 1970-01-01
  • 2018-05-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-10-26
  • 2011-10-27
相关资源
最近更新 更多