c# - 传递 sqlparameter 中的值列表,可能是结构化的
问题描述
是否可以使用 SqlDbCommand 和 SqlParameter 在 C# 代码中创建类似的东西?
DECLARE @Users TABLE (ID INT)
INSERT INTO @Users
VALUES (10),(20),(30)
SELECT COUNT(*) FROM @Users
我尝试过这样的事情:
1)数据表创建者:
private static DataTable CreateDataTable(IEnumerable<int> ids)
{
DataTable table = new DataTable();
table.Columns.Add("ID", typeof(int));
foreach (int id in ids)
{
table.Rows.Add(id);
}
return table;
2)添加SqlParameter:
sqlParameters.Add(new SqlParameter()
{
ParameterName = $"@paramname",
SqlDbType = SqlDbType.Structured,
Value = table
});
3) 执行命令(命令是 SELECT COUNT(*) FROM @Users),参数是步骤 2 中的参数列表:
using (SqlCommand cmd = new SqlCommand(command, connection))
{
if (parameters != null)
cmd.Parameters.AddRange(parameters.ToArray());
SqlDataReader reader = cmd.ExecuteReader();
我得到的是:
表类型参数“@Users”必须具有有效的类型名称。
而且我真的没有真正的桌子,所以没有可用的类型,只是希望它是:
声明@Users 表(ID INT)
那可行吗?我想要实现的只是传递值列表,在这种情况下显然是整数列表。
关于标记为重复:
提供的链接不能解决问题,因为它不是缺少类型名问题,而是缺少要使用的类型名。问题是我不能创建任何表,也不能使用任何现有的表在 SqlParameter 中传递 TypeName。
一种可行的解决方案:
CREATE TYPE [dbo].[IntList] AS TABLE(
[Value] [int] NOT NULL
)
然后是SqlParameter:
sqlParameters.Add(new SqlParameter()
{
ParameterName = $"@paramname",
SqlDbType = SqlDbType.Structured,
Value = table,
TypeName = "dbo.IntList"
});
然而,另一个步骤是使用 GarethD 建议的内置类型。我不确定它们是否在 SQL Server 2016 中可用。
解决方案
您需要在 sqlParameter 中添加 TypeName ,与您在 DB 中创建表类型的名称相同。
sqlParameters.Add(new SqlParameter()
{
ParameterName = $"@paramname",
SqlDbType = SqlDbType.Structured,
Value = table,
TypeName = "dbo.MyType";
});
如果您在数据库中没有表类型,那么首先您需要在 SQL 中创建它
CREATE TYPE [dbo].[IntegerList] AS TABLE(
[Data] [int] NOT NULL,
)
GO
然后在您的代码中给出该名称。这将起作用,您确实需要为此在数据库中创建表。
推荐阅读
- python - 使用 Pandas 读取列标题上方和文件底部具有非分隔文本和空行的 csv
- r - 如何将非 HANA ECC 表提取到 R 中?
- java - 为什么在 docker 容器中 java -Xms 会超出可用内存?
- sql - 在数据透视表上添加没有重复 ItemId 的 Featurevalue?
- javascript - 无法使用 Firestore 时间戳(未定义的“toDate”)
- microservices - Service Mesh 不是微服务领域的单一(讽刺)解决方案吗?
- c - 启动时的 INITIAL_JIFFIES 值
- doi - Scopus DOI 在文章检索 API 中不起作用
- javascript - 尝试打开 .js 文件时出现错误 Object
- node.js - nodejs rhea npm for amqp couldn't create subscription queue on address in activemq artemis