using (Instrucción, Referencia de C#)

Ofrece una sintaxis adecuada que garantiza el uso correcto de objetos IDisposable. A partir de C# 8.0, la instrucción using garantiza el uso correcto de los objetos IAsyncDisposable.

Ejemplo

En el ejemplo siguiente se muestra cómo usar la instrucción using.

string manyLines = @"This is line one
This is line two
Here is line three
The penultimate line is line four
This is the final, fifth line.";

using (var reader = new StringReader(manyLines))
{
    string? item;
    do
    {
        item = reader.ReadLine();
        Console.WriteLine(item);
    } while (item != null);
}

La declaración using, que se introdujo en C# 8.0, no requiere llaves:

string manyLines = @"This is line one
This is line two
Here is line three
The penultimate line is line four
This is the final, fifth line.";

using var reader = new StringReader(manyLines);
string? item;
do
{
    item = reader.ReadLine();
    Console.WriteLine(item);
} while (item != null);

Comentarios

File y Font son ejemplos de tipos administrados que acceden a recursos no administrados (en este caso, identificadores de archivo y contextos de dispositivo). Hay muchos otros tipos de recursos no administrados y tipos de la biblioteca de clases que los encapsulan. Todos estos tipos deben implementar la interfaz IDisposable o la interfaz IAsyncDisposable.

Cuando la duración de un IDisposable objeto se limita a un único método, debe declararlo y crear una instancia de él en la using instrucción o using declaración. La using declaración llama al Dispose método en el objeto de la manera correcta cuando sale del ámbito. La using instrucción hace que el propio objeto salga del ámbito tan pronto como Dispose se llame. Dentro del bloque using, el objeto es de solo lectura y no se puede modificar ni reasignar. Una variable declarada con una using declaración es de solo lectura. Si el objeto implementa en lugar de , cualquiera de los formularios IAsyncDisposable llama a DisposeAsync y awaits al devueltoValueTask.usingIDisposable Para obtener más información sobre IAsyncDisposable, vea Implementación de un método DisposeAsync.

Ambos using formularios garantizan que Dispose se llame a (o DisposeAsync) incluso si se produce una excepción dentro del using bloque . Puede lograr el mismo resultado colocando el objeto dentro de un try bloque y, a continuación, llamando a Dispose (o DisposeAsync) en un finally bloque; de hecho, esta es la forma en que el compilador traduce la using instrucción y la using declaración. El ejemplo de código anterior se extiende al siguiente código en tiempo de compilación (tenga en cuenta las llaves adicionales para crear el ámbito limitado del objeto):

string manyLines = @"This is line one
This is line two
Here is line three
The penultimate line is line four
This is the final, fifth line.";

{
    var reader = new StringReader(manyLines);
    try
    {
        string? item;
        do
        {
            item = reader.ReadLine();
            Console.WriteLine(item);
        } while (item != null);
    }
    finally
    {
        reader?.Dispose();
    }
}

La nueva sintaxis de la instrucción using se traduce en un código similar. Se abre el bloque try en el que se declara la variable. El bloque finally se agrega al cierre del bloque de inclusión, normalmente, al final de un método.

Consulte el artículo sobre try-finally para obtener más información sobre la instrucción try-finally.

Se pueden declarar varias instancias de un tipo en una sola instrucción using, tal y como se muestra en el ejemplo siguiente. Tenga en cuenta que no se pueden usar variables con tipo implícito (var) cuando se declaran varias variables en una sola instrucción:

string numbers = @"One
Two
Three
Four.";
string letters = @"A
B
C
D.";

using (StringReader left = new StringReader(numbers),
    right = new StringReader(letters))
{
    string? item;
    do
    {
        item = left.ReadLine();
        Console.Write(item);
        Console.Write("    ");
        item = right.ReadLine();
        Console.WriteLine(item);
    } while (item != null);
}

También puede combinar varias declaraciones del mismo tipo mediante la sintaxis de declaración introducida con C# 8, como se muestra en el ejemplo siguiente:

string numbers = @"One
Two
Three
Four.";
string letters = @"A
B
C
D.";

using StringReader left = new StringReader(numbers),
    right = new StringReader(letters);
string? item;
do
{
    item = left.ReadLine();
    Console.Write(item);
    Console.Write("    ");
    item = right.ReadLine();
    Console.WriteLine(item);
} while (item != null);

Puede crear una instancia del objeto de recurso y luego pasar la variable a la instrucción using, pero esto no es un procedimiento recomendado. En este caso, después de que el control abandone el bloque using el objeto permanece en el ámbito, pero probablemente ya no tenga acceso a sus recursos no administrados. En otras palabras, ya no se inicializa totalmente. Si intenta usar el objeto fuera del bloque using, corre el riesgo de iniciar una excepción. Por este motivo, es mejor crear una instancia del objeto en la instrucción using y limitar su ámbito al bloque using.

string manyLines = @"This is line one
This is line two
Here is line three
The penultimate line is line four
This is the final, fifth line.";

var reader = new StringReader(manyLines);
using (reader)
{
    string? item;
    do
    {
        item = reader.ReadLine();
        Console.WriteLine(item);
    } while (item != null);
}
// reader is in scope here, but has been disposed

Para obtener más información sobre cómo eliminar objetos IDisposable, vea Uso de objetos que implementan IDisposable.

Especificación del lenguaje C#

Para obtener más información, vea el apartado Instrucción using en la Especificación del lenguaje C#. La especificación del lenguaje es la fuente definitiva de la sintaxis y el uso de C#.

Vea también