c# - 如何使用 C# 从 SqlConnection 返回多个结果

标签 c# sql

我有工作代码,我在下面列出了它,它正是我想要的。但是,我想将其最小化,因此我只调用数据库一次而不是两次。我目前编写的查询仅返回 1 条包含 1 列的记录。

此列返回我在代码中使用的日期。问题是我还需要带回用户。我基本上通过使用相同的查询来实现这一点,但让它带回用户而不是日期。

大问题: 我有用于返回两条信息的查询,但是,我不确定如何将这些信息返回到我的代码中使用?当查询返回不止一列时。 旁注新查询仍然只返回一条记录,但有 2 列。

工作代码: 我将在最后一个选择语句中添加“UpdatedBy”以添加第二列。

SqlConnection conn = new SqlConnection(@"Data Source=(localdb)\......");
                SqlCommand cmd = conn.CreateCommand();

                string updatedOn;
                conn.Open();
                cmd.CommandText = ("USE CORNERSTONE DECLARE @SID int SET @SID = " + SupplierId + "; "  +
                "with MaxDate as " +
                "(select UpdatedOn, UpdatedBy, SupplierId from CORNERSTONE.Suppliers.Supplier where SupplierId = @SID " +
                "UNION " +
                "select UpdatedOn, UpdatedBy, SupplierId from Suppliers.CompanyLocation where SupplierId = @SID " +
                "UNION " +
                "select UpdatedOn, UpdatedBy, SupplierId from Suppliers.AssignedContact where SupplierId = @SID) " +
                "select UpdatedOn " +
                "from MaxDate " +
                "where UpdatedOn = (Select MAX(UpdatedOn) from MaxDate)");

                updatedOn = cmd.ExecuteScalar().ToString();
                DateTime ParsedDateTime = DateTime.Parse(updatedOn);
                AuditUpdatedOn = ParsedDateTime;

                conn.Close();

最佳答案

我假设您想要 UpdatedBy来自查询;如果是这样,这应该只是:

cmd.CommandText = @"
with MaxDate as (
    select UpdatedOn, UpdatedBy from CORNERSTONE.Suppliers.Supplier where SupplierId = @SID
    union select UpdatedOn, UpdatedBy from Suppliers.CompanyLocation where SupplierId = @SID
    union select UpdatedOn, UpdatedBy from Suppliers.AssignedContact where SupplierId = @SID
)
select top 1 UpdatedOn, UpdatedBy
from MaxDate 
where UpdatedOn = (Select MAX(UpdatedOn) from MaxDate)
";

但是,问题来自于您现在有两列需要阅读的事实,因此 ExecuteScalar没有用。有两种选择:

  1. 使用ExecuteReader并使用读取 API,或者
  2. 作弊并获得一个工具来为您完成这一切

关于第二点,坦率地说:这对于 "Dapper" 来说是一个完美的场景。 :

(var when, var who) = conn.QuerySingle<(DateTime, string)>(@"
with MaxDate as (
    select UpdatedOn, UpdatedBy from CORNERSTONE.Suppliers.Supplier where SupplierId = @SID
    union select UpdatedOn, UpdatedBy from Suppliers.CompanyLocation where SupplierId = @SID
    union select UpdatedOn, UpdatedBy from Suppliers.AssignedContact where SupplierId = @SID
)
select top 1 UpdatedOn, UpdatedBy
from MaxDate 
where UpdatedOn = (Select MAX(UpdatedOn) from MaxDate)
", new { SID = SupplierId });

然后whenwho应该被填充。您可能需要考虑是否需要 QuerySingleOrDefault如果没有行。

通常,当您使用 Query[First/Single/etc]<T> 时与 Dapper 一起,T使用列名称进行映射(以填充对象模型),但它会检测值元组( (DateTime, string) 是值元组)并按位置处理它们。


如果您必须使用原始 ADO.NET - 类似于以下内容:

using (var cmd = conn.CreateCommand())
{
    cmd.CommandText = @"
with MaxDate as (
select UpdatedOn, UpdatedBy from CORNERSTONE.Suppliers.Supplier where SupplierId = @SID
union select UpdatedOn, UpdatedBy from Suppliers.CompanyLocation where SupplierId = @SID
union select UpdatedOn, UpdatedBy from Suppliers.AssignedContact where SupplierId = @SID
);
select top 1 UpdatedOn, UpdatedBy
from MaxDate 
where UpdatedOn = (Select MAX(UpdatedOn) from MaxDate)
";
    cmd.CommandType = CommandType.Text;
    var p = cmd.CreateParameter();
    p.ParameterName = "@SID";
    p.Value = SupplierId;
    p.DbType = DbType.Int32;
    cmd.Parameters.Add(p);

    using (var reader = cmd.ExecuteReader())
    {
        if (reader.Read())
        {
            var who = reader.GetDateTime(0);
            var when = reader.GetString(1);
            // *** HERE *** we now know the answers
        }
        else
        {
            // what to do if we don't get anyone?
        }
        do // need to consume entire TDS to
        { // make sure we see errors
            while (reader.Read()) { }
        } while (reader.NextResult());
    }
}

关于c# - 如何使用 C# 从 SqlConnection 返回多个结果,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62173441/

相关文章:

SQL:从第 1 列中提取不同的值,并使用第 2 列中的所有值

mysql select 基于两个条件

c# - 无法运行 WCF https Web 服务

c# - 我在哪里放置最后添加记录的突出显示代码?

c# - 在 Windows 7 上使用 .NET 以编程方式创建/销毁网桥

sql - 为每个导致效率问题的键找到最小值

sql - 如何根据电话号码找到长途费率的最佳匹配?

c# - `Any()` 是否强制执行 linq?

c# - 如何在 C# 中取消设置变量?

sql - 选择所有列,但也可以按不同的列和最旧的日期选择