DataContext.ExecuteQuery <TEntity>和Null值

Ber*_*tie 4 c# linq-to-sql


所以我的问题是这个.当使用Data Context ExecuteQuery(字符串查询,params object []参数)(这里)时,我无法以任何形式或形式传递null.启动此操作的参数是SQL nvarchar参数,需要允许空值.

我在stackoverflow上阅读了这篇文章,其中"使用DBNull.Value"标记为答案 - 所以我尝试了,没有任何东西(所以想知道如果它不起作用的答案,如果它不起作用??!).

这是我试图运行的示例代码(注意,这只是为了测试这个概念):

var db = new Test1DataContext(Properties.Settings.Default.TestConnectionString);
var query = "EXEC UpInsertTest4 {0}, {1}";

// Works fine
var list1 = new List<object> { 1, "1" };
db.ExecuteQuery<UpInsertTest4Result>(query, list1.ToArray());

// Doesn't work
var list2 = new List<object> { 1, DBNull.Value };
db.ExecuteQuery<UpInsertTest4Result>(query, list2.ToArray());
Run Code Online (Sandbox Code Playgroud)

以下是我收到的各种错误:

null                : A query parameter cannot be of type 'System.Object'.
default(string)     : A query parameter cannot be of type 'System.Object'.
DBNull.Value        : Unexpected type code: DBNull (which give this as a stack trrace)
Run Code Online (Sandbox Code Playgroud)

at System.Data.Linq.SqlClient.SqlTypeSystem.Sql2005Provider.From(Type type, Nullable`1 size)
   at System.Data.Linq.SqlClient.SqlTypeSystem.Sql2008Provider.From(Type type, Nullable`1 size)
   at System.Data.Linq.SqlClient.SqlTypeSystem.ProviderBase.From(Type type)
   at System.Data.Linq.SqlClient.SqlTypeSystem.ProviderBase.From(Object o)
   at System.Data.Linq.SqlClient.SqlFactory.ValueFromObject(Object value, Type clrType, Boolean isClientSpecified, Expression sourceExpression)
   at System.Data.Linq.SqlClient.QueryConverter.VisitConstant(ConstantExpression cons)
   at System.Data.Linq.SqlClient.QueryConverter.VisitInner(Expression node)
   at System.Data.Linq.SqlClient.QueryConverter.VisitExpression(Expression exp)
   at System.Data.Linq.SqlClient.QueryConverter.VisitUserQuery(String query, Expression[] arguments, Type resultType)
   at System.Data.Linq.SqlClient.QueryConverter.VisitMethodCall(MethodCallExpression mc)
   at System.Data.Linq.SqlClient.QueryConverter.VisitInner(Expression node)
   at System.Data.Linq.SqlClient.QueryConverter.ConvertOuter(Expression node)
   at System.Data.Linq.SqlClient.SqlProvider.BuildQuery(Expression query, SqlNodeAnnotations annotations)
   at System.Data.Linq.SqlClient.SqlProvider.System.Data.Linq.Provider.IProvider.Execute(Expression query)
   at System.Data.Linq.DataContext.ExecuteMethodCall(Object instance, MethodInfo methodInfo, Object[] parameters)
   at System.Data.Linq.DataContext.ExecuteQuery[TResult](String query, Object[] parameters)
   at ConsoleApplication1.Program.Main(String[] args) in E:\TestBed\Testbed\ConsoleApplication1\Program.cs:line 36
   at System.AppDomain._nExecuteAssembly(RuntimeAssembly assembly, String[] args)
   at System.AppDomain.ExecuteAssembly(String assemblyFile, Evidence assemblySecurity, String[] args)
   at Microsoft.VisualStudio.HostingProcess.HostProc.RunUsersAssembly()
   at System.Threading.ThreadHelper.ThreadStart_Context(Object state)
   at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean ignoreSyncCtx)
   at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state)
   at System.Threading.ThreadHelper.ThreadStart()


从我读过的内容来看,我可以用这个来对抗一场失败的战斗!这是我最后的尝试!

非常感谢,
克里斯.

Ari*_*ion 5

你可以这样做:

db.ExecuteQuery<UpInsertTest4Result>(string.Format(query,1,"null"));
Run Code Online (Sandbox Code Playgroud)

更新

是的,我已经测试了解决方案.它不会包含@p1=N'null'.因为我直接使用sql作为字符串.所以概念教授.

存储程序:

CREATE PROCEDURE testas
@test1 INT,  
@test2 INT 
AS
SELECT 1 test 
Run Code Online (Sandbox Code Playgroud)

用于测试输出的类:

public class testout
{
    public int test { get; set; }
}
Run Code Online (Sandbox Code Playgroud)

使用db上下文查询Linq:

var query="exec testas {0}, {1}";
db.ExecuteQuery<testout>(string.Format(query,"0","null"));
Run Code Online (Sandbox Code Playgroud)

如果你查看linqpad,sql输出是这样的:

exec testas 0, null
Run Code Online (Sandbox Code Playgroud)

字符串格式只是改变字符串.这与写这个是一样的:

db.ExecuteQuery<testout>("exec testas 0, null")
Run Code Online (Sandbox Code Playgroud)