32

I can't update temp table. This is my query

CREATE TABLE #temp_po(IndentID INT, OIndentDetailID INT, OD1 VARCHAR(50), OD2 VARCHAR(50), 
        OD3 VARCHAR(50), ORD VARCHAR(50), NIndentDetailID INT, ND1 VARCHAR(50), ND2 VARCHAR(50), 
        ND3 VARCHAR(50), NRD VARCHAR(50), Quantity DECIMAL(15,3))

        INSERT INTO #temp_po(IndentID, OIndentDetailID, OD1, OD2, OD3, ORD)
        SELECT ID.IndentID, ID.IndentDetailID, ID.D1, ID.D2, ID.D3, ID.RandomDimension 
        FROM STR_IndentDetail ID WHERE ID.IndentID = @IndentID

        UPDATE 
            t 
        SET
            t.ND1 = CASE WHEN D.D1 = '' THEN NULL ELSE D.D1 END,
            t.ND2 = CASE WHEN D.D2 = '' THEN NULL ELSE D.D2 END,
            t.ND3 = CASE WHEN D.D3 = '' THEN NULL ELSE D.D3 END,
            t.NRD = CASE WHEN D.RandomDim = '' THEN NULL ELSE D.RandomDim END,
            t.Quantity = D.PurchaseQty
        FROM
            #temp_po t INNER JOIN @detail D ON D.IndentDetailID = t.OIndentDetailID
        WHERE
            t.IndentID = @IndentID

But it gives the error

Cannot resolve the collation conflict between "Latin1_General_CI_AI" and "SQL_Latin1_General_CP1_CI_AS" in the equal to operation.

How to resolve this problem?

My tempdb collation is Latin1_General_CI_AI and my actual database collation is SQL_Latin1_General_CP1_CI_AS.

4

4 回答 4

51

发生这种情况是因为排序规则#tempdb.temp_po.OD1STR_IndentDetail.D1不同(特别是,请注意这#tempdb是一个不同的系统数据库,这通常是为什么它会有一个默认的排序规则意见,不像您自己的数据库和表,您可能已经提供了更具体的意见) .

由于您可以控制临时表的创建,因此解决此问题的最简单方法似乎是在临时表中使用与表相同的排序规则创建 *char 列STR_IndentDetail

CREATE TABLE #temp_po(
    IndentID INT, 
    OIndentDetailID INT, 
    OD1 VARCHAR(50) COLLATE SQL_Latin1_General_CP1_CI_AS, 
    .. Same for the other *char columns   

在您无法控制表创建的情况下,当您连接列时,另一种方法是COLLATE在发生错误的 DML 中添加显式语句,无论是通过COLLATE SQL_Latin1_General_CP1_CI_AS或更简单,使用COLLATE DATABASE_DEFAULT

SELECT * FROM #temp_po t INNER JOIN STR_IndentDetail s 
   ON t.OD1 = s.D1 COLLATE SQL_Latin1_General_CP1_CI_AS;

或者,更容易

SELECT * FROM #temp_po t INNER JOIN STR_IndentDetail s 
   ON t.OD1 = s.D1 COLLATE DATABASE_DEFAULT;

SqlFiddle 在这里

于 2014-01-24T12:07:02.160 回答
7

更改服务器排序规则不是一个直接的决定,服务器上可能有其他数据库可能会受到影响。对于现有的填充数据库,即使更改数据库排序规则也不总是可取的。我认为COLLATE DATABASE_DEFAULT在创建临时表时使用是最安全和最简单的选择,因为它不会在你的 sql 中硬编码任何排序规则。例如:

CREATE TABLE #temp_table1
(
    column_1    VARCHAR(2)  COLLATE database_default
)
于 2017-04-28T08:40:18.983 回答
0

我们现在遇到了同样的问题。我们没有将排序规则添加到临时表创建(或每个临时表连接),而是将临时表创建更改为表变量声明。

于 2016-10-14T08:19:47.923 回答
0

默认情况下,临时表采用服务器的排序规则。因此,使用临时表更新所有存储过程只会更改服务器排序规则。

检查此链接以设置或更改服务器排序规则

这对我有用。

于 2016-06-02T12:38:39.687 回答