Sql 计算条件未返回正确结果的地方

Sql count where condition is not returning correct result

我有一个 Cars table(sql 服务器)用于我的停车管理应用程序,其中每条汽车记录都将在签入时由应用程序自动分配唯一的插槽。

我正在努力实施它。这个概念是我将在变量 "slotx" 中保留“1”值,然后使用查询确定 table 的 'Slot' 列中是否已经存在相同的值。如果它已经存在,则 "slotx" 值递增 1,并再次查询数据库以检查 table 中是否存在下一个数字,即“2”,此过程一直持续到 "slotx"值与 Cars table 中的任何记录都不匹配,此时(当 table 中不存在相同值时)此值 "slotx" 被分配给 'Slot' 列table 来车。

但是代码不工作,我尝试使用断点找出问题并希望正确地发现以下查询总是 returning 值 '1' 即使没有任何匹配的记录,因此导致无限循环。 "Select COUNT(Slot) From Cars Where Slot= @slot;"

代码:

//variables/member declaration
public static int slotx = 1;
private static string searchcarslotauto = "Select COUNT(Slot) From Cars Where Slot= @slot;";

//sqlcommand setup
SqlCommand checkreservedcar = new SqlCommand(searchcarslotauto, con);
checkreservedcar.Parameters.AddWithValue("@slot", slotx);

//CheckIn related
con.Open();
Loop: int isreservereader = (int)checkreservedcar.ExecuteScalar();
if (isreservereader != 0)
{
     slotx++;
     goto Loop;
}
else
{
     insertcarcmd.ExecuteNonQuery();
}
con.Close();

示例输入数据(Table 汽车):- 序列号:1 注册号:JGI-12-5888 DateTimeIn:3/5/2018 9:52:00 AM 插槽:1 已订阅:False;

预期结果:如果变量 "slotx" 的值与 'Slot' 列的任何记录值都不匹配,则查询应为 return '0' 值,但事实并非如此。吨。

抱歉,这个问题太长了,我无法简单地解释一下。请有人指导我!

已尝试替代查询无济于事。 Count based on condition in SQL Server

您的代码中的问题很可能出在调用 AddWithValue 中。您在命令中添加了一个初始值为 slotx 的参数,我猜是 1。然后在你的 "Loop" 中你不断更新 slotx 的值,但这只是更新那个静态变量,而不是你存储在命令参数中的值。请参阅 Tim Schmelter 对 this question 的已接受答案,了解为每次循环迭代更新该参数的方法。另一种方法是保留 AddWithValue 返回的 SqlParameter 对象并更新该对象。

一些额外的评论:
- 遵循 dee zg 在该问题的另一个答案中的建议 并仔细查看使用 sql 交易以确保同一时段不会分配给多辆汽车。
- 不要使用 goto 标签,当它不做任何 for/while 循环可以完美完成的事情时更是如此
- 考虑使用 Numbers table,这样你就可以在你的 SQL 查询中使用 WHERE NOT EXISTS 并只用一个查询解决问题,根本不需要循环。 Here link 到 Aaron Bertrand 的一篇文章中谈论那些 table。

您的循环代码可能如下所示:

con.Open();
while ((int)checkreservedcar.ExecuteScalar() != 0)
{
     slotx++;
     checkreservedcar .Parameters["@slot"].Value = slotx;
}
insertcarcmd.ExecuteNonQuery();
con.Close();

请停止你正在做的事情,忘记你到目前为止为这个特定问题所做的一切,并跳到学习一些关于数据库规范化和身份的知识。

简而言之,考虑这种情况:

  1. 您的应用程序收到插槽请求
  2. 它 ping SQL 服务器并获取 2 空闲的信息
  3. 另一个请求到达应用程序
  4. (第一个请求尚未写入)应用程序再次 ping SQL 服务器并获取插槽 2 空闲的信息
  5. 两个插槽请求都是为插槽 2 写入的 - 实际上,您丢失了一条记录

底线:让应用程序检查身份是一个非常糟糕的主意。这必须以事务方式或使用 IDENTITY 列来完成(现在对你来说更好)。