惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

T
Tenable Blog
Last Week in AI
Last Week in AI
P
Proofpoint News Feed
Engineering at Meta
Engineering at Meta
H
Help Net Security
F
Fortinet All Blogs
MyScale Blog
MyScale Blog
宝玉的分享
宝玉的分享
让小产品的独立变现更简单 - ezindie.com
让小产品的独立变现更简单 - ezindie.com
博客园 - 司徒正美
量子位
N
Netflix TechBlog - Medium
Apple Machine Learning Research
Apple Machine Learning Research
小众软件
小众软件
Recorded Future
Recorded Future
博客园 - 三生石上(FineUI控件)
Vercel News
Vercel News
aimingoo的专栏
aimingoo的专栏
I
InfoQ
Microsoft Security Blog
Microsoft Security Blog
Scott Helme
Scott Helme
The Last Watchdog
The Last Watchdog
cs.AI updates on arXiv.org
cs.AI updates on arXiv.org
IT之家
IT之家
AI
AI
WordPress大学
WordPress大学
Security Archives - TechRepublic
Security Archives - TechRepublic
Google Online Security Blog
Google Online Security Blog
U
Unit 42
V2EX - 技术
V2EX - 技术
MongoDB | Blog
MongoDB | Blog
Schneier on Security
Schneier on Security
博客园 - Franky
H
Heimdal Security Blog
奇客Solidot–传递最新科技情报
奇客Solidot–传递最新科技情报
Jina AI
Jina AI
W
WeLiveSecurity
P
Privacy & Cybersecurity Law Blog
Cloudbric
Cloudbric
B
Blog RSS Feed
N
News | PayPal Newsroom
S
Securelist
Threat Intelligence Blog | Flashpoint
Threat Intelligence Blog | Flashpoint
I
Intezer
Hacker News - Newest:
Hacker News - Newest: "LLM"
CTFtime.org: upcoming CTF events
CTFtime.org: upcoming CTF events
博客园_首页
罗磊的独立博客
H
Hackread – Cybersecurity News, Data Breaches, AI and More
雷峰网
雷峰网

博客园 - 露雨城市.NET2.0和Sql Server 2005开发研究

关于asp.net将动态页直接生成静态页的随笔(乱码) 我的神龙卡KTV点播软件只有一个遗憾了 关于清除Sql Server Express版本的数据库日志文件 关于微软2008技术预览大会南京站和Vista 也许是转折-放弃了5,6K的月薪 关于vs2005中ajax控件暴露模板中控件,请高手进来聊聊. - 露雨城市.NET2.0和Sql Server 2005开发研究 好久没有来发文章了,今天来秀一下。 在.NET2.0中如何更简单的使用委托将方法加载到事件中去 Visual C#中父窗口和子窗口之间实现控件互操作 关于如何在子窗口中选择后,在父窗口赋值并让输入框设为只读。 - 露雨城市.NET2.0和Sql Server 2005开发研究 我的新资源网站开张了,韩国模版,韩国设计资源等。 关于在插入的模版中如何为已绑定了Text属性的TextBox设置默认值 今天好高兴,通过了微软的Sql Server 2005的70-31的考试。 赠送一张微软免费考试券 关于GridView中选择当前行的问题。 VS2005中的一个小BUG:关于Dropdownlist无法Datadinding的解决方法。 如何动态设置全局theme,及在web.config中读取pages节点的内容。 讲故事谈.NET委托:一个C#睡前故事 关于的MasterPage和Theme的问题。
这个基础题,你能做对吗?
露雨城市.NET2.0和Sql Server 2005开发研究 · 2007-07-20 · via 博客园 - 露雨城市.NET2.0和Sql Server 2005开发研究

今天我遇到一个题目,是关于AcceptChanges()和RejectChanges()方法的,考虑到可能很多人不清楚这些概念。
所以拿出来讲讲。由这个问题我们也深入了解一下这两个方法。
为了不在显示略文时显示出代码来,我就在刚开始多打一点字了。呵。。。

