简体   繁体   English

将 null 分配给 SqlParameter

[英]Assign null to a SqlParameter

The following code gives an error - "No implicit conversion from DBnull to int."下面的代码给出了一个错误——“没有从 DBnull 到 int 的隐式转换”。

SqlParameter[] parameters = new SqlParameter[1];    
SqlParameter planIndexParameter = new SqlParameter("@AgeIndex", SqlDbType.Int);
planIndexParameter.Value = (AgeItem.AgeIndex== null) ? DBNull.Value : AgeItem.AgeIndex;
parameters[0] = planIndexParameter;

The problem is that the ?: operator cannot determine the return type because you are either returning an int value or a DBNull type value, which are not compatible.问题是?:运算符无法确定返回类型,因为您返回的是不兼容的int值或 DBNull 类型的值。

You can of course cast the instance of AgeIndex to be type object which would satisfy the ?: requirement.您当然可以将 AgeIndex 的实例转换为满足?:要求的类型object

You can use the ??你可以使用?? null-coalescing operator as follows空合并运算符如下

SqlParameter[] parameters = new SqlParameter[1];     
SqlParameter planIndexParameter = new SqlParameter("@AgeIndex", SqlDbType.Int);
planIndexParameter.Value = (object)AgeItem.AgeIndex ?? DBNull.Value;
parameters[0] = planIndexParameter; 

Here is a quote from the MSDN documentation for the ?: operator that explains the problem这是MSDN 文档中对?:运算符的引用,它解释了问题

Either the type of first_expression and second_expression must be the same, or an implicit conversion must exist from one type to the other. first_expression 和 second_expression 的类型必须相同,或者必须存在从一种类型到另一种类型的隐式转换。

The accepted answer suggests making use of a cast.公认的答案建议使用演员表。 However, most of the SQL types have a special Null field which can be used to avoid this cast.但是,大多数 SQL 类型都有一个特殊的 Null 字段,可以用来避免这种强制转换。

For example, SqlInt32.Null "Represents a DBNull that can be assigned to this instance of the SqlInt32 class."例如, SqlInt32.Null “表示可以分配给此 SqlInt32 类实例的 DBNull。”

int? example = null;
object exampleCast = (object) example ?? DBNull.Value;
object exampleNoCast = example ?? SqlInt32.Null;

You need pass DBNull.Value as a null parameter within SQLCommand, unless a default value is specified within stored procedure (if you are using stored procedure).您需要在 SQLCommand 中将DBNull.Value作为 null 参数传递,除非在存储过程中指定了默认值(如果您使用的是存储过程)。 The best approach is to assign DBNull.Value for any missing parameter before query execution, and following foreach will do the job.最好的方法是在查询执行之前为任何缺少的参数分配DBNull.Value ,然后 foreach 将完成这项工作。

foreach (SqlParameter parameter in sqlCmd.Parameters)
{
    if (parameter.Value == null)
    {
        parameter.Value = DBNull.Value;
    }
}

Otherwise change this line:否则更改此行:

planIndexParameter.Value = (AgeItem.AgeIndex== null) ? DBNull.Value : AgeItem.AgeIndex;

As follows:如下:

if (AgeItem.AgeIndex== null)
    planIndexParameter.Value = DBNull.Value;
else
    planIndexParameter.Value = AgeItem.AgeIndex;

Because you can't use different type of values in conditional statement, as DBNull and int are different from each other.因为您不能在条件语句中使用不同类型的值,因为 DBNull 和 int 彼此不同。 Hope this will help.希望这会有所帮助。

用一行代码,试试这个:

var piParameter = new SqlParameter("@AgeIndex", AgeItem.AgeIndex ?? (object)DBNull.Value);

If you use the conditional(ternary) operator the compiler needs an implicit conversion between both types, otherwise you get an exception.如果使用条件(三元)运算符,编译器需要在两种类型之间进行隐式转换,否则会出现异常。

So you could fix it by casting one of both to System.Object :因此,您可以通过将两者之一转换为System.Object来修复它:

planIndexParameter.Value = (AgeItem.AgeIndex== null) ? DBNull.Value : (object) AgeItem.AgeIndex;

But since the result is not really pretty and you always have to remember this casting, you could use such an extension method instead:但是由于结果不是很漂亮,而且你总是要记住这个转换,你可以使用这样的扩展方法:

public static object GetDBNullOrValue<T>(this T val)
{
    bool isDbNull = true;
    Type t = typeof(T);

    if (Nullable.GetUnderlyingType(t) != null)
        isDbNull = EqualityComparer<T>.Default.Equals(default(T), val);
    else if (t.IsValueType)
        isDbNull = false;
    else
        isDbNull = val == null;

    return isDbNull ? DBNull.Value : (object) val;
}

Then you can use this concise code:然后你可以使用这个简洁的代码:

