如何从 .NET 中的 SQLDataReader 获取 INT 数据

How to get data in INT from SQLDataReader in .NET

我正在尝试从数据库中获取 int 值,但出现错误

Unable to cast object of type 'System.Byte' to type 'System.Int32'.

在数据库中,活动字段是tinyint

此外,如何从该方法中 return 两个值。

private string CheckData(string firstValue, string SecondValue, int Active)
{
    string Data = "";

    StringBuilder sb = new StringBuilder();
    string query = @"select M.ident Mi, mmp.active Active 
                     from Iden.Iden M
                     inner join PtM.MPt MMP on MMP.mPat = M.id
                     where M.ident = 'firstValue' 
                       and Mi.ident = 'SecondValue'";
    sb.Append(query);

    sb.Replace("firstValue", firstValue);
    sb.Replace("SecondValue", SecondValue);
            
    SqlConnection connection = new SqlConnection(connString);

    SqlCommand cmd = new SqlCommand(sb.ToString());
    cmd.CommandTimeout = 0;
    cmd.CommandType = CommandType.Text;
    cmd.Connection = connection;

    try
    {
        connection.Open();

        SqlDataReader reader = cmd.ExecuteReader();

        if (reader.HasRows)
        {
            while (reader.Read())
            {
                Data = reader.GetString(reader.GetOrdinal("Mi"));
                Active = reader.GetInt32(reader.GetOrdinal("Active"));
            }
        }
    }
    catch (Exception ex)
    {
        _log.Error($"Exception:{ex.Message}");
    }
    finally
    {
        connection.Close();
        connection.Dispose();
    }

    return Data;
}

这是一个尝试。我无法调试它(因为我不想创建数据库)。

首先我创建一个类型来保存结果。你可以只使用元组,但这看起来更清楚:

public class DataActive
{
    public string Data { get; set; }
    public byte Active { get; set; }
}

我让你的函数 return 成为这些的集合 - 从你的代码中看不出只有一个。

您还会注意到我使用 SqlParameterfirstValuesecondValue 添加到您的查询中。查找 SQL Injection(和 Little Bobby Tables)。

如果您使用的是最新版本的 C#(我没有),using 有一个新语法,它需要更少的缩进。 using 语句在块末尾的 finally 语句中粘贴对 Dispose 的调用。另请注意,我正在处理 SqlCommand 和 DataReader

public static IEnumerable<DataActive> CheckData(string firstValue, string secondValue)
{
    var results = new List<DataActive>();

    const string query = @"select M.ident Mi,mmp.active Active from Iden.Iden M
                Inner join PtM.MPt MMP on MMP.mPat =M.id                    
                where M.ident = @firstValue and Mi.ident = @secondValue";

    using (var connection = new SqlConnection(connString))
    {
        using (var cmd = new SqlCommand(query))
        {
            cmd.CommandTimeout = 0;
            cmd.CommandType = CommandType.Text;
            cmd.Connection = connection;

            cmd.Parameters.Add("@firstValue", SqlDbType.NVarChar, 50).Value = firstValue;
            cmd.Parameters.Add("@secondValue", SqlDbType.NVarChar, 50).Value = secondValue;

            try
            {
                connection.Open();
                using (var reader = cmd.ExecuteReader())
                {
                    var dataOrdinal = reader.GetOrdinal("Mi");
                    var activeOrdinal = reader.GetOrdinal("Active");
                    if (reader.HasRows)
                    {
                        while (reader.Read())
                        {
                            results.Add(new DataActive
                            {
                                Data = reader.GetString(dataOrdinal),
                                Active = reader.GetByte(activeOrdinal),
                            });
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                _log.Error($"Exception:{ex.Message}");
            }
        }
    }
    return results;
}

如果你的 TINY_INT Active 代表一个布尔值,弄清楚规则是什么,然后做一个转换 之后你使用 reader.GetByte.

最后一点,通常记录 ex.ToString() 而不是 ex.Message 更好。您会以这种方式获得消息和堆栈。