题目的代码如下:

 1private void button1_Click(object sender, System.EventArgs e)
 2        {
 3            DataSet ds= new DataSet();
 4
 5            DataTable tb = ds.Tables.Add("Items");
 6            DataColumn pk = tb.Columns.Add("ID"typeof(Int32));
 7            tb.Columns.Add("Items"typeof(string));
 8            tb.PrimaryKey = new DataColumn[] {pk};
 9
10            for(int i=0;i<6;i++)
11            {
12                DataRow dr = tb.NewRow();
13                dr[0= i.ToString();
14                dr[1= "Itme "+i;
15                tb.Rows.Add(dr);
16            }

17
18            tb.AcceptChanges();
19            tb.Rows[0].Delete();
20            tb.Rows.RemoveAt(1);
21            tb.Rows.RemoveAt(2);
22            tb.RejectChanges();
23
24            dataGrid1.DataSource = tb;
25        }

我们看到在第3-16行,实际上我们是生成了一个DataTable,这个dt有两个字段,分别是ID和Items,然后通过添加6条记录。
如果到此为止,那么这个的内容应该是如下:

ID Items
0 Item 0
1 Item 1
2 Item 2
3 Item 3
4 Item 4
5 Item 5

不过我们在第19,20,21行中分别删除了第0行,然后是移除第1行,移除第2行。当然如果只是这样就算不上题目了,我们在18和22行用到了DataTable的AcceptChanges()方法和RejectChanages()方法。

首先大家先想一下答案是什么?随便我把MSDN上对这两个方法的解释粘一下,好让大家理解。

DataTable.AcceptChanges方法
提交自上次调用 AcceptChanges 以来对该表进行的所有更改。调用 AcceptChanges 时,任何仍处于编辑模式的 DataRow 对象将成功结束其编辑。DataRowState 也会随之更改:所有状态为 Added 和 Modified 的行的状态都变为 Unchanged;状态为 Deleted 的行则被移除。
在您尝试使用 DbDataAdapter.Update 方法更新 DataSet 之后,通常会对 DataTable 调用 AcceptChanges 方法。

DataTable.RejectChanges方法
回滚自该表加载以来或上次调用 AcceptChanges 以来对该表进行的所有更改。
调用 RejectChanges 时,任何仍处于编辑模式的 DataRow 对象将取消其编辑。新行被移除。DataRowState 设置为 Modified 或 Deleted 的行返回到其初始状态。

一个意思表示立即更新,一个表示在接受上次调用AcceptChanges后进行回滚。

好的,那么是不是说,我们这儿的3条记录都能够回滚回来呢?

我们先公布一下答案吧,看看和大家想的是不是一样的。

ID Items
0 Item 0
2 Item 2
4 Item 4
5 Item 5

OK,答案表明并不是所有的记录都被回滚回来了,似乎只有0被回滚了。这并不是奇怪,那是因为我们使用删除行的方法不一样,一个是Delete(),一个是RemoveAt(int)。

我们通过在MSDN中的查询了解到在使用 Delete 方法后,RowState 变成“已删除”。在您调用 AcceptChanges 之前,它一直保持“已删除”。可通过调用 RejectChanges 取消删除行。

而RemoveAt表示当移除行时,该行中的所有数据都将丢失。您还可以调用 DataRow 类的 Delete 方法来标记某行以供移除。调用 RemoveAt 等同于先调用 Delete 再调用 AcceptChanges。

那就是说,我们使用Delete()方法删除行后是可以回滚的,而使用RemoveAt(int)方法是不能回滚的。
所以刚刚前面我们删除的三行,只回滚了0的那行是完成正确的。我想大家对答案应该没有疑问了。

从这个题目中,我引申出几个题目来,看看大家会不会做哦?

下面接着,我们再来修改一下代码看看。

tb.Rows[0].Delete();
tb.AcceptChanges();
tb.Rows.RemoveAt(
1);
tb.Rows.RemoveAt(
2);
tb.RejectChanges();

我们把AcceptChanges()方法放到后Delete()后面,很明显这样做,会让ID为0的数据也无法回滚。为什么大家看我上面粘的MSDN解释就知道了。

那么就这的话,答案会是什么呢,会不会有人想到是2,4,5呢。

想到2,4,5的人就错了哦。因为当接受AcceptChanges()方法后,前面的0行就彻底删除了,这时数据应该是1,2,3,4,5,然后RemoveAt(1)表示删除第2行,删除后也是立刻删除的,无法回滚,所以这时数据应该是1,3,4,5,接着RemoveAt(2)删除第3行,所以答案应该是1,3,5。
而原来把AcceptChanage()方法放在Delete()前面时,当调用tb.Rows[0].Delete()时,只是标记状态为删除,并没有直接移除第0行,所以那个RemoveAt(1),还是从0,1,2,3,4,5中删除第2行,所以答案是0,2,4,5。

好,我们再修改一下代码:

tb.AcceptChanges();
tb.Rows[
0].Delete();            
tb.Rows.RemoveAt(
1);
tb.AcceptChanges();
tb.Rows.RemoveAt(
2);
tb.RejectChanges();

大家来猜猜答案是什么呢?

不知道有没有人想到会是2,4,5,实际上不对。
正确的答案应该是2,3,5。

首先的第一个AcceptChanages表示将无法回滚前面添加数据的操作。接着第二个AcceptChanages表示彻底删除Delete()所删除的数据,这个时候数据就只剩下2,3,4,5了,然后再RemoveAt(2)把第三行删除了,所以就剩下2,3,5了。

好的,我们再把第一个AcceptChanages()方法给删除了,大家想想答案会是什么呢,代码如下:

tb.Rows[0].Delete();            
tb.Rows.RemoveAt(
1);
tb.AcceptChanges();
tb.Rows.RemoveAt(
2);
tb.RejectChanges();

可能有人说了,AcceptChanages()方法是对前面的语句生效的,所以你把这个删除了一点问题也没有,答案当然还是2,3,5了,其实这种说法是错误的。

这段代码的正确答案是1,3,5。
为什么会是这样呢,那是因为当Delete()方法在前面没有接收到AcceptChaages()方法后,会彻底删除因为没有必要回滚。所以RemoveAt(1)在执行时,实际上数据是1,2,3,4,5,它删除第2行,也就是3。

好的,我们再看看下面的这段代码:

tb.Rows[0].Delete();            
tb.Rows.RemoveAt(
1);
tb.Rows.RemoveAt(
2);
tb.AcceptChanges();
tb.RejectChanges();

不知道有没有人会笑话我,实际上这段代码和上面的代码是一个效果哦。

那么我们再看看这段代码呢?

tb.Rows[0].Delete();            
tb.Rows.RemoveAt(
1);
tb.Rows.RemoveAt(
2);
tb.RejectChanges();

我们把所有的AcceptChanges()方法都给去掉了,那么只剩下RejectChanages()方法了,会是什么样的结果呢?
结果返回空记录了,为什么呢????

其实在前面最早是无已经给出定义了,不知道的同学是太粗心了哦。自己去看哦。