Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/73.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/9/loops/2.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 使用循环中的select设置变量的最佳实践_Sql_Loops_Variables - Fatal编程技术网

Sql 使用循环中的select设置变量的最佳实践

Sql 使用循环中的select设置变量的最佳实践,sql,loops,variables,Sql,Loops,Variables,我目前正在尝试修复一个存储过程中的错误,每个人偶尔一次,每个月一次,我会发现一个子记录由于两个系统之间的同步错误而出现在错误的父帐户上。看看代码,我相信我已经找到了问题所在。我看到的问题是,在循环中,每个子记录的父帐户都使用select语句设置,如果查询不返回任何结果,用于分配accountid和accountname的变量将保留上一个循环周期中的信息。至于为什么循环无法找到相关记录,这完全是另一个问题,也是我尚未解决的一个间歇性问题。考虑到这一点,我认为这种设置变量的方法不是一个好主意!是否有

我目前正在尝试修复一个存储过程中的错误,每个人偶尔一次,每个月一次,我会发现一个子记录由于两个系统之间的同步错误而出现在错误的父帐户上。看看代码,我相信我已经找到了问题所在。我看到的问题是,在循环中,每个子记录的父帐户都使用select语句设置,如果查询不返回任何结果,用于分配accountid和accountname的变量将保留上一个循环周期中的信息。至于为什么循环无法找到相关记录,这完全是另一个问题,也是我尚未解决的一个间歇性问题。考虑到这一点,我认为这种设置变量的方法不是一个好主意!是否有任何方法可以验证或确认变量设置是否正确,如果没有,则不考虑处理该记录?非常感谢任何帮助、建议或智慧之言

下面是一个代码示例,它在循环中运行以设置变量@id是将在循环周期中处理的当前子对象id

Select  @AccountId = t1.AccountId,
        @Account = t1.AccountName
From    Accounts t1
Inner Join ChildTable t2 on t1.ID = t2.ID
Where   t2.Id = @Id

谢谢大家的意见。每个人都提供了宝贵的反馈,我很抱歉没有提供更多的脚本,这将允许更精确的解决方案。我决定使用的是检查变量赋值中使用的表,确认帐户数据是否存在,并且只将这些子记录添加到集合中以进行循环。仍然存在一个问题,即数据从添加到集合的点a变为分配变量的点b,但我将设法控制这些表,因为这些表不是非常活跃的,而且我在大多数情况下只能访问它们。再次感谢

如果您的输出有多行,sql会将最后一个值分配给变量。因此,我建议改用表

insert into @table(
@accountid,Account)
Select  t1.AccountId,
         t1.AccountName
From    Accounts t1
Inner Join ChildTable t2 on t1.ID = t2.ID
Where   t2.Id = @Id

如果您的输出有多行,sql会将最后一个值分配给变量。因此,我建议改用表

insert into @table(
@accountid,Account)
Select  t1.AccountId,
         t1.AccountName
From    Accounts t1
Inner Join ChildTable t2 on t1.ID = t2.ID
Where   t2.Id = @Id

我假设子表可以返回多行 所以TOP1应该更有效

@idFound = null;
Select  top 1
        @AccountId = t1.AccountId,
        @Account   = t1.AccountName 
        @idFound   = t1.Id
From    Accounts t1
Inner Join ChildTable t2 on t2.Id = t1.Id
                        and t2.Id = @Id

if(@idFound <> @Id)  -- did not find record

若@AccountId和/或@Account从来都不是空的,你们可以先分配一个空值,然后检查空值,我假设子表可以返回多行 所以TOP1应该更有效

@idFound = null;
Select  top 1
        @AccountId = t1.AccountId,
        @Account   = t1.AccountName 
        @idFound   = t1.Id
From    Accounts t1
Inner Join ChildTable t2 on t2.Id = t1.Id
                        and t2.Id = @Id

if(@idFound <> @Id)  -- did not find record

如果@AccountId和/或@Account从不为空,您可以先分配一个空值,然后检查空值

最有可能的问题是查询中的结果集为空。对此进行测试的最简单方法是验证语句行计数。您没有指定您的SQL风格,但是大多数(如果不是所有的话)引擎都有一些测试行数的方法,例如在SQL Server中


只需使用if语句验证查询是否影响了1行…

最可能的问题是查询中的结果集为空。对此进行测试的最简单方法是验证语句行计数。您没有指定您的SQL风格,但是大多数(如果不是所有的话)引擎都有一些测试行数的方法,例如在SQL Server中


只需使用if语句验证查询影响的1行…

如果提供围绕此查询的代码:循环,以及可能正在循环的另一个查询,您将获得更好的答案。如果提供围绕此查询的代码:循环,可能还有另一个循环查询。但我认为t1是父级,只是重复相同的值。但我认为t1是父级,只是重复相同的值。空结果集正是问题所在。在变量赋值时添加任何逻辑都会遇到问题,就像在这条语句之前一样,会调用一个存储过程,在遗留系统中创建一个id,甚至将NULL赋值给accountId,也只会在遗留系统中产生一个孤立的记录。这似乎是由于同步程序希望在创建子对象所属的帐户之前插入该子对象造成的。在将帐户添加到要循环通过的子列表之前,我将简单地检查以确保帐户在两个表中都有表示。空的结果集正是问题所在。在变量赋值时添加任何逻辑都会遇到问题,就像在这条语句之前一样,会调用一个存储过程,在遗留系统中创建一个id,甚至将NULL赋值给accountId,也只会在遗留系统中产生一个孤立的记录。这似乎是由于同步程序希望在创建子对象所属的帐户之前插入该子对象造成的。在将帐户添加到要循环通过的子列表之前,我将简单地检查以确保该帐户在两个表中都有表示。