日期:2014-05-18  浏览次数:21205 次

关于sqldatareader if(!dr.read())的作用
dr.read()的作用到底是什么?

C# code

        public static int  ReturnCount(Entity.WeaponInfo ReturnCount,string type)
        {
            SqlConnection conn = new SqlConnection("Server=.; Integrated Security=True; Database=WeaponSalesMng");
            SqlCommand cmd = new SqlCommand("select sum(Count) from CusRec where WeapName=@WeapName and Type=@Type", conn);
            cmd.Parameters.Add(new SqlParameter("@WeapName", ReturnCount.Name));
            cmd.Parameters.Add(new SqlParameter("@Type", type));//表里没有与type对应的记录,查询结果是Null;
            conn.Open();
            SqlDataReader dr = cmd.ExecuteReader();
            if (!dr.Read())
            {
                conn.Close();//但是程序并没有跳到这里;
                return 0;
            }
            else
            {
                int i = (int)dr[0];//而是进到了这里;并且出现了“制定的转换无效”
                conn.Close();
                return i;
            }
        }



渣菜鸟学生,什么都不知道 T_T。。。rd.Read()的作用到底是什么呢?
如果我想达到,当查询结果为空时,return 0;我该怎么做?


------解决方案--------------------
rd.Read() 是尝试读取一行数据,如果读取成功,返回 true ,并将数据置于缓冲区内,如果没读到,返回 false 
因为是的 sql 语句 select sum(Count),这样一定为返回一行,所以第一次调用 rd.Read() 一定会返回 true,代码修改下
C# code
public static int ReturnCount(Entity.WeaponInfo ReturnCount, string type)
{
    SqlConnection conn = new SqlConnection("Server=.; Integrated Security=True; Database=WeaponSalesMng");
    SqlCommand cmd = new SqlCommand("select sum(Count) from CusRec where WeapName=@WeapName and Type=@Type", conn);
    cmd.Parameters.Add(new SqlParameter("@WeapName", ReturnCount.Name));
    cmd.Parameters.Add(new SqlParameter("@Type", type));//表里没有与type对应的记录,查询结果是Null;
    conn.Open();
    int num = Convert.ToInt32(cmd.ExecuteScalar());
    cmd.Dispose();
    conn.Dispose();
    return num;
}

------解决方案--------------------
如果sql查询没有返回记录,函数返回0。

如果sql查询返回了(一条或者多条)记录,取第一条记录的第一列的值(假设它是int类型的)并返回。

可惜你的sql查询返回的第一列不是一个int(例如可能是个DBNull)。



你可以去重新学学t-sql,看看统计函数sum(Count)会不会得到null值。
------解决方案--------------------
实际上,你代码中写的判断完全是多余的。因为此sql不可能是没有记录返回。因此就算使用你的ExecuteReader写的话那么应该类似地,写为
C# code
        using(var conn = new SqlConnection("Server=.; Integrated Security=True; Database=WeaponSalesMng"))
       {
            SqlCommand cmd = new SqlCommand("select isnull(sum(Count),0) from CusRec where WeapName=@WeapName and Type=@Type", conn);
            cmd.Parameters.Add(new SqlParameter("@WeapName", ReturnCount.Name));
            cmd.Parameters.Add(new SqlParameter("@Type", type));
            conn.Open();
            SqlDataReader dr = cmd.ExecuteReader();
            dr.Read();  //它永远都是true,因此你用不着多次一举去判断if
            int i = (int)dr[0];
            return i;
       }