【问题标题】:SQL Server SELECT INTO @variable?SQL Server SELECT INTO @variable?
【发布时间】:2011-06-16 23:16:36
【问题描述】:

我的 Sql (2008) Stored Procs 中有以下代码,执行得非常好:

    CREATE PROCEDURE [dbo].[Item_AddItem]
        @CustomerId uniqueidentifier,
        @Description nvarchar(100),
        @Type int,
        @Username nvarchar(100),
    AS
    BEGIN

        DECLARE @TopRelatedItemId uniqueidentifier;
        SET @TopRelatedItemId = 
        (
           SELECT top(1) RelatedItemId 
           FROM RelatedItems 
           WHERE CustomerId = @CustomerId
        ) 

        DECLARE @TempItem TABLE
        (
            ItemId uniqueidentifier,
            CustomerId uniqueidentifier,
            Description nvarchar(100),
            Type int,
            Username nvarchar(100),
            TimeStamp datetime
        );

        INSERT INTO Item
        OUTPUT INSERTED.* INTO @TempItem
        SELECT NEWID(), @CustomerId, @Description, @Type, @Username, GETDATE()

        SELECT
            ItemId,
            CustomerId,
            @TopRelatedItemId,
            Description,
            Type,
            Username,
            TimeStamp
        FROM
            @TempItem
END
GO

所以你们的问题是有没有可能做一些类似的事情:

DECLARE @TempCustomer TABLE
(
   CustomerId uniqueidentifier,
   FirstName nvarchar(100),
   LastName nvarchar(100),
   Email nvarchar(100)
);
SELECT 
    CustomerId, 
    FirstName, 
    LastName, 
    Email 
INTO 
    @TempCustomer 
FROM 
    Customer
WHERE 
    CustomerId = @CustomerId

以便我可以在其他以下语句中重用内存中的这些数据? SQL Server 与上述语句相匹配,但是我不想创建单独的变量并通过针对同一张表的单独 SELECT 语句初始化它们中的每一个......呃!!!

关于如何在不针对同一个表进行多次查询的情况下实现某些目标的任何建议?

【问题讨论】:

  • “创建单独的变量并通过单独的 SELECT 语句初始化每个变量” - 为什么需要这样做? declare @t table 一次,如果您需要重复使用它,请在再次插入之前触发 DELETE @TempCustomer

标签: sql sql-server tsql sql-server-2008


【解决方案1】:

我发现您的问题正在寻找解决同一问题的方法;其他答案未能指出的是一种使用变量以永久形式而不是临时形式为每次执行过程更改表名称的方法。

到目前为止,我所做的是将整个 SQL 代码与要使用的变量连接起来。像这样:

declare @table_name as varchar(30)
select @table_name = CONVERT(varchar(30), getdate(), 112)
set @table_name = 'DAILY_SNAPSHOT_' + @table_name

