我有工作代码,我在下面列出了它,它正是我想要的。但是,我想将其最小化,因此我只调用数据库一次而不是两次。我目前编写的查询仅返回 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
没有用。有两种选择:
- 使用
ExecuteReader
并使用读取 API,或者 - 作弊并获得一个工具来为您完成这一切
关于第二点,坦率地说:这对于 "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 });
然后when
和who
应该被填充。您可能需要考虑是否需要 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/