我正在尝试从数据库中的视图中提取一个字段。我确定这个实例有数据,我正确设置了SQLDataReader(我相信),调试器验证我在DataReader中有行,但是当我尝试读取时出现错误。
以下是代码:
public string[] getReasons(string Accession) {
string[] reasonList = new string[0];
SqlParameter accNumber = new SqlParameter();
accNumber.SqlDbType = System.Data.SqlDbType.VarChar;
accNumber.ParameterName = "@Accession";
accNumber.Value = Accession;
string selectText = "select reason from pendingList where accession = @Accession";
SqlCommand selectStmt = new SqlCommand(selectText,toPending);
selectStmt.Parameters.Add(accNumber);
if (selectStmt.Connection.State == System.Data.ConnectionState.Closed) {
selectStmt.Connection.Open();
}
SqlDataReader pendList = selectStmt.ExecuteReader();
while (pendList.Read()) {
reasonList[reasonList.Length] = pendList["reason"].toString();
}
pendList.Close();
return reasonList;
}
我叫getReasons('RAM4658980')。我已经验证了以下SQL查询
select reason
from pendingList
where accession = 'RAM4658980'
只返回一行。 pendList
变量如下所示:
我不确定为什么会得到“枚举没有结果”;在reasonList[reasonList.Length] = pendList["reason"].toString();
步骤,我自然得到“无效尝试读取...”错误。我错过了什么?
答案 0 :(得分:1)
您不应该使用调试器来确认您在阅读器中有行"。虽然SqlDataReader
(和DbDataReader
一般)实现IEnumerable
,但它们是特殊的,因为reader是仅向前只读数据库游标的托管等效项,因此在迭代时,它确实消耗底层光标,或者简单来说,它可以迭代一次。如果你使用调试器,你就可以有效地射击你的单个子弹。
改为验证缓冲结果(在您的情况下为reasonList
)。
更新:实际上除了上述内容之外,您的代码中还有一个错误 - reasonList
数组。要更正它,请使用以下内容(注意new List<string>
,reasonList.Add
和reasonList.ToArray
):
public string[] getReasons(string Accession) {
var reasonList = new List<string>();
SqlParameter accNumber = new SqlParameter();
accNumber.SqlDbType = System.Data.SqlDbType.VarChar;
accNumber.ParameterName = "@Accession";
accNumber.Value = Accession;
string selectText = "select reason from pendingList where accession = @Accession";
SqlCommand selectStmt = new SqlCommand(selectText,toPending);
selectStmt.Parameters.Add(accNumber);
if (selectStmt.Connection.State == System.Data.ConnectionState.Closed) {
selectStmt.Connection.Open();
}
SqlDataReader pendList = selectStmt.ExecuteReader();
while (pendList.Read()) {
reasonList.Add(pendList["reason"].toString());
}
pendList.Close();
return reasonList.ToArray();
}