EXEC('
        SELECT var1, var2, var3
        INTO '+@table_name+'
        FROM my_view
        WHERE string = ''Strings must use double apostrophe''
    ');

希望对你有帮助,但是如果代码太大会比较麻烦,所以如果你找到了更好的方法,请分享!

【讨论】:

    【解决方案2】:
    "SELECT *
      INTO 
        @TempCustomer 
    FROM 
        Customer
    WHERE 
        CustomerId = @CustomerId"
    

    这意味着创建一个新的@tempCustomer 表变量并插入来自客户的数据。您已经在上面声明了它,因此无需再次声明。最好搭配

    INSERT INTO @tempCustomer SELECT * FROM Customer
    

    【讨论】:

    • 它不起作用。您仍然需要事先声明表变量。
    【解决方案3】:

    如果您想简单地分配一些变量供以后使用,您可以按照以下方式一次性完成:

    declare @var1 int,@var2 int,@var3 int;
    
    select 
        @var1 = field1,
        @var2 = field2,
        @var3 = field3
    from
        table
    where
        condition
    

    如果那是你所追求的东西

    【讨论】:

    • 最佳答案恕我直言,但如果结果不止一个会怎样?
    • 如果结果多于一个,您将获得可用值之一。这可能是一个有趣的谜题!见mssqltips.com/sqlservertip/1888/…
    • 强制查询返回单行使用 SELECT TOP 1
    • @Adrian 是的,上面的查询假设您选择了一行。如果你想要更多花哨的逻辑,你也可以使用排序和聚合函数。
    • 如果您不使用 OP 正在使用的数据库类型,并非所有都支持 TOP 1,正如 Adrian 提到的。 SQL Server/MS Access 使用 TOP,MySQL 使用 LIMIT,Oracle 使用 ROWNUM。请参阅w3schools.com/sql/sql_top.asp 了解更多信息。
    【解决方案4】:

    你可以这样做:

    SELECT 
        CustomerId, 
        FirstName, 
        LastName, 
        Email
    INTO #tempCustomer 
    FROM 
        Customer
    WHERE 
        CustomerId = @CustomerId
    

    后来

    SELECT CustomerId FROM #tempCustomer
    

    你不需要声明#tempCustomer的结构

    【讨论】:

    • @webturner 这些观点都不正确。临时表的范围不在 proc 之外,并且表变量不再比临时表“仅内存”。
    • 不要忘记在不再需要#tempCustomer 时添加DROP TABLE #tempCustomer,否则下一次选择将导致#tempCustomer already exists 错误
    【解决方案5】:

    听起来你想要临时表。 http://www.sqlteam.com/article/temporary-tables

    请注意,#TempTable 在整个 SP 中都可用。

    请注意,##TempTable 可供所有人使用。

    【讨论】:

    • ##temptable - 直到所有者(创建者)删除它或断开连接
    • 我不想要临时表。临时表既昂贵又缓慢。我只想在一小段时间内为特定记录保留一些数据,并使其可用于多个 sql 语句,而无需后续查找。由于表变量在定义它们的存储过程中具有作用域,因此它们是为该存储过程调用存储元组数据的完美解决方案......
    • 我也忘了提到数据库驻留在 Azure 中......我不想在管理临时表时引入混乱。
    • 变量表是要走的路。声明@varTable Table (....)
    【解决方案6】:

    看起来你的语法有点不对劲。这有一些good examples

    DECLARE @TempCustomer TABLE
    (
       CustomerId uniqueidentifier,
       FirstName nvarchar(100),
       LastName nvarchar(100),
       Email nvarchar(100)
    );
    INSERT @TempCustomer 
    SELECT 
        CustomerId, 
        FirstName, 
        LastName, 
        Email 
    FROM 
        Customer
    WHERE 
        CustomerId = @CustomerId
    

    后来

    SELECT CustomerId FROM @TempCustomer
    

    【讨论】:

    • 由于来自 dbforums 的重定向,“优秀示例”链接已转化为广告。是否有更好的链接来表达您的意图?
    【解决方案7】:

    您不能选择 .. INTO .. 一个表变量。你能做的最好的就是先创建它,然后插入它。你的第二个 sn-p 必须是

    DECLARE @TempCustomer TABLE
    (
       CustomerId uniqueidentifier,
       FirstName nvarchar(100),
       LastName nvarchar(100),
       Email nvarchar(100)
    );
    INSERT INTO 
        @TempCustomer 
    SELECT 
        CustomerId, 
        FirstName, 
        LastName, 
        Email 
    FROM 
        Customer
    WHERE 
        CustomerId = @CustomerId
    

    【讨论】:

    • 应该注意,这在 CTE 上下文中也可以正常工作。巴津加!
    • 谁知道为什么不能像使用实际临时表那样选择表变量?
    • 为什么不可能?可能是为了防止因内存不足异常而炸毁数据库服务器的可能性。 DB服务器需要是一个非常稳定的进程...
    猜你喜欢
    • 2012-01-23
    • 1970-01-01
    • 1970-01-01
    • 2023-03-13
    • 2010-11-21
    • 2018-05-22
    • 2023-02-09
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多