Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/78.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sql-server/23.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Sql 我如何向上插入桌子?_Sql_Sql Server_Tsql - Fatal编程技术网

Sql 我如何向上插入桌子?

Sql 我如何向上插入桌子?,sql,sql-server,tsql,Sql,Sql Server,Tsql,我有一个视图,其中有一个工作列表,其中包含分配给谁以及他们所处的阶段等数据。我需要编写一个存储过程,返回每个人在每个阶段有多少个作业 到目前为止,我有以下内容(简化): 问题是这些行不能合并。因此,如果一名员工在stage1和stage2中有工作,@resultable中有两行。我真正想做的是,如果工作人员的行存在,则更新该行,如果不存在,则插入新行 是否有人知道如何做到这一点,或者可以提出不同的方法? 我真的希望避免使用游标来迭代用户列表(但这是我的回退选项) 我正在使用SQLServer20

我有一个视图,其中有一个工作列表,其中包含分配给谁以及他们所处的阶段等数据。我需要编写一个存储过程,返回每个人在每个阶段有多少个作业

到目前为止,我有以下内容(简化):

问题是这些行不能合并。因此,如果一名员工在stage1和stage2中有工作,@resultable中有两行。我真正想做的是,如果工作人员的行存在,则更新该行,如果不存在,则插入新行

是否有人知道如何做到这一点,或者可以提出不同的方法? 我真的希望避免使用游标来迭代用户列表(但这是我的回退选项)

我正在使用SQLServer2005

Edit:@Lee:不幸的是,InStage1=1是一种简化。这更像是DateStart不为NULL,DateFinished为NULL

Edit:@BCS:我喜欢先插入所有员工的想法,所以每次我只需要做一次更新。但我正在努力使这些更新语句正确无误。

要获得真正的“upsert”类型的查询,您需要使用if exists。。。类型的东西,不幸的是这意味着使用游标


但是,您可以运行两个查询,一个用于在存在现有行的位置执行更新,然后插入新的行。我认为这种基于集合的方法更可取,除非您专门处理少量行。

您可以检查是否存在并使用适当的命令。我相信这确实在幕后使用了光标,但这是您可能得到的最好结果:

IF (EXISTS (SELECT * FROM MyTable WHERE StaffName = @StaffName))
begin
    UPDATE MyTable SET ... WHERE StaffName = @StaffName
end
else
begin
    INSERT MyTable ...
end 

SQL2008有一个新的合并功能,这很酷,但它不是在2005年。

事实上,我认为你让它变得更难了。这段代码对您正在尝试的工作不起作用吗

SELECT StaffName, SUM(InStage1) AS 'JobsAtStage1', SUM(InStage2) AS 'JobsAtStage2'
  FROM ViewJob
GROUP BY StaffName

下面对结果表的查询应再次合并这些行。这是假设InStage1和InStage2永远都不是“1”

select distinct(rt1.StaffName), rt2.Stage1Count, rt3.Stage2Count
from @ResultTable rt1
left join @ResultTable rt2 on rt1.StaffName=rt2.StaffName and rt2.Stage1Count is not null
left join @ResultTable rt3 on rt1.StaffName=rt2.StaffName and rt3.Stage2Count is not null

IIRC有一种“On Duplicate”(名称可能错误)语法,允许您在存在行时进行更新(MySQL)

或者,某种形式的:

INSERT INTO @ResultTable (StaffName, Stage1Count, Stage2Count)
  SELECT StaffName,0,0 FROM ViewJob
  GROUP BY StaffName

UPDATE @ResultTable Stage1Count= (
  SELECT COUNT(*) AS count FROM ViewJob
  WHERE InStage1 = 1
  @ResultTable.StaffName = StaffName)

UPDATE @ResultTable Stage2Count= (
  SELECT COUNT(*) AS count FROM ViewJob
  WHERE InStage2 = 1
  @ResultTable.StaffName = StaffName)

我设法用BCS的一个不同的答案使它工作。但它不允许我使用表变量,所以我必须创建一个临时表

CREATE TABLE #ResultTable
(
  StaffName nvarchar(100),
  Stage1Count int,
  Stage2Count int
)

INSERT INTO #ResultTable (StaffName)
  SELECT StaffName FROM ViewJob
  GROUP BY StaffName

UPDATE #ResultTable SET 
  Stage1Count= (
    SELECT COUNT(*) FROM ViewJob V
    WHERE InStage1 = 1 AND 
        V.StaffName = @ResultTable.StaffName COLLATE Latin1_General_CI_AS
    GROUP BY V.StaffName),
  Stage2Count= (
    SELECT COUNT(*) FROM ViewJob V
    WHERE InStage2 = 1 AND 
        V.StaffName = @ResultTable.StaffName COLLATE Latin1_General_CI_AS
    GROUP BY V.StaffName)

SELECT StaffName, Stage1Count, Stage2Count FROM #ResultTable

DROP TABLE #ResultTable
你提到的“重复”是插入。。。关于重复密钥更新,文档如下:
CREATE TABLE #ResultTable
(
  StaffName nvarchar(100),
  Stage1Count int,
  Stage2Count int
)

INSERT INTO #ResultTable (StaffName)
  SELECT StaffName FROM ViewJob
  GROUP BY StaffName

UPDATE #ResultTable SET 
  Stage1Count= (
    SELECT COUNT(*) FROM ViewJob V
    WHERE InStage1 = 1 AND 
        V.StaffName = @ResultTable.StaffName COLLATE Latin1_General_CI_AS
    GROUP BY V.StaffName),
  Stage2Count= (
    SELECT COUNT(*) FROM ViewJob V
    WHERE InStage2 = 1 AND 
        V.StaffName = @ResultTable.StaffName COLLATE Latin1_General_CI_AS
    GROUP BY V.StaffName)

SELECT StaffName, Stage1Count, Stage2Count FROM #ResultTable

DROP TABLE #ResultTable