planIndexParameter.Value = AgeItem.AgeIndex.GetDBNullOrValue();

Try this:尝试这个:

SqlParameter[] parameters = new SqlParameter[1];    
SqlParameter planIndexParameter = new SqlParameter("@AgeIndex", SqlDbType.Int);

planIndexParameter.IsNullable = true; // Add this line

planIndexParameter.Value = (AgeItem.AgeIndex== null) ? DBNull.Value : AgeItem.AgeIndex== ;
parameters[0] = planIndexParameter;
if (_id_categoria_padre > 0)
{
    objComando.Parameters.Add("id_categoria_padre", SqlDbType.Int).Value = _id_categoria_padre;
}
else
{
    objComando.Parameters.Add("id_categoria_padre", DBNull.Value).Value = DBNull.Value;
}

Consider using the Nullable(T) structure available.考虑使用可用的 Nullable(T) 结构。 It'll let you only set values if you have them, and your SQL Command objects will recognize the nullable value and process accordingly with no hassle on your end.它只会让你设置值,如果你有它们,你的 SQL Command 对象将识别可以为空的值并相应地进行处理,而不会有任何麻烦。

A simple extension method for this would be:一个简单的扩展方法是:

    public static void AddParameter(this SqlCommand sqlCommand, string parameterName, 
        SqlDbType sqlDbType, object item)
    {
        sqlCommand.Parameters.Add(parameterName, sqlDbType).Value = item ?? DBNull.Value;
    }

I use a simple method with a null check.我使用带有空检查的简单方法。

    public SqlParameter GetNullableParameter(string parameterName, object value)
    {
        if (value != null)
        {
            return new SqlParameter(parameterName, value);
        }
        else
        {
            return new SqlParameter(parameterName, DBNull.Value);
        }
    }

Try this:尝试这个:

if (AgeItem.AgeIndex != null)
{
   SqlParameter[] parameters = new SqlParameter[1];
   SqlParameter planIndexParameter = new SqlParameter("@AgeIndex", SqlDbType.Int);
   planIndexParameter.Value = AgeItem.AgeIndex;
   parameters[0] = planIndexParameter;
}

In other words, if the parameter is null just don't send it to your stored proc (assuming, of course, that the stored proc accepts null parameters which is implicit in your question).换句话说,如果参数为空,则不要将其发送到您的存储过程(当然,假设存储过程接受您的问题中隐含的空参数)。

In my opinion the better way is to do this with the Parameters property of the SqlCommand class:在我看来,更好的方法是使用SqlCommand类的Parameters属性来做到这一点:

public static void AddCommandParameter(SqlCommand myCommand)
{
    myCommand.Parameters.AddWithValue(
        "@AgeIndex",
        (AgeItem.AgeIndex== null) ? DBNull.Value : AgeItem.AgeIndex);
}

My code, working in real project Look the ternary operator beafore make the sqlparameter this is the best way for me, withou problems:我的代码,在实际项目中工作 在制作 sqlparameter 之前查看三元运算符,这对我来说是最好的方法,没有问题:

    public bool Key_AddExisting
    (
          string clave
        , int? idHito_FileServer
        , int? idTipoDocumental_Almacen
        , string tipoExp_CHJ
        , int idTipoExp_Verti2
        , int idMov_Verti2
    )
    {
        List<SqlParameter> pars = new List<SqlParameter>()
        {
              new SqlParameter { ParameterName = "@Clave", Value = clave }
    LOOK -> , idHito_FileServer == null ? new SqlParameter { ParameterName = "@IdHito_FileServer", Value = DBNull.Value } : new SqlParameter { ParameterName = "@IdHito_FileServer", Value = idHito_FileServer }
    LOOK -> , idTipoDocumental_Almacen == null ? new SqlParameter { ParameterName = "@IdTipoDocumental_Almacen", Value = DBNull.Value } : new SqlParameter { ParameterName = "@IdTipoDocumental_Almacen", Value = idTipoDocumental_Almacen }
            , new SqlParameter { ParameterName = "@TipoExp_CHJ", Value = tipoExp_CHJ }
            , new SqlParameter { ParameterName = "@IdTipoExp_Verti2", Value = idTipoExp_Verti2 }
            , new SqlParameter { ParameterName = "@IdMov_Verti2", Value = idMov_Verti2 }
        };

        string sql = "INSERT INTO [dbo].[Enlaces_ClavesCHJ_MovimientosVerti2] " +
            "( " +
            "  [Clave] " +
            ", [IdHito_FileServer] " +
            ", [IdTipoDocumental_Almacen] " +
            ", [TipoExp_CHJ] " +
            ", [IdTipoExp_Verti2] " +
            ", [IdMov_Verti2] " +
            ") " +
            "VALUES" +
            "( " +
            "  @Clave" +
            ", @IdHito_FileServer" +
            ", @IdTipoDocumental_Almacen" +
            ", @TipoExp_CHJ" +
            ", @IdTipoExp_Verti2" +
            ", @IdMov_Verti2" +
            ")";

        return DbBasic.ExecNonQuery(ref this.conn, sql, pars);
    }

