Compartir a través de


Atributos

Los atributos proporcionan un método eficaz para asociar metadatos o información declarativa, con código (ensamblados, tipos, métodos, propiedades, etc.). Después de asociar un atributo a una entidad de programa, el atributo se puede consultar en tiempo de ejecución mediante una técnica denominada reflexión.

Los atributos tienen las siguientes propiedades:

  • Los atributos agregan metadatos al programa. Metadatos son información sobre los tipos definidos en un programa. Todos los ensamblados de .NET contienen un conjunto especificado de metadatos que describe los tipos y miembros de tipo definidos en el ensamblado. Puede agregar atributos personalizados para especificar cualquier información adicional necesaria.
  • Puede aplicar uno o más atributos a ensamblados, módulos o elementos de programa más pequeños, como clases y propiedades.
  • Los atributos pueden aceptar argumentos de la misma manera que los métodos y propiedades.
  • El programa puede examinar sus propios metadatos o los metadatos de otros programas mediante la reflexión.

Reflection proporciona objetos (de tipo Type) que describen ensamblados, módulos y tipos. Puede usar la reflexión para crear dinámicamente una instancia de un tipo, enlazar el tipo a un objeto existente o obtener el tipo de un objeto existente e invocar sus métodos o acceder a sus campos y propiedades. Si usa atributos en el código, la reflexión le permite acceder a ellos. Para obtener más información, vea atributos de .

Este es un ejemplo sencillo de reflexión mediante el método GetType() , heredado por todos los tipos de la clase base Object , para obtener el tipo de una variable:

Nota

Asegúrese de agregar using System; y using System.Reflection; en la parte superior del archivo .cs.

// Using GetType to obtain type information:
int i = 42;
Type type = i.GetType();
Console.WriteLine(type);

La salida es: System.Int32.

En el ejemplo siguiente se usa la reflexión para obtener el nombre completo del ensamblado cargado.

// Using Reflection to get information of an Assembly:
Assembly info = typeof(int).Assembly;
Console.WriteLine(info);

La salida es similar a esta: System.Private.CoreLib, Version=7.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e.

Nota

Las palabras clave de C# protected y internal no tienen ningún significado en el lenguaje intermedio (IL) y no se usan en las API de reflexión. Los términos correspondientes en IL son Family y Assembly. Para identificar un método internal mediante la reflexión, use la propiedad IsAssembly. Para identificar un método protected internal, use IsFamilyOrAssembly.

Uso de atributos

Los atributos se pueden colocar en casi cualquier declaración, aunque un atributo específico podría restringir los tipos de declaraciones en las que es válido. En C#, especifique un atributo colocando el nombre del atributo entre corchetes ([]) encima de la declaración de la entidad a la que se aplica.

En este ejemplo, el atributo SerializableAttribute se usa para aplicar una característica específica a una clase:

[Serializable]
public class SampleClass
{
    // Objects of this type can be serialized.
}

Un método con el atributo DllImportAttribute se declara como en el ejemplo siguiente:

[System.Runtime.InteropServices.DllImport("user32.dll")]
extern static void SampleMethod();

Se puede colocar más de un atributo en una declaración, como se muestra en el ejemplo siguiente:

void MethodA([In][Out] ref double x) { }
void MethodB([Out][In] ref double x) { }
void MethodC([In, Out] ref double x) { }

Algunos atributos se pueden especificar más de una vez para una entidad determinada. Un ejemplo de este atributo multiuso es ConditionalAttribute:

[Conditional("DEBUG"), Conditional("TEST1")]
void TraceMethod()
{
    // ...
}

Nota

Por convención, todos los nombres de atributo terminan con la palabra "Attribute" para distinguirlos de otros elementos de las bibliotecas de .NET. Sin embargo, no es necesario especificar el sufijo de atributo al usar atributos en el código. Por ejemplo, [DllImport] equivale a [DllImportAttribute], pero DllImportAttribute es el nombre real del atributo en la biblioteca de clases de .NET.

Parámetros de atributo

Muchos atributos tienen parámetros, que pueden ser posicionales, sin nombre o con nombre. Los parámetros posicionales deben especificarse en un orden determinado y no se pueden omitir. Los parámetros con nombre son opcionales y se pueden especificar en cualquier orden. Los parámetros posicionales se especifican primero. Por ejemplo, estos tres atributos son equivalentes:

[DllImport("user32.dll")]
[DllImport("user32.dll", SetLastError=false, ExactSpelling=false)]
[DllImport("user32.dll", ExactSpelling=false, SetLastError=false)]

El primer parámetro, el nombre del archivo DLL, es posicional y siempre viene primero; los demás son nombrados. En este caso, ambos parámetros con nombre tienen como valor predeterminado false, por lo que se pueden omitir. Los parámetros posicionales corresponden a los parámetros del constructor de atributos. Los parámetros con nombre o opcionales corresponden a propiedades o campos del atributo . Consulte la documentación del atributo individual para obtener información sobre los valores de parámetro predeterminados.

Para obtener más información sobre los tipos de parámetros permitidos, consulte la sección Atributos de de la especificación del lenguaje C# .

Destinos de atributo

El destino de un atributo es la entidad a la que se aplica el atributo. Por ejemplo, un atributo puede aplicarse a una clase, a un método determinado o a un ensamblado completo. De forma predeterminada, un atributo se aplica al elemento que lo sigue. Pero también puede identificar explícitamente, por ejemplo, si se aplica un atributo a un método o a su parámetro o a su valor devuelto.

Para identificar explícitamente un destino de atributo, use la sintaxis siguiente:

[target : attribute-list]

La lista de posibles valores de target se muestra en la tabla siguiente.

Valor del objetivo Se aplica a
assembly Ensamblado completo
module Módulo de ensamblado actual
field Campo de una clase o un struct
event Evento
method Método o descriptores de acceso de propiedad get y set
param Parámetros de método o parámetros de descriptor de acceso de propiedad set
property Propiedad
return Valor devuelto de un método, indexador de propiedad o descriptor de acceso de propiedad get
type Estructura, clase, interfaz, enumeración o delegado

Especificaría el valor de destino field para aplicar un atributo al campo de respaldo creado para una propiedad implementada automáticamente.

En el ejemplo siguiente se muestra cómo aplicar atributos a ensamblados y módulos. Para obtener más información, vea Atributos comunes (C#).

using System;
using System.Reflection;
[assembly: AssemblyTitleAttribute("Production assembly 4")]
[module: CLSCompliant(true)]

En el ejemplo siguiente se muestra cómo aplicar atributos a métodos, parámetros de método y valores devueltos de método en C#.

// default: applies to method
[ValidatedContract]
int Method1() { return 0; }

// applies to method
[method: ValidatedContract]
int Method2() { return 0; }

// applies to parameter
int Method3([ValidatedContract] string contract) { return 0; }

// applies to return value
[return: ValidatedContract]
int Method4() { return 0; }

Nota

Independientemente de los destinos en los que se defina ValidatedContract para que sea válido, el destino return debe especificarse, incluso si ValidatedContract se definiera para aplicar solo a los valores devueltos. En otras palabras, el compilador no usará la información AttributeUsage para resolver destinos de atributo ambiguos. Para obtener más información, vea AttributeUsage.

Usos comunes para atributos

En la lista siguiente se incluyen algunos de los usos comunes de atributos en el código:

  • Marcar métodos mediante el atributo WebMethod en servicios web para indicar que el método debe llamarse a través del protocolo SOAP. Para obtener más información, consulte WebMethodAttribute.
  • Describir cómo manejar parámetros de método al interoperar con código nativo. Para obtener más información, consulte MarshalAsAttribute.
  • Describir las propiedades COM para clases, métodos e interfaces.
  • Llamada a código no administrado mediante la clase DllImportAttribute.
  • Describir el ensamblado en términos de título, versión, descripción o marca comercial.
  • Describir qué miembros de una clase serializar para la persistencia.
  • Describir cómo realizar asignaciones entre los miembros de clase y los nodos XML para la serialización XML.
  • Descripción de los requisitos de seguridad de los métodos.
  • Especificación de características usadas para aplicar la seguridad.
  • Controlar optimizaciones mediante el compilador Just-In-Time (JIT) para que el código siga siendo fácil de depurar.
  • Obtener información sobre el llamador de un método.

Visión general de la reflexión

La reflexión es útil en las siguientes situaciones:

Para obtener más información: