1

我有一个SQL Server存储过程,在我的数据库引用表,用户可以手动更新为rent场('Rent1')值。该过程将此租赁价值与另一个表中的租赁字段('Rent2')进行比较。如果Rent1Rent2不同,则Rent2的值更新为Rent1的值......或者至少这是应该发生的情况。更新存储过程不更新

当我执行该存储过程,它运行良好,我收到这些输出消息:

(1 row(s) affected) 


(1 row(s) affected) 

哪个是结果,我期望,因为测试的手段,我已经改变了两个值在Rent1Rent2之间不同。但是当我查询我的更新表时,值保持不变。

这里是我的存储过程:

SET QUOTED_IDENTIFIER ON 
GO 
SET ANSI_NULLS ON 
GO 

ALTER PROCEDURE update_rent 
AS 
DECLARE @flag INT 
SET @flag = (select COUNT(*) from unit_rent left outer join unittype on unittype = scode where rent <> srent) 

WHILE (@flag > 0) 

BEGIN 

IF (select min(rent) from unit_rent 
    left outer join unittype on unittype = scode 
    left outer join property on property.scode = unit_rent.pscode 
    where rent <> srent) <> 
    (select min(srent) from unit_rent 
    left outer join unittype on unittype = scode 
    left outer join property on property.scode = unit_rent.pscode 
    where rent <> srent 
    and rent in (select min(rent) from unit_rent 
    left outer join unittype on unittype = scode 
    left outer join property on property.scode = unit_rent.pscode 
    where rent <> srent)) 

BEGIN 

UPDATE unittype 
SET srent = (select min(rent) from unit_rent 
    left outer join unittype on unittype = scode 
    left outer join property on property.scode = unit_rent.pscode 
    where rent <> srent) 
WHERE unittype.hmy = (select min(hmy) from unittype left outer join unit_rent on unittype = scode where rent <> srent 
     and rent = (select min(rent) from unit_rent left outer join unittype on unittype = scode where rent <> srent)) 

SET @flag = @flag-1; 

END 

END 

GO 
SET QUOTED_IDENTIFIER OFF 
GO 
SET ANSI_NULLS ON 
GO 

任何人都可以看到我可能会错误或者告诉我为什么我的输出信息骗我?或者,也许我可以采取不同的方法?我会很感激任何形式的帮助,谢谢!

UPDATE:只是尝试了不同的方法,同样的结果,只是3个(1 row(s) addected)消息:

ALTER PROCEDURE update_rent 
AS 
DECLARE @tmprent TABLE (hmy INT, rent decimal(11,2)); 
DECLARE @flag INT 
SET @flag = (select COUNT(*) from unit_rent left outer join unittype on unittype = scode where rent <> srent) 

INSERT INTO @tmprent (hmy, rent) values (1, 0.00); 

WHILE (@flag > 0) 

BEGIN 

IF (select min(rent) from unit_rent 
    left outer join unittype on unittype = scode 
    left outer join property on property.scode = unit_rent.pscode 
    where rent <> srent) <> 
    (select min(srent) from unit_rent 
    left outer join unittype on unittype = scode 
    left outer join property on property.scode = unit_rent.pscode 
    where rent <> srent 
    and rent in (select min(rent) from unit_rent 
    left outer join unittype on unittype = scode 
    left outer join property on property.scode = unit_rent.pscode 
    where rent <> srent)) 

BEGIN 

UPDATE @tmprent 
SET rent = (select min(rent) from unit_rent 
    left outer join unittype on unittype = scode 
    left outer join property on property.scode = unit_rent.pscode 
    where rent <> srent) 
WHERE hmy = 1 

UPDATE unittype 
SET srent = (select rent from @tmprent where hmy = 1) 
WHERE unittype.hmy = (select min(hmy) from unittype left outer join unit_rent on unittype = scode where rent <> srent 
     and rent = (select min(rent) from unit_rent left outer join unittype on unittype = scode where rent <> srent)) 

SET @flag = @flag-1; 

END 

END 
+0

如果您在连接表时总是使用别名,这将有所帮助。从这里我们不知道哪些列来自哪个表。 – HABO 2013-04-24 17:22:25

+0

但是,我可以认为,除非您处理空值,否则包含空值的字段可能无法正常工作。 – HLGEM 2013-04-24 17:57:07

回答

1

我不知道我的回答能有多大帮助别人,但它可以在关闭的机会,我会在这里包括它..

所以我unit_rent表在我的SP被引用,是由我创建,并从我的unittype表(SP中引用)填充数据。当我填充表unit_rent时,我抓取了我的unittype表中的所有行。这是我犯了我的错误。 unittype表包含与特定单元类型关联的多个单元,因此无论何时使用我的存储过程更新一行,与该单元类型关联的所有其他单元都将变为!=,以达到我更改的租金数量。所以我重新填充我的unit_rent表,只有不同的单位类型,我的问题解决了。

非常愚蠢的错误,但我不希望它没有回应的机会,它可能会帮助别人。

@granadaCoder - 谢谢,再次为您的帮助。第二次你非常彻底地帮助我。

1

在故障修复世界:

更新之前将一个select语句,看看如果有任何匹配

/* 
UPDATE unittype 
SET srent = (select min(rent) from unit_rent 
    left outer join unittype on unittype = scode 
    left outer join property on property.scode = unit_rent.pscode 
    where rent <> srent) 
*/ 
select * from unittype 
WHERE unittype.hmy = (select min(hmy) from unittype left outer join unit_rent on unittype = scode where rent <> srent 
     and rent = (select min(rent) from unit_rent left outer join unittype on unittype = scode where rent <> srent)) 

OR

declare @myCountCheck 
select @myCountCheck = 
(select count(*) 
from unittype 
    WHERE unittype.hmy = (select min(hmy) from unittype left outer join unit_rent on unittype = scode where rent <> srent 
      and rent = (select min(rent) from unit_rent left outer join unittype on unittype = scode where rent <> srent)) 
) 

if (@myCountCheck < 1) 
BEGIN 
    print 'No Row Match !!!' 
END 

编辑---------------------------------------

如果你真的想看看发生了什么,然后编写了一些“输出”审计...... 这样,你可以捕捉什么在INSERT/UPDATE语句发生

http://granadacoder.wordpress.com/2008/12/10/sqlserver20052008-output-clause-in-insertupdatedelete-statements/

这里是示例代码:在插入/更新

SQLSERVER2005/2008 // OUTPUT子句/ DELETE语句

这些类型的样品都是在网络上的地方,但这里是我原来的例子对我相信这是更好的清晰度。

原来的例子(S)为: http://blogs.msdn.com/sqltips/archive/2005/06/13/OUTPUT-clause.aspx

create table PrimaryHolderTable (i int identity (1001,2) not null primary key, j int not null unique) 
create table #OutputResultsHolder (i int not null, j int not null) 

insert into PrimaryHolderTable (j) 
output inserted.i, inserted.j into #OutputResultsHolder 
select top 10 o.object_id from sys.objects as o order by o.object_id desc –<< from sys.objects is there just to provide some rows 


select * from #OutputResultsHolder 
drop table #OutputResultsHolder, PrimaryHolderTable; 

go 



create table dbo.EmployeeTable (EmpKey int identity(1001,2) , EmpAge int not null); 
create table dbo.AuditTable (EntityKey int not null default -1 , OldValue int null, NewValue int null , Tag varchar(64) ); 

insert into dbo.EmployeeTable (EmpAge) 
output inserted.EmpKey , null , inserted.EmpAge , ‘Employee Inserted’ into dbo.AuditTable (EntityKey , OldValue , NewValue , Tag) 
values(18); 

insert into dbo.EmployeeTable (EmpAge) 
output inserted.EmpKey , null , inserted.EmpAge , ‘Employee Inserted’ into dbo.AuditTable (EntityKey , OldValue , NewValue , Tag) 
values(20); 

insert into dbo.EmployeeTable (EmpAge) 
output inserted.EmpKey , null , inserted.EmpAge , ‘Employee Inserted’ into dbo.AuditTable (EntityKey , OldValue , NewValue , Tag) 
values(22); 


update dbo.EmployeeTable 
    set EmpAge = EmpAge + 1 
output inserted.EmpKey , deleted.EmpAge, inserted.EmpAge , ‘Employee Updated’ into dbo.AuditTable (EntityKey , OldValue , NewValue , Tag) 
where EmpAge <=20; 

delete from dbo.EmployeeTable 
output deleted.EmpKey , deleted.EmpAge, NULL , ‘Employee Deleted’ into dbo.AuditTable (EntityKey , OldValue , NewValue , Tag) 
where EmpAge > 0;–Test multi rows 

select * from dbo.EmployeeTable;–<<will be empty at this point 
select * from dbo.AuditTable; 

drop table dbo.EmployeeTable, dbo.AuditTable; 
go 
+0

对不起。如果有什么符合什么? – reubenCanowski 2013-04-24 17:26:30

+0

您正在使用WHERE子句运行UPDATE。好。那么,必须从WHERE子句或需要更新的任何东西“匹配”。通过在UPDATE之前立即放置一个SELECT语句(并假设没有其他人在同一时间访问同一数据),您将看到是否有任何内容需要实际更新。 – granadaCoder 2013-04-24 17:32:32

+0

我想我明白了。如果我从where子句运行查询,我会收到一个结果,这是我期望的结果。 'hmy'是表主键,因此每个'hmy'只有一行。所以在这种情况下,我的更新应该工作,或者至少我会想.. – reubenCanowski 2013-04-24 17:49:52