web-dev-qa-db-fra.com

Comment tester si un type est anonyme?

J'ai la méthode suivante qui sérialise un objet en une balise HTML. Je veux seulement le faire si le type n'est pas anonyme.

private void MergeTypeDataToTag(object typeData)
{
    if (typeData != null)
    {
        Type elementType = typeData.GetType();

        if (/* elementType != AnonymousType */)
        {
            _tag.Attributes.Add("class", elementType.Name);    
        }

        // do some more stuff
    }
}

Quelqu'un peut-il me montrer comment y parvenir?

Merci

66
DaveDev

De http://www.liensberger.it/web/blog/?p=191 :

private static bool CheckIfAnonymousType(Type type)
{
    if (type == null)
        throw new ArgumentNullException("type");

    // HACK: The only way to detect anonymous types right now.
    return Attribute.IsDefined(type, typeof(CompilerGeneratedAttribute), false)
        && type.IsGenericType && type.Name.Contains("AnonymousType")
        && (type.Name.StartsWith("<>") || type.Name.StartsWith("VB$"))
        && type.Attributes.HasFlag(TypeAttributes.NotPublic);
}

ÉDITER:
Un autre lien avec la méthode d'extension: Déterminer si un type est un type anonyme

61
Sunny

Rapide et sale:

if(obj.GetType().Name.Contains("AnonymousType"))
14
BjarkeCK

Vous pouvez simplement vérifier si l'espace de noms est nul.

public static bool IsAnonymousType(this object instance)
{

    if (instance==null)
        return false;

    return instance.GetType().Namespace == null;
}
9
DalSoft

Eh bien, aujourd'hui, compiier génère des types anonymes en tant que classes génériques ET scellées. Une combinaison paradoxale puisque la spécialisation d'une classe générique est une sorte d'héritage, n'est-ce pas? Vous pouvez donc vérifier ceci: 1. Est-ce un type générique? Oui => 2) sa définition est-elle scellée et n'est-elle pas publique? Oui => 3) sa définition a-t-elle l'attribut CompilerGeneratedAttribute? Je suppose que si ces 3 critères sont vrais ensemble, nous avons un type anonyme ... Eh bien ... Il y a un problème avec TOUTES les méthodes décrites - ce sont des aspects d'utilisation qui peuvent changer dans les prochaines versions de .NET et ce sera jusqu'à ce que Microsoft ajoute la propriété booléenne IsAnonymous à la classe Type. J'espère que cela arrivera avant de mourir tous ... Jusqu'à ce jour, cela peut être vérifié comme suit:

using System.Runtime.CompilerServices;
using System.Reflection;

public static class AnonymousTypesSupport
{
    public static bool IsAnonymous(this Type type)
    {
        if (type.IsGenericType)
        {
            var d = type.GetGenericTypeDefinition();
            if (d.IsClass && d.IsSealed && d.Attributes.HasFlag(TypeAttributes.NotPublic))
            {
                var attributes = d.GetCustomAttributes(typeof(CompilerGeneratedAttribute), false);
                if (attributes != null && attributes.Length > 0)
                {
                    //WOW! We have an anonymous type!!!
                    return true;
                }
            }
        }
        return false;
    }

    public static bool IsAnonymousType<T>(this T instance)
    {
        return IsAnonymous(instance.GetType());
    }
}
7
Konstantin Isaev

Vérifiez CompilerGeneratedAttribute et DebuggerDisplayAttribute.Type

voici le code généré par le compilateur pour un type anomymous

[CompilerGenerated, DebuggerDisplay(@"\{ a = {a} }", Type="<Anonymous Type>")]
internal sealed class <>f__AnonymousType0<<a>j__TPar>
{
...
}
5
Catalin DICU