代码之家  ›  专栏  ›  技术社区  ›  Knox

SQL Server中要用作可写时间戳的类型是什么?

  •  4
  • Knox  · 技术社区  · 15 年前

    我在SQL Server中有一个表,tblmain。有一个触发器,当一行发生更改时,它基本上从tblmain执行select*并将更改后的行插入tblHistory。tblHistory是tblMain的副本(只有更高的版本),它有一个额外的字段作为唯一的ID。我最近添加了一个timestamp类型的字段(我现在知道它正在被弃用,但稍后我将处理它),以避免在Microsoft Access 2007中出现写冲突问题。

    显然,触发器将tblmain中的每个字段复制到tblHistory。它正在进行选择*。但是,如果我将timestamp类型的字段放在history表中以从tblmain接收该字段,那么触发器显然会失败。我应该在历史记录表中使用什么类型来接受时间戳源?

    3 回复  |  直到 15 年前
        1
  •  5
  •   AakashM    15 年前

    来自文档:

    不可为空的时间戳列在语义上等同于二进制(8)列。可以为空的时间戳列在语义上等价于varbinary(8)列。

    这工作:

    -- //Main table, with TIMESTAMP column
    CREATE TABLE Main ( id INT, TIMESTAMP )
    
    -- //Some values
    INSERT Main VALUES ( 8, DEFAULT )
    INSERT Main VALUES ( 4, DEFAULT )
    INSERT Main VALUES ( 2, DEFAULT )
    INSERT Main VALUES ( 7, DEFAULT )
    INSERT Main VALUES ( 0, DEFAULT )
    
    -- //See the values
    SELECT * FROM Main
    
    -- //History table
    -- //with VARBINARY(8) to store a nullable TIMESTAMP
    CREATE TABLE History (id INT, ts VARBINARY(8))
    
    -- //Populate History table
    INSERT History
    SELECT * FROM Main
    
    -- //See the values
    SELECT * FROM History
    
        2
  •  3
  •   marc_s    15 年前

    这个 TIMESTAMP 列类型正在被重命名,基本上,使用SQL Server 2008及更高版本,它将被调用 ROWVERSION 相反,它不会消失,只是有了一个新名字。

    现在,时间戳列确实是不可写的——所以基本上,在您的触发器中,您需要执行一个insert语句,其中列出了您要写的所有列——并省略时间戳。

    timestamp/rowversion是您的最佳选择——只有该类型的列被保证总是唯一的,并且对于每个后续的插入总是不断增加。任何与日期相关的列都可能有重复项(在SQL Server 2005中,日期时间的精度为3.33ms,因此您肯定可以有重复项)。

    您可能需要一个精确性和唯一性的时间戳和人类可读性的日期时间组合。时间戳由SQL Server自动处理,用于 LastModifiedDate DATETIME 你可以定义一个 DEFAULT CONSTRAINT 属于 GETDATE() 这样就可以记录每个插入的当前日期/时间。

        3
  •  0
  •   KM.    15 年前

    在触发器中,您可以这样做,这只会插入受影响的行,而且比解析原始表以查找已更改的内容快得多。

    INSERT INTO tblHistory
            (col1, col2, ...)
        SELECT
            col1, col2, ...
            FROM INSERTED