Scope of variables in aspx.cs file

2019-03-03 15:42发布

问题:

I am writing following code:

namespace WebApplication5
{
    public partial class WebForm1 : System.Web.UI.Page
    {
        private DataSet dataset1 = new DataSet();
        OleDbDataAdapter adapter;

        public DataSet ds
        {
            get { return dataset1; }
            set { dataset1 = value; }
        }

        protected void Page_Load(object sender, EventArgs e)
        {
        }

        protected void Button1_Click(object sender, EventArgs e)
        {
            OleDbConnection con = new OleDbConnection();
            con.ConnectionString = @"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\jayant\Documents\User_Details.accdb";
            con.Open();
            adapter = new OleDbDataAdapter("Select * from User_Details",con);
            adapter.Fill(ds);
            GridView1.DataSource = ds;
            GridView1.DataBind();
           //  ds.WriteXml("C:\\MyUser_Details.xml"); If I do this here it writes data
            con.Close();
        }

        protected void Button2_Click(object sender, EventArgs e)
        {
            ds.WriteXml("C:\\MyUser_Details.xml");
            // no data in xml files, just root tags
        }
    }
}

Here my DataSet variable is global but when I am clicking on button2, it sends no data to the Ouput XML file. Can you please tell me why? Or what modifications shall I make to perform this?

Thanks

回答1:

You need to have a look at Asp.net page life cycle, In your code when you click on your button page is destroyed and re created again and whole life cycle is followed and in that process your ds(dataset) is recreated too, therefore output xml doesn't have any data in it. To maintain state of your dataset have a look at State Management in Asp.net



回答2:

It is because you create a new Dataset during postback.

move the initialization of the Dataset private DataSet dataset1= new DataSet();

in to the Load

protected void Page_Load(object sender, EventArgs e)
    {
         if(!Page.IsPostBack) { dataset1= new DataSet(); }
    }

and obviously, don`t forget to click Button1 before you click Button2 :)



回答3:

Yes you are partially correct that your ds is Global but only for life time of Web Page. Once the page is rendered and sent to client, your page is disposed and hence with it the variable.

If you want to ds to be available in button_click event, either populate it inside Page_Load event

protected void Page_Load(object sender, EventArgs e)
{ 
           OleDbConnection con = new OleDbConnection();
           con.ConnectionString = @"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\jayant\Documents\User_Details.accdb";
            con.Open();
            adapter = new OleDbDataAdapter("Select * from User_Details",con);
            adapter.Fill(ds);
            con.close();
}

Or generate the dataset in your Button_Click event handler.

If you do not want to generate this data set every time, you have to either keep this variable in Session or ViewState or Cache

UPDATE 1

The third and last option could be to make this dataset variable as class level variable i.e static and it would be available all the time



回答4:

You don't get Data in the dataset in button2_click because button1_click and button2_clicks are entirely different requests to the server. And asp.net does not persists data stored in variables between requests. If you need to persist data you should use any State Management techniques provided by asp.net, like Session or Viewstate or Caching.



回答5:

I suggest please use ViewState as Session will consume lot of server memory, though you can use any one of them to solve the purpose.

I don't think button1's event handler is doing anything apart from creating ds. So only one event handler will solve the purpose.

Another way to access ds in both the event handlers without losing data is declare ds as static. But this mechanism does not suit this scenario.



回答6:

 protected void Button1_Click(object sender, EventArgs e)
    {
        OleDbConnection con = new OleDbConnection();
        con.ConnectionString = @"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\jayant\Documents\User_Details.accdb";
        con.Open();
        adapter = new OleDbDataAdapter("Select * from User_Details",con);
        adapter.Fill(ds);
        GridView1.DataSource = ds;
        Session.Add("Dataset", ds); //Adding Session here
        GridView1.DataBind();
        con.Close();
    }

    protected void Button2_Click(object sender, EventArgs e)
    {
        DataSet ds = (DataSet)Session["Dataset"]; //Retrieving Value from session
        ds.WriteXml("C:\\MyUser_Details.xml");
    }