Share via


Tutorial: Conservar un objeto (C# y Visual Basic)

Aunque en tiempo de diseño se pueden establecer las propiedades de un objeto en valores predeterminados, cualquier valor introducido en tiempo de ejecución se pierde cuando se destruye el objeto. Puede usar la serialización para conservar los datos de un objeto entre las instancias, lo que permite almacenar valores y recuperarlos la próxima vez que se cree una instancia del objeto.

Nota

En Visual Basic, para almacenar datos simples, como un nombre o un número, puede usar el objeto My.Settings. Para obtener más información, vea My.Settings (Objeto) (Visual Basic).

En este tutorial, creará un objeto Loan simple y guardará sus datos en un archivo. Recuperará a continuación los datos del archivo al volver a crear el objeto. Por último, modificará el código para almacenar el objeto con un formato SOAP.

Nota de seguridadNota sobre la seguridad

En este ejemplo se crea un nuevo archivo, si es que aún no existe. Si una aplicación debe crear un archivo, necesitará tener permisos Create en la carpeta correspondiente. Los permisos se establecen usando listas de control de acceso. Sin embargo, si el archivo ya existe, la aplicación sólo precisará el permiso de Write, un permiso menor. Por tanto, siempre que sea posible, resulta más seguro crear el archivo durante la implementación y conceder sólo permisos Read a un único archivo (en lugar de conceder permisos Create a una carpeta). También es más seguro escribir datos en carpetas de usuario en lugar de en la carpeta raíz o en la carpeta Archivos de programa.

Nota de seguridadNota sobre la seguridad

En este ejemplo se almacenan datos en un formato de archivo binario o SOAP. Estos formatos no se deben usar con datos confidenciales, como contraseñas o información de la tarjeta de crédito.

Nota

Los cuadros de diálogo y comandos de menú que se ven pueden diferir de los descritos en la Ayuda, en función de los valores de configuración o de edición activos. Para cambiar su configuración, haga clic en Importar y exportar configuraciones en el menú Herramientas. Para obtener más información, vea Valores de configuración de Visual Studio.

Crear el objeto Loan

El primer paso consiste en crear una clase Loan y una aplicación de prueba que utilice esta clase.

Para crear la clase Loan

  1. Cree un nuevo proyecto Biblioteca de clases y denomínelo "LoanClass". Para obtener más información, vea Cómo: Crear soluciones y proyectos.

  2. En el Explorador de soluciones, haga clic con el botón secundario del mouse en el archivo Class1 y, a continuación, haga clic en Cambiar nombre. Cambie el nombre del archivo a Loan y, a continuación, presione ENTRAR. Al cambiar el nombre del archivo también se cambiará el nombre de la clase a Loan.

  3. Agregue a la clase los miembros públicos siguientes:

    Public Class Loan
        Implements System.ComponentModel.INotifyPropertyChanged
    
        Public Property LoanAmount As Double
        Public Property InterestRate As Double
        Public Property Term As Integer
    
        Private p_Customer As String
        Public Property Customer As String
            Get
                Return p_Customer
            End Get
            Set(ByVal value As String)
                p_Customer = value
                RaiseEvent PropertyChanged(Me,
                  New System.ComponentModel.PropertyChangedEventArgs("Customer"))
            End Set
        End Property
    
        Event PropertyChanged As System.ComponentModel.PropertyChangedEventHandler _
          Implements System.ComponentModel.INotifyPropertyChanged.PropertyChanged
    
        Public Sub New(ByVal loanAmount As Double,
                       ByVal interestRate As Double,
                       ByVal term As Integer,
                       ByVal customer As String)
    
            Me.LoanAmount = loanAmount
            Me.InterestRate = interestRate
            Me.Term = term
            p_Customer = customer
        End Sub
    End Class
    
    public class Loan : System.ComponentModel.INotifyPropertyChanged
    {
        public double LoanAmount {get; set;}
        public double InterestRate {get; set;}
        public int Term {get; set;}
    
        private string p_Customer;
        public string Customer
        {
            get { return p_Customer; }
            set 
            {
                p_Customer = value;
                PropertyChanged(this,
                  new System.ComponentModel.PropertyChangedEventArgs("Customer"));
            }
        }
    
        public event System.ComponentModel.PropertyChangedEventHandler PropertyChanged;
    
        public Loan(double loanAmount,
                    double interestRate,
                    int term,
                    string customer)
        {
            this.LoanAmount = loanAmount;
            this.InterestRate = interestRate;
            this.Term = term;
            p_Customer = customer;
        }
    }
    

También tendrá que crear una aplicación simple que utilice la clase Loan.

Para crear una aplicación de prueba

  1. Para agregar a la solución un proyecto de aplicación de Windows Forms, en el menú Archivo, elija Agregar y, a continuación, haga clic en Nuevo proyecto.

  2. En el cuadro de diálogo Agregar nuevo proyecto, escriba LoanApp como el nombre del proyecto y haga clic en Aceptar para cerrar el cuadro de diálogo.

  3. En el Explorador de soluciones, seleccione el proyecto LoanApp.

  4. En el menú Proyecto, haga clic en Establecer como proyecto de inicio.

  5. Haga clic en la opción Agregar referencia del menú Proyecto.

  6. En el cuadro de diálogo Agregar referencia, haga clic en la ficha Proyectos y seleccione el proyecto LoanClass.

  7. Haga clic en Aceptar para cerrar el cuadro de diálogo.

  8. En el diseñador, agregue cuatro controles TextBox al formulario.

  9. En el Editor de códigos, agregue el siguiente código:

    Private WithEvents TestLoan As New LoanClass.Loan(10000.0, 0.075, 36, "Neil Black")
    
    Private Sub Form1_Load() Handles MyBase.Load
        TextBox1.Text = TestLoan.LoanAmount.ToString
        TextBox2.Text = TestLoan.InterestRate.ToString
        TextBox3.Text = TestLoan.Term.ToString
        TextBox4.Text = TestLoan.Customer
    End Sub
    
    private LoanClass.Loan TestLoan = new LoanClass.Loan(10000.0, 0.075, 36, "Neil Black");
    
    private void Form1_Load(object sender, EventArgs e)
    {
        textBox1.Text = TestLoan.LoanAmount.ToString();
        textBox2.Text = TestLoan.InterestRate.ToString();
        textBox3.Text = TestLoan.Term.ToString();
        textBox4.Text = TestLoan.Customer;
    }
    
  10. Agregue al formulario un controlador de eventos para el evento PropertyChanged mediante el siguiente código:

    Public Sub CustomerPropertyChanged(
          ByVal sender As Object,
          ByVal e As System.ComponentModel.PropertyChangedEventArgs
        ) Handles TestLoan.PropertyChanged
    
        MsgBox(e.PropertyName & " has been changed.")
    End Sub
    
    private void CustomerPropertyChanged(object sender, 
        System.ComponentModel.PropertyChangedEventArgs e)
    {
        MessageBox.Show(e.PropertyName + " has been changed.");
    }
    

Llegado este punto, puede generar y ejecutar la aplicación. Observe que los valores predeterminados de la clase Loan aparecen en los cuadros de texto. Pruebe a cambiar el valor del tipo de interés de 7,5 a 7,1 y, a continuación, cierre la aplicación y ejecútela de nuevo; el valor vuelve a ser el predeterminado de 7,5.

En el mundo real, los tipos de interés cambian periódicamente, pero no forzosamente cada vez que se ejecuta la aplicación. En lugar de hacer que el usuario actualice el tipo de interés cada vez que se ejecute la aplicación, sería mejor guardar el tipo de interés más reciente entre las instancias de la aplicación. En el paso siguiente, hará exactamente eso agregando la serialización a la clase Loan.

Usar serialización para guardar el objeto

Para guardar los valores de la clase Loan, primero debe marcarse la clase con el atributo Serializable.

Para marcar una clase como serializable

  • Cambie la declaración de la clase Loan del modo siguiente:

    <Serializable()>
    Public Class Loan
    
    [Serializable()]
    public class Loan : System.ComponentModel.INotifyPropertyChanged
    {
    

El atributo Serializable indica al compilador que todo el contenido de la clase se puede guardar en un archivo. Dado que el evento PropertyChanged lo controla un objeto de Windows Forms, no es posible serializarlo. El atributo NonSerialized se puede utilizar para marcar miembros de clase que no deberían guardarse.

Para evitar que un miembro se serialice

  • Cambie la declaración del evento PropertyChanged del modo siguiente:

    <NonSerialized()>
    Event PropertyChanged As System.ComponentModel.PropertyChangedEventHandler _
      Implements System.ComponentModel.INotifyPropertyChanged.PropertyChanged
    
    [field: NonSerialized()]
    public event System.ComponentModel.PropertyChangedEventHandler PropertyChanged;
    

El paso siguiente es agregar el código de serialización a la aplicación LoanApp. Para serializar la clase y escribirla en un archivo, utilizará los espacios de nombres System.IO y System.Xml.Serialization. Para evitar que tenga que escribir nombres completos, puede agregar referencias a las bibliotecas de clases necesarias.

Para agregar referencias a espacios de nombres

  • Agregue las siguientes instrucciones al principio de la clase Form1:

    Imports System.IO
    Imports System.Runtime.Serialization.Formatters.Binary
    
    using System.IO;
    using System.Runtime.Serialization.Formatters.Binary;
    

    En este caso, está usando un formateador para guardar el objeto en un formato binario. Más adelante en este tutorial modificará el código para guardar el objeto en un formato SOAP.

El paso siguiente es agregar código para deserializar el objeto del archivo cuando se cree.

Para deserializar un objeto

  1. Agregue una constante a la clase para el nombre de archivo de datos serializados.

    Const FileName As String = "..\..\SavedLoan.bin"
    
    const string FileName = @"..\..\SavedLoan.bin";
    
  2. Modifique el código del procedimiento de evento Form1_Load del modo siguiente:

    Private WithEvents TestLoan As New LoanClass.Loan(10000.0, 0.075, 36, "Neil Black")
    
    Private Sub Form1_Load() Handles MyBase.Load
        If File.Exists(FileName) Then
            Dim TestFileStream As Stream = File.OpenRead(FileName)
            Dim deserializer As New BinaryFormatter
            TestLoan = CType(deserializer.Deserialize(TestFileStream), LoanClass.Loan)
            TestFileStream.Close()
        End If
    
        AddHandler TestLoan.PropertyChanged, AddressOf Me.CustomerPropertyChanged
    
        TextBox1.Text = TestLoan.LoanAmount.ToString
        TextBox2.Text = TestLoan.InterestRate.ToString
        TextBox3.Text = TestLoan.Term.ToString
        TextBox4.Text = TestLoan.Customer
    End Sub
    
    private LoanClass.Loan TestLoan = new LoanClass.Loan(10000.0, 0.075, 36, "Neil Black");
    
    private void Form1_Load(object sender, EventArgs e)
    {
        if (File.Exists(FileName))
        {
            Stream TestFileStream = File.OpenRead(FileName);
            BinaryFormatter deserializer = new BinaryFormatter();
            TestLoan = (LoanClass.Loan)deserializer.Deserialize(TestFileStream);
            TestFileStream.Close();
        }
    
        TestLoan.PropertyChanged += this.CustomerPropertyChanged;
    
        textBox1.Text = TestLoan.LoanAmount.ToString();
        textBox2.Text = TestLoan.InterestRate.ToString();
        textBox3.Text = TestLoan.Term.ToString();
        textBox4.Text = TestLoan.Customer;
    }
    

    Observe que primero tiene que comprobar que el archivo existe. Si es así, cree una clase Stream para leer el archivo binario y una clase BinaryFormatter para traducirlo. Asimismo, deberá convertir el tipo de la secuencia en el tipo del objeto Loan.

A continuación, tiene que agregar código para guardar los datos introducidos en los cuadros de texto de la clase Loan y, a continuación, debe serializar la clase en un archivo.

Para guardar los datos y serializar la clase

  • Agregue el siguiente código al procedimiento de evento Form1_FormClosing:

    Private Sub Form1_FormClosing() Handles MyBase.FormClosing
        TestLoan.LoanAmount = CDbl(TextBox1.Text)
        TestLoan.InterestRate = CDbl(TextBox2.Text)
        TestLoan.Term = CInt(TextBox3.Text)
        TestLoan.Customer = TextBox4.Text
    
        Dim TestFileStream As Stream = File.Create(FileName)
        Dim serializer As New BinaryFormatter
        serializer.Serialize(TestFileStream, TestLoan)
        TestFileStream.Close()
    End Sub
    
    private void Form1_FormClosing(object sender, FormClosingEventArgs e)
    {
        TestLoan.LoanAmount = Convert.ToDouble(textBox1.Text);
        TestLoan.InterestRate = Convert.ToDouble(textBox2.Text);
        TestLoan.Term = Convert.ToInt32(textBox3.Text);
        TestLoan.Customer = textBox4.Text;
    
        Stream TestFileStream = File.Create(FileName);
        BinaryFormatter serializer = new BinaryFormatter();
        serializer.Serialize(TestFileStream, TestLoan);
        TestFileStream.Close();
    }
    

Llegado este punto, puede volver a generar y ejecutar la aplicación. Inicialmente, los valores predeterminados aparecen en los cuadros de texto. Pruebe a cambiar los valores e introducir un nombre en el cuarto cuadro de texto. Cierre la aplicación y, a continuación, ejecútela de nuevo. Observe que los nuevos valores aparecen ahora en los cuadros de texto.

Guardar el objeto con un formato SOAP

En este ejemplo se ha mostrado hasta ahora cómo guardar un objeto en un archivo de texto usando un formato binario, que resulta correcto para la mayoría de las aplicaciones Windows; sin embargo, para las aplicaciones web o los servicios Web, es conveniente guardar el objeto en un archivo XML con un formato SOAP, lo que facilita el uso compartido del objeto.

Para guardar el objeto en un formato SOAP, primero debe hacerse referencia a la clase SoapFormatter. La clase SoapFormatter reside en su propio espacio de nombres: System.Runtime.Serialization.Formatters.Soap.

Para guardar el objeto con un formato SOAP

  1. En el Explorador de soluciones, seleccione el proyecto LoanApp.

  2. Haga clic en la opción Agregar referencia del menú Proyecto.

  3. En el cuadro de diálogo Agregar referencia, haga clic en la ficha .NET y seleccione el componente System.Runtime.Serialization.Formatters.Soap.

  4. Haga clic en Aceptar para cerrar el cuadro de diálogo.

  5. En el Editor de código, agregue la siguiente instrucción al principio del módulo Form1:

    Imports System.Runtime.Serialization.Formatters.Soap
    
    using System.Runtime.Serialization.Formatters.Soap;
    
  6. Cambie el nombre de archivo de SavedLoan.bin a SavedLoan.xml.

  7. En el procedimiento de evento Form1_Load, cambie la declaración de la variable deserializer a:

    Dim deserializer As New SoapFormatter
    
    SoapFormatter deserializer = new SoapFormatter();
    
  8. En el procedimiento de evento Form1_FormClosing, cambie la declaración de la variable serializer a:

    Dim serializer As New SoapFormatter
    
    SoapFormatter serializer = new SoapFormatter();
    

Llegado este punto, puede generar y probar la aplicación. La primera vez que ejecute la aplicación, se creará el archivo SavedLoan.xml. Para ver el archivo, elija la opción Mostrar todos los archivos en el Explorador de soluciones; se encuentra en el nodo Bin del proyecto de aplicación para Windows.

Nota

Si ya se encuentra en el modo Mostrar todos los archivos, para ver el archivo tendrá que actualizar la vista; para ello, seleccione Actualizar en el menú Ver.

Observe que los tres miembros de la clase LoanClass se muestran en formato XML. Cambie el valor de InterestRate en el archivo XML, a continuación guárdelo y ejecute la aplicación de nuevo. El nuevo tipo de interés aparecerá en el segundo cuadro de texto.

Vea también

Conceptos

Guía de programación de C#

Otros recursos

Serialización (C# y Visual Basic)

Guía de programación en Visual Basic