用datareader如何获取数据的总行数
1 ,这里我就不谈SqlDataReader和DateSet的区别了,主要说下我们怎么能够构造一个能够高效率的DataTable,当然也是可以构造一个ArrayList来添加实体类。SqlDataReader中我们能够获取执行SQL后的字段名称(GetName方法)和获取字段类型(GetFieldType方法),这样我们就能够构造一个DataTable.
for (int i = 0; i < intColLength; i++)
{
//构造sql的table
dtb.Columns.Add(dtrValue.GetName(i), GetColType(i));
}
SqlDataReader是一个单向的游标,不能够从某个起点往下读数据,这点我觉得微软是做的有点不够,这样如果查询结果多,而要获取的是数据集的最后的数据要消耗掉一点资源。
2,如何让SqlDataReader再提高点,那你就只能指定是从那一行纵向读数据了,也就是在你页面中需要显示的数据才读取,其他数据单向下移动读取游标就可以,下面就是一个这样的实例代码
#region "私有变量"
///
/// 表示一个到数据库的打开的连接
///
private System.Data.SqlClient.SqlConnection Con = new SqlConnection();
///
/// 表示执行对象是SQl还是存储过程
///
private System.Data.SqlClient.SqlCommand Cmd = new SqlCommand();
///
/// 表示用于填充 System.Data.DataSet 和更新数据库的一组数据命令和到数据库的连接
///
private System.Data.SqlClient.SqlDataAdapter Dtapt = new SqlDataAdapter();
///
/// 表示要在数据库中生成的事务
///
private System.Data.SqlClient.SqlTransaction sqlTran;
///
/// 提供从数据源读取数据行的只进流的方法
///
private SqlDataReader dtrValue = null;
#endregion
#region"数据库连接处理"
///
/// 获得webconfig中的 默认 Sql连接字符串
///
private string strConSql
{
get
{
return System.Configuration.ConfigurationManager.AppSettings["SQLConntionStr"].ToString();
}
}
#endregion
#region "事务处理"
///
/// 开始事务
///
public void BeginTransaction()
{
if (Con.State == ConnectionState.Closed)
{
//打开连接
OpenCn();
//开始事务
if (sqlTran == null)
{
sqlTran = Con.BeginTransaction();
}
Cmd.Transaction = sqlTran;
}
}
///
/// 提交事务
///
public void CommitTransection()
{
sqlTran.Commit();
sqlTran.Dispose();
sqlTran = null;
CloseCn();
}
///
/// 回滚事务
///
public void RollbackTransection()
{
sqlTran.Rollback();
sqlTran.Dispose();
sqlTran = null;
CloseCn();
}
#endregion
#region"返回分页表数据Datatable [Read] 方式获取数据,数据量建议在查询结果在10000条记录内"
///
/// 用于分页控件,返回需要显示页的数据和记录条数
///
/// SQL语句
/// SQL参数和其对应值
/// 开始记录
/// 每页显示记录条数
/// 返回记录条数
/// 查询数据集
protected DataTable ExecuteReadTable(string p_strSql, SqlParameter[] p_CmdParms, int p_intStart, int p_intPageSize, ref int out_intCount)
{
return ExecuteReadTable(CommandType.Text, p_strSql, p_CmdParms, p_intStart, p_intPageSize, ref out_intCount);
}
///
/// 1. 根据存储过程和参数值得到DataTable 值
/// 2. 根据SQL的得到DataTable 值
///
/// 是存储过程还是SQL
/// 开始记录
/// 每页显示条数
/// 可是是SQL 也可以是存储过程
/// SqlParameter参数列表
/// 返回总记录数
/// 返回DataTable
protected DataTable ExecuteReadTable(CommandType p_objCmdType, string p_strSql, SqlParameter[] p_CmdParms, int p_intStart, int p_intPageSize, ref int out_intCount)
{
DataTable dtb = new DataTable();
DateTime dtStart = DateTime.Now;
dtrValue = ExecuteReader(p_objCmdType, p_strSql, p_CmdParms);
if (dtrValue == null)
{
CloseCn();
return dtb;
}
int intColLength = dtrValue.FieldCount;
for (int i = 0; i < intColLength; i++)
{
//构造sql的table
dtb.Columns.Add(dtrValue.GetName(i), GetColType(i));
}
DataRow dr;
int k = 0;
if (dtrValue.HasRows)
{
//读取数据行值
while (dtrValue.Read())
{
//读取分页间数据
if (p_intStart <= k && k < p_intStart + p_intPageSize)
{
dr = dtb.NewRow();
//读取每列值
for (int j = 0; j < intColLength; j++)
{
//读取每列的值
dr[dtrValue.GetName(j)] = GetValue(j, GetFieldType(j).ToString());
}
dtb.Rows.Add(dr);
}
k++;
}
//删除了当前页所有数据则读上一页数据
if (k <= p_intStart)
{
while (k <= p_intStart)
{
p_intStart = p_intStart - p_intPageSize;
}
k = 0;
dtrValue = ExecuteReader(p_objCmdType, p_strSql, p_CmdParms);
if (dtrValue.HasRows)
{
while (dtrValue.Read())
{
//读取分页间数据
if (p_intStart <= k && k < p_intStart + p_intPageSize)
{
dr = dtb.NewRow();
//读取每列值
for (int j = 0; j < intColLength; j++)
{
//读取每列的值
dr[dtrValue.GetName(j)] = GetValue(j, GetFieldType(j).ToString());
}
dtb.Rows.Add(dr);
}
k++;
}
}
}
}
CloseCn();
SEHR.BLL.Function.AddSQLLog.WriteLog(p_strSql, dtStart.TimeOfDay.ToString(), DateTime.Now.TimeOfDay.ToString(), Convert.ToString(DateTime.Now - dtStart));
if (out_intCount == 0)
{
out_intCount = k;//获得总行数并且返回到页面
}
return dtb;
}
#endregion
#region "ExecuteReader 执行SQL语句"
///
/// ExecuteReader
///
/// 命令类型 1CommandType.Text SQL语句 2CommandType.StoredProcedure存储过程
/// 命令类型 1 SQL语句 2存储过程名称
/// SqlParameter
/// SqlDataReader
private SqlDataReader ExecuteReader(CommandType p_objCmdType, string p_strSQL, SqlParameter[] p_CmdParms)
{
SqlDataReader dtrRet = null;
try
{
//打开连接
OpenCn();
//命令行连接
Cmd.Connection = Con;
Cmd.CommandText = p_strSQL;
//是SQL语句还是存储过程
Cmd.CommandType = p_objCmdType;
//循环CmdParms值
if (p_CmdParms != null)
{
foreach (SqlParameter objParm in p_CmdParms)
{
Cmd.Parameters.Add(objParm);
}
}
dtrRet = Cmd.ExecuteReader();
Cmd.Parameters.Clear();
return dtrRet;
}
catch (Exception e)
{
string strErr = string.Empty; //p_CmdParms 参数值
if (p_CmdParms != null)
{
foreach (SqlParameter objParm in p_CmdParms)
{
strErr += objParm.ParameterName + " ='" + objParm.Value + "' ";
}
}
if (Con.State != ConnectionState.Closed && sqlTran == null)
{
Cmd.Parameters.Clear();
CloseCn();
}
// 写错误日志
SEHR.BLL.Function.AddMsgLog.AddError("SqlBase", e.Message + ""n"r SQL : " + p_strSQL + ""n"r 参数 : " + strErr, e.StackTrace);
return null;
}
finally
{
//如果连接打开并且没有事务和SqlDataReader事件 则关闭连接
if (Con.State != ConnectionState.Closed && sqlTran == null && dtrRet == null)
{
Cmd.Parameters.Clear();
CloseCn();
}
}
}
#endregion
VB.net OleDbDataReader 类的用法问题。
conn.Close()
cmd.Connection = myconn
cmd.CommandText = "select * FROM address WHERE id,name='*************此处看你的
conn.Open()
Dim mydatareader As OleDbDataReader
mydatareader = cmd.ExecuteReader()
mydatareader.Read()
Me.textbox1.Text = mydatareader.Item("id")
Me.textbox2.Text = mydatareader.Item("name")
C# datagridview显示access
改成用Adapter替换DataReader,然后用Fill方法填充dataset
OleDbConnection con = new OleDbConnection("Provider=Microsoft.Jet.OLEDB.4.0;Data Source=Neusoft IP Configer.mdb");
con.Open();
string sql = "select * from IP";
OleDbDataAdapter ad = new OleDbDataAdapter(sql, con);
DataTable dt = new DataTable();
ad.Fill(dt);
dataGridView1.DataSource = dt.DefaultView;
需要添加System.Data 命名空间。
c#(winform)中如何用sqldatareader数据绑定到datagridview
String connectionString = "Data Source=local;Initial Catalog=TotalManagement;Integrated Security=True";
string selectCommand = "select ID,Name,LawRank,ExecuteDate,ContentType FROM LawsAndRegulations";
using (SqlConnection cn = new SqlConnection(connectionString))
{
SqlDataAdapter sda = new SqlDataAdapter(selectCommand , cn);
cn.Open();
DataSet dr = cmd.DataAdapter();
sda.Fill(dr);
dataGridViewLaw.DataSource = dr;
dataGridViewLaw.AutoResizeColumns(DataGridViewAutoSizeColumnsMode.AllCellsExceptHeader);
}
C#OleDbDataReader在命令提示符下怎么获取某行某列的值,能给句代码吗?
1)在Access数据库 Database1.mdb 中有一个表:表12)用OleDbDataReader 获取指定行、指定列的值using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Data;using System.Data.OleDb;namespace ConsoleOleDb{ class Program { static void Main(string[] args) { OleDbConnection conn = new OleDbConnection(@"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=|DataDirectory|\Database1.mdb"); OleDbCommand cmd =conn.CreateCommand(); cmd.CommandText ="select * from 表1"; conn.Open(); OleDbDataReader rd = cmd.ExecuteReader(); //获取表中第二行,第二列的值 string s = (string) GetValue(rd, 1, 2); Console.WriteLine("表1第2行,第二列的值为:{0}", s); } // 从OleDbDataReader中获取指定行、指定列的值 static object GetValue(OleDbDataReader reader, int row, int col) { int i = 0; object value = null; while (reader.Read()) { if (i == row) { value = reader[col]; break; } i++; } reader.Close(); return value; } }}
用c#连接数据库的时候 读数据是dataReader.HasRows 和dataReader.Read()这两个有什么明显的区别那
datareader.HasRows 只是检则库中是否有记录,如果有则返回true,还得再用read()读取.
datareader.read()为从数据开头往后读,如果库中已读到结尾了(可能没有记录)则返回false,如果用在if中,则会自动读出一条,else里则不必再用read(),如果有while(含有read()条件),则自动从第二条开始往下读
结论:单条可用read()检测,多条用到while时用HasRows检测...
声明:SqlDataReader 提供一种从 SQL Server 数据库读取行的只进流的方式。无法继承此类。
我在编写一个小程序时遇到一个小问题:
使用SqlDataReader实例reader的HasRows判断数据流中是否存在数据,进而执行数据的输出操作,其中用到代码如下
SqlDataReader reader = Command.ExecuteReader();
while(reader.HasRows)
{
reader.Read();
qx_Str = reader[0].ToString(); //出错位置
}
reader.Close();
sqlcon.Close();
运行后在红色位置报错:在没有任何数据时进行无效的读取尝试
出现这种情况很明显是读取器运行到的位置无数据流,无法执行数据的输出
这时确定判断是while处的判断条件有误,在MSDN文档中查询到:
HasRows属性
// HasRows 获取一个值,该值指示 System.Data.SqlClient.SqlDataReader 是否包含一行或多行。
原来是出在HasRows的使用上,只要SqlDataReader存在数据流(数据流不为空)则返回的bool值为真,这样的话,这个循环总执行(难怪使用try ..catch 假死)。数据为空时,read[0]读取数据时,则会出现错误!
那么如何避免出现该错误呢,仍然是用HasRows属性?
可以想到只需利用if语句取消循环状态!!
那么要用while怎么办呢?使用SqlDataReader实例的Read()方法,对!
让我们认识一下Read()方法:
// 摘要: 使 System.Data.SqlClient.SqlDataReader 前进到下一条记录。
// 返回结果: 如果存在多个行,则为 true;否则为 false。
则只需将reader.Read()替换reader.HasRows执行循环,为什么行呢?
SqlDataReader的默认位置在[第一条记录前面]。因此,必须调用 Read 来开始访问任何数据。
Read()为前进到下一条记录。当循环执行到Read()无数据时,则循环结束!!不过还要将循环里的Read()去掉,则每循环一次前进了两行数据。
如何使用c#操作ACCESS数据库
在BETA2中,。NET提供了以下的NAMESPACE:
System.Data Namespace
System.Data.OleDb (和BETA1中已经不同了,所以如果拿BETA1中的程序到BETA2中来运行肯定不可以的)
如果想讲清楚这些东西,我不认为是我可以作到的,所以我想通过一些具体的程序来把我们对数据库的最基本的操作(SELECT、UPDATE、DELETE、INSERT等)演示一下,其他的还是需要朋友们在学习过程中来慢慢体会了!
要想操作一个数据库,不论是那种操作,首先要做的肯定是打开数据库,下面我们以ACCESS数据库来做例子说明如何打开一个数据库连接!在这里我们需要用到的是:System.Data.OleDb.OleDbConnection类!(如果操作SQL数据库,我们最好使用System.Data.SqlClient.SqlConnection类)
我先写出我自己使用的程序:
using System.Data
using System.Data.OleDb
public OleDbConnection getConn()
{
string connstr="Provider=Microsoft.Jet.OLEDB.4.0 ;Data Source=F:\\web\\notesbook\\class\\leavenotes.mdb";
OleDbConnection tempconn= new OleDbConnection(connstr);
return(tempconn);
}
相信只要使用过ADO的朋友应该都可以看懂的!我们先定义一个String类型的变量,其中存放了我们连接数据库的连接字符串,然后在定义一个System.Data.OleDb.OleDbConnection类型的对象并实例化,最后返回这个对象!需要说明一下的是,我并没有把语句:tempconn.Open();放到这个函数中,原因我我稍后在说明,这里只是先提醒一下!
通过上面的函数,我们就已经得到了类似于ADO中的连接对象Connection了!下面的就是具体操作数据库了!
在具体讲操作前,我认为有必要先认识一下下面的两个类:
System.Data.OleDb.OleDbDataAdapter
System.Data.OleDb.OleDbDataReader
System.Data.OleDb.OleDbDataAdapter:可以直接和DataSet联系,并操作数据源的,它的功能相对强大一些,因此也比较耗系统资源!
System.Data.OleDb.OleDbDataReader:则有些类似于ADO中的哪个只读向前的记录集,它最常用在只需要依次读取并显示数据的时候,相比System.Data.OleDb.OleDbDataAdapter来说,他耗用的系统资源要小!其实,OleDbDataReader能实现的功能,OleDbDataAdapter都可以实现,不过从资源使用率的角度考虑我们应该尽量使用前者!但有些功能,却是必须使用OleDbDataAdapter才可以实现的!
* SELECT操作!
下面是我的自己在写测试程序的时候用到了,先列出来看看OleDbDataReader和OleDbDataAdapter是如何操作从数据库中选择记录的:
//通过ID得到当前留言详细内容.通过STRING类型参数
public Notebook getNoteFromID(string noteid)
{
Notebook tempnote=new Notebook(); //定义返回值
try
{
OleDbConnection conn = getConn(); //getConn():得到连接对象
string strCom = "Select * from notes where id=" + noteid ;
OleDbCommand myCommand =new OleDbCommand(strCom,conn);
conn.Open();
OleDbDataReader reader;
reader =myCommand.ExecuteReader() ; //执行command并得到相应的DataReader
//下面把得到的值赋给tempnote对象
if(reader.Read())
{
tempnote.id=(int)reader["id"];
tempnote.title=reader["title"].ToString();
tempnote.content=reader["content"].ToString();
tempnote.author=reader["author"].ToString();
tempnote.email=reader["email"].ToString();
tempnote.http=reader["http"].ToString();
tempnote.pic=reader["pic"].ToString();
tempnote.hits=(int)reader["hits"];
tempnote.posttime=(DateTime)reader["posttime"];
}
else //如没有该记录,则抛出一个错误!
{
throw(new Exception("当前没有该记录!"));
}
reader.Close();
conn.Close();
}
catch(Exception e)
{
//throw(new Exception("数据库出错:" + e.Message)) ;
}
return(tempnote); //返回Databook对象
}
上面的程序就是通过OleDbDataReader来得到特定的记录的!其中用到的语句我单独写到下面:
OleDbConnection conn = getConn(); //getConn():得到连接对象
string strCom = "Select * from notes where id=" + noteid ; //SQL语句
OleDbCommand myCommand =new OleDbCommand(strCom,conn); //建立OleDbCommand对象
conn.Open(); //注意我在前面说的Open语句在这里使用到了!
OleDbDataReader reader;
reader =myCommand.ExecuteReader() ; //执行command并得到相应的结果
我在每句话后都加入了说明,其中OleDbConnection conn = getConn();就是通过我前面提到的getConn函数来得到数据库连接的,其他语句没有什么好说的,都很简单,就不多说了!
我再列一个通过OleDbDataAdapter来得到记录的例程:
//Getlist():得到当前需要的留言列表
public DataView getNoteList()
{
DataView dataview;
System.Data.DataSet mydataset; //定义DataSet
try
{
OleDbConnection conn = getConn(); //getConn():得到连接对象
OleDbDataAdapter adapter = new OleDbDataAdapter();
string sqlstr="select * from notes order by posttime desc";
mydataset= new System.Data.DataSet();
adapter.SelectCommand = new OleDbCommand(sqlstr, conn);
adapter.Fill(mydataset,"notes");
conn.Close();
}
catch(Exception e)
{
throw(new Exception("数据库出错:" + e.Message)) ;
}
dataview = new DataView(mydataset.Tables["notes"]);
return(dataview);
}
这个程序或许有些复杂,同样的,我还是先把那些关键语句列出,并说明:
OleDbConnection conn = getConn(); //通过函数getConn()得到连接对象
OleDbDataAdapter adapter = new OleDbDataAdapter(); //实例化OleDbDataAdapter对象
string sqlstr="select * from notes order by posttime desc"; //SQL语句
mydataset= new System.Data.DataSet(); //由于OleDbDataAdapter需要和DataSet结合使用,所以在这里定义了DataSet对象,其实说OleDbDataAdapter复杂,其实就是因为DataSet的缘故DataSet有些类似于ADO中的recordset 对象,但功能远远超过了它,而且它和数据库是断开的,并能存放多个记录集!
adapter.SelectCommand = new OleDbCommand(sqlstr, conn); //设置命令为SelectCommand类型的
adapter.Fill(mydataset,"notes"); //执行,并将结果添加到mydataset中的”notes”表中
conn.Close(); //关闭连接!
在对上面的程序加一些补充说明,由于getNoteLista是得到一系列记录,并通过控件DataGrid来做分页显示的,所以我返回的是一个DataView类型的对象!
----------------------------------------
上次说了如何在ADO。NET中执行“SELECT”语句,这次我们看看,如何执行“DELETE、UPDATE、INSERT”等语句。
我们这次同样通过例子来看,其中我们用到了System.Data.OleDb.OleDbCommand类,其实,我们在前面执行SELECT的时候也用到了!
下面我写出我的程序:
//修改留言本中特定的数据
public Boolean UpdateNote(Notebook note)
{
Boolean tempvalue=false;
string sqlstr=""; //当时在这里定义,是为了在出现异常的时候看看我的SQL语句是否正确
try
{
//用到了我前面写的那个得到数据库连接的函数
OleDbConnection conn = getConn(); //getConn():得到连接对象,
conn.Open();
//确定我们需要执行的SQL语句,本处是UPDATE语句!
sqlstr = "UPDATE notes SET ";
sqlstr += "title='" + note.title + "',";
sqlstr += "content='" + DealString(note.content) +"',";
sqlstr += "author='" + note.author + "',";
sqlstr += "email='" +note.email +"',";
sqlstr += "http='" +note.http +"'";
//sqlstr += "pic='" +note.pic +"'";
sqlstr += " where id=" + note.id;
//定义command对象,并执行相应的SQL语句
OleDbCommand myCommand = new OleDbCommand(sqlstr,conn);
myCommand.ExecuteNonQuery(); //执行SELECT的时候我们是用的ExecuteReader()
conn.Close();
//假如执行成功,则,返回TRUE,否则,返回FALSE
tempvalue=true;
return(tempvalue);
}
catch(Exception e)
{
throw(new Exception("数据库更新出错:" + sqlstr + "\r" + e.Message)) ;
}
}
这个例子是对于特定ID好的记录进行UPDATE操作,具体解释我都写在了程序中,其中的与数据库有关的语句是try内部的那些!
其实,我们同样可以通过上面的那种模式执行INSERT、DELETE操作,下面我把我的程序列到下面!
/*删除特定记录,通过string类型的ID删除字段,在我的程序中,我把这个函数重载了,这样我们就可以通过INT类型的ID参数来删除特定的字段了*/
public Boolean DelNote(string delid)
{
Boolean tempvalue=false;
string sqlstr="";
//连接数据库
try
{
OleDbConnection conn = getConn(); //getConn():得到连接对象
conn.Open();
sqlstr = "delete * from notes where id=" + delid;
//定义command对象,并执行相应的SQL语句
OleDbCommand myCommand = new OleDbCommand(sqlstr,conn);
myCommand.ExecuteNonQuery();
conn.Close();
//假如执行成功,则,返回TRUE,否则,返回FALSE
tempvalue=true;
return(tempvalue);
}
catch(Exception e)
{
throw(new Exception("数据库更新出错:" + sqlstr + "\r" + e.Message)) ;
}
}
细心的朋友们应该能看到,其实这个程序和上面的相比,只是哪个SQL语句不同而已,其他的都基本一样的!同样的,我们想在数据库中插入新的记录的时候也可以用这样的方式,程序如下:
//向留言本中添加数据
public Boolean AddNote(Notebook note)
{
Boolean tempvalue=false; //定义返回值,并设置初值
//下面把note中的数据添加到数据库中!
try{
OleDbConnection conn = getConn(); //getConn():得到连接对象
conn.Open();
//设置SQL语句
string insertstr="INSERT INTO notes(title, content, author, email, http, pic ,hits,posttime) VALUES ('";
insertstr += note.title +"', '";
insertstr += DealString(note.content) + "','";
insertstr += note.author + "','";
insertstr += note.email + "','";
insertstr += note.http + "','";
insertstr += note.pic + "',";
insertstr += note.hits + ",'";
insertstr += note.posttime +"')";
OleDbCommand insertcmd = new OleDbCommand(insertstr,conn) ;
insertcmd.ExecuteNonQuery() ;
conn.Close();
tempvalue=true;
}
catch(Exception e)
{
throw(new Exception("数据库出错:" + e.Message)) ;
}
return(tempvalue);
}
//处理数据,在把数据存到数据库前,先屏蔽那些危险字符!
public string DealString(string str)
{
str=str.Replace("<","<");
str=str.Replace(">",">");
str=str.Replace("\r","");
str=str.Replace("\'","’");
str=str.Replace("\x0020"," ");
return(str);
}
//恢复数据:把数据库中的数据,还原成未处理前的样子
public string UnDealString(string str)
{
str=str.Replace("<","<");
str=str.Replace(">",">");
str=str.Replace("","\r");
str=str.Replace("’","\'");
str=str.Replace(" ","\x0020");
return(str);
}
SqlDataReader和oledbDataReader和DataReader区别
他们本质上没有什么不同
都是提供对数据顺序读取一种读取器
它依赖于连接对象也就是只有在与数据库连接在打开的状态下才可以使用
SqlDataReader:是专门用来读取SQl数据库中的数据的,对读取方式进行了优化
oledbDataReader:适用于所有使用oledb驱动的数据库,例如SQl、MySql、ORACAL、Access等
DataReader:是上面两个类的父类,属于基类
oledbDataReader可以访问ORACAL、MySql、Access数据库、甚至是Excel表格
SqlDataReader是C#中专门操作MS SQLServer数据库的数据集合,在oledb的基础上做了优化
另外oledbDataReader也可以操作MS SQLServer数据库,但是SqlDataReader对它做了一些优化,
所以要是操作MS SQLServer就用SqlDataReader就对了