先不多说,看一段代码:
Default.aspx

 1 <%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" %>
 2 
 3 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
 4 <html xmlns="http://www.w3.org/1999/xhtml">
 5 <head runat="server">
 6     <title></title>
 7 </head>
 8 <body>
 9     <form id="F" runat="server">
10     <div>
11         <asp:GridView ID="GV" runat="server" Width="250px" AutoGenerateColumns="false">
12             <Columns>
13                 <asp:TemplateField HeaderText="Name">
14                     <ItemTemplate>
15                         <asp:TextBox ID="tbName" runat="server" Text='<%#Bind("Name") %>'></asp:TextBox>
16                     </ItemTemplate>
17                 </asp:TemplateField>
18                 <asp:TemplateField HeaderText="Age">
19                     <ItemTemplate>
20                         <asp:TextBox ID="tbAge" runat="server" Text='<%#Bind("Age") %>'>
21                         </asp:TextBox></ItemTemplate>
22                 </asp:TemplateField>
23             </Columns>
24         </asp:GridView>
25         <br />
26         <asp:Button ID="Button1" runat="server" Text="Save" Width="143px" 
27             onclick="Button1_Click" />
28     </div>
29     </form>
30 </body>
31 </html>
32 

后台代码:Default.aspx.cs
 1 using System;
 2 using System.Collections.Generic;
 3 using System.Linq;
 4 using System.Web;
 5 using System.Web.UI;
 6 using System.Web.UI.WebControls;
 7 
 8 public class Person
 9 {
10     public string Name { getset; }
11     public int Age { getset; }
12 }
13 
14 public partial class _Default : System.Web.UI.Page
15 {
16     public List<Person> GetData()
17     {
18         return new List<Person>
19                     {
20                         new Person{Name="CsharpFarmer",Age=26},
21                         new Person{Name="Rose",Age=24}
22                     };
23     }
24 
25     protected void Page_Load(object sender, EventArgs e)
26     {
27         GV.DataSource = this.GetData();
28         GV.DataBind();
29     }
30 
31     protected void Button1_Click(object sender, EventArgs e)
32     {
33         var data = this.GetData();
34         data.Clear();
35         foreach (GridViewRow gvr in GV.Rows)
36         {
37             data.Add(new Person { Name = ((TextBox)gvr.FindControl("tbName")).Text, Age = int.Parse(((TextBox)gvr.FindControl("tbAge")).Text) });
38         }
39         GV.DataSource = data;
40         GV.DataBind();
41     }
42 }

取一段数据,然后绑定在GridView中,最后进行修改.
事实上无论我们怎么样点Save,我们会发现,数据始终没有变动,为什么呢?

要搞清这个问题,先看一下控件的生命周期.


从这幅图,可以看出,ViewState和PostBack Data(回传数据)在PageLoad之前已经被执行,
当运行到PageLoad时,我们手动输入的数据被重置了,而按钮的事件RaisePostBackEvent发生在PageLoad之后,
所以,我们的数据始没法保存了.
那么怎么解决呢?
方法有三:
1)在PageLoad里加上if(!IsPostBack){......},注意,此时EnableViewState必须设为true;
这样你修改的数据在PageLoad里回传的时候,不会再被重置
2)将PageLoad里的代码移到RaisePostBackEvent后面,通常放在OnPreRender里机,
这样,回传的数据在保存之后,再次绑定.
注意第三种方法
3)将GridView的EnableViewState设为false.
为什么?
其实要知道第三种方法,必须搞清动态控件了.
因为禁用了ViewState,GridView在运行到PageLoad之前,是没有任何数据的,当在PageLoad里绑定之后,生成了子控件,
大家都知道,动态控件的ViewState或回传值是在pageLoad之后和PageLoadComplete之前加载的,而RaisePostBackEvent发生在
PageLoadComplete 之后,所以能保存到你修改的数据了.

以是只是个人看法,有什么不对的地方,请指教.