大家都知道在一个datatable中删除datarow有两个方法,调用remove()和delete()方法。
其中remover()方法是直接删除,delete()方法则是先做标记,再调用AcceptChanges()的时候才会删除。但是有时候会发现delete()在调用AcceptChanges()之前也会直接删除,这是为什么呢。
如下一段代码在调试过程中就会发现会有异常。
using System;
using System.Text;
using System.Collections;
using System.Data;
namespace Test
{
class TEST1
{
static void Main(string[] args)
{
DataSet ds = new DataSet();
CreatDataSetSchema(ds);
InitData(ds);
int count = ds.Tables[0].Rows.Count;
for (int i =0 ; i < count ; i++ )
{
ds.Tables[0].Rows[i].Delete();
Console.WriteLine(ds.Tables[0].Rows.Count.ToString());
}
Console.WriteLine("end");
Console.ReadLine();
}
//初始化数据集结构
private static void CreatDataSetSchema(DataSet ds)
{
DataTable dt = new DataTable("Hosts");
DataColumn dc = new DataColumn("HId", typeof(String));
dt.Columns.Add(dc);
dc = new DataColumn("IsLocal", typeof(Boolean));
dt.Columns.Add(dc);
ds.Tables.Add(dt);
}
//加入数据
private static void InitData(DataSet ds)
{
DataRow hostsRow = ds.Tables["Hosts"].NewRow();
hostsRow["HId"] = "192.168.1.1";
hostsRow["IsLocal"] = true;
ds.Tables["Hosts"].Rows.Add(hostsRow);
hostsRow = ds.Tables["Hosts"].NewRow();
hostsRow["HId"] = "192.168.1.2";
hostsRow["IsLocal"] = false;
ds.Tables["Hosts"].Rows.Add(hostsRow);
hostsRow = ds.Tables["Hosts"].NewRow();
hostsRow["HId"] = "192.168.1.3";
hostsRow["IsLocal"] = false;
ds.Tables["Hosts"].Rows.Add(hostsRow);
hostsRow = ds.Tables["Hosts"].NewRow();
hostsRow["HId"] = "192.168.1.4";
hostsRow["IsLocal"] = false;
ds.Tables["Hosts"].Rows.Add(hostsRow);
}
}
}
通过调试中查看ds对象的数据发现在调用delete()方法后数据被删除了,而不是被置为删除标记。为什么会有这种情况呢,很多网上的文章和MSDN的帮助都说的是做标记而不是删除?
我也被这种情况折腾了两天,快要放弃的情况下想到我的另外一个delete()方法就是置为删除标记,两者的区别就是一个是直接从数据库填充的数据,而这个是自己手动添加的数据,于是想到了试试在插入完成数据库调用AcceptChanges()方法。
上面的main方法代码修改为如下:
static void Main(string[] args)
{
DataSet ds = new DataSet();
CreatDataSetSchema(ds);
InitData(ds);
//调用delete方法前保存数据插入
ds.Tables[0].AcceptChanges();
int count = ds.Tables[0].Rows.Count;
for (int i =0 ; i < count ; i++ )
{
ds.Tables[0].Rows[i].Delete();
Console.WriteLine(ds.Tables[0].Rows.Count.ToString());
}
Console.WriteLine("end");
Console.ReadLine();
}
这个时候调试就正确了,能够在ds对象上看到数据都被标记为删除了。