you can do something like this.你可以做这样的事情。 Here startDate and endDate are nullable datetime param这里startDateendDate是可为的日期时间参数

var Statistics= db.Database.SqlQuery<ViewStatistics>("YourStoreProcedure_Or_sqlQuery  @startDate,@endDate",
        new SqlParameter("startDate", startDate?? (object)DBNull.Value),
        new SqlParameter("endDate", endDate?? (object)DBNull.Value)
        ).ToList();

try something like this:尝试这样的事情:

if (_id_categoria_padre > 0)
{
    objComando.Parameters.Add("id_categoria_padre", SqlDbType.Int).Value = _id_categoria_padre;
}
else
{
    objComando.Parameters.Add("id_categoria_padre", DBNull.Value).Value = DBNull.Value;
}
int? nullableValue = null;
object nullableValueDB
{
   get{
       if(nullableValue==null)
          return DBNull.Value;
       else
          return (int)nullableValue;
   }
}

I'm solving like that.我就是这样解决的。

if (AgeItem.AgeIndex== null)  
    cmd.Parameters.Add(new SqlParameter("ParaMeterName", SqlDbType.DateTime).Value = DBNull);  
else  
    cmd.Parameters.Add(new SqlParameter("ParaMeterName", SqlDbType.DateTime).Value = AgeItem.AgeIndex);

This is what I simply do...这就是我所做的...

        var PhoneParam = new SqlParameter("@Phone", DBNull.Value);
        if (user.User_Info_Phone != null)
        {
            PhoneParam.SqlValue = user.User_Info_Phone;
        }

        return this.Database.SqlQuery<CustLogonDM>("UpdateUserInfo @UserName, @NameLast, @NameMiddle, @NameFirst, @Address, @City, @State, @PostalCode, @Phone",
            UserNameParam, NameLastParam, NameMiddleParam, NameFirstParam, AddressParam, CityParam, StateParam, PostalParam, PhoneParam).Single();
            dynamic psd = DBNull.Value;

            if (schedule.pushScheduleDate > DateTime.MinValue)
            {
                psd = schedule.pushScheduleDate;
            }


            sql.DBController.RunGeneralStoredProcedureNonQuery("SchedulePush",
                     new string[] { "@PushScheduleDate"},
                     new object[] { psd }, 10, "PushCenter");
sqlCom.Parameters.Add(new SqlParameter("@qavCode", SqlDbType.Char, 11)).Value = (object)(string.IsNullOrEmpty(rf.Request.QavCode) ? null : rf.Request.QavCode) ?? DBNull.Value;

To improve the usage of the null-coalescing operator ??改进空合并运算符的使用 ?? to manage empty strings in my example I mixed the regular ternary ?: to the null-coalescing operator ??.为了在我的示例中管理空字符串,我将常规三元 ?: 与空合并运算符 ?? 混合在一起。 Hope my suggestion is useful.希望我的建议有用。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何在不检查null或0的情况下为sqlparameter NULL值赋值? - How to assign a value to sqlparameter NULL values without checking for null or 0? 将null作为SQLParameter DateTime值传递 - Passing null as SQLParameter DateTime value 将NULL值分配给SqlParameter的最佳方法 - Best method of assigning NULL value to SqlParameter 如果为空,则将sqlparameter强制转换为DBNULL值 - Cast a sqlparameter into a DBNULL value if it's null SqlParameter在实体框架SqlQuery中返回null - SqlParameter returns null in Entity Framework SqlQuery 我的 SQLParameter 没有正确传递 NULL - My SQLParameter isn't passing NULL correctly SqlParameterCollection 只接受非空的 SqlParameter 类型对象,而不接受 Microsoft.Data.SqlClient 中的 SqlParameter 对象 - The SqlParameterCollection only accepts non-null SqlParameter type objects, not SqlParameter objects in Microsoft.Data.SqlClient System.InvalidCastException:“SqlParameterCollection 只接受非空 SqlParameter 类型对象,不接受 SqlParameter 对象。” - System.InvalidCastException: 'The SqlParameterCollection only accepts non-null SqlParameter type objects, not SqlParameter objects.' 为什么 SqlParameter 名称/值构造函数将 0 视为空? - Why does the SqlParameter name/value constructor treat 0 as null? SqlParameterCollection只接受非null的SqlParameter类型对象,而不接受DBNull对象 - SqlParameterCollection only accepts non-null SqlParameter type objects, not DBNull objects
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM