Как сравнить типы при использовании дженериков? - PullRequest
5 голосов
/ 29 июля 2009

Я пытаюсь определить тип объекта во время выполнения. В частности, мне нужно знать две вещи, реализует ли он ICollection или IDto. В настоящее время мое единственное решение, которое мне удалось найти, это:

   private static bool IsACollection(PropertyDescriptor descriptor)
    {
        bool isCollection = false;

        foreach (Type type in descriptor.PropertyType.GetInterfaces())
        {
            if (type.IsGenericType)
            {
                if (type.GetGenericTypeDefinition() == typeof(ICollection<>))
                {
                    isCollection = true;
                    break;
                }
            }
            else
            {
                if (type == typeof(ICollection))
                {
                    isCollection = true;
                    break;
                }
            }
        }


        return isCollection;
    }

    private static bool IsADto(PropertyDescriptor descriptor)
    {
        bool isDto = false;

        foreach (Type type in descriptor.PropertyType.GetInterfaces())
        {
            if (type == typeof(IDto))
            {
                isDto = true;
                break;
            }
        }          
        return isDto;
    }

Однако я убежден, что должен быть лучший способ, чем этот. Я попытался сравнить обычным способом, например:

if(descriptor.PropertyType == typeof(ICollection<>))

Однако, это не работает, если используется отражение, но когда оно не используется, оно работает нормально.

Я не хочу перебирать интерфейсы для каждого поля моей сущности. Может ли кто-то пролить свет на другой метод, с помощью которого это можно сделать? Да, я преждевременно оптимизирую, но это тоже выглядит некрасиво, поэтому, пожалуйста, позабавьте меня.

Предостережения:

  1. Он может или не может быть универсальным, таким как IList <> или просто ArrayList, поэтому я ищу ICollection или ICollection <>. Поэтому я предполагаю, что должен использовать IsGenericType в операторе if, чтобы знать, тестировать ли с использованием ICollection <> или нет.

Заранее спасибо!

Ответы [ 2 ]

11 голосов
/ 29 июля 2009

Это:

type == typeof(ICollection)

проверит, является ли тип свойства точно ICollection. То есть вернет true для:

public ICollection<int> x { get; set; }

но не для:

public List<int> x { get; set; }

Если вы хотите проверить, является ли тип свойства или получен из , ICollection, самый простой способ - использовать Type.IsAssignableFrom:

typeof(ICollection).IsAssignableFrom(type)

и то же самое относится к универсальному:

typeof(ICollection<>).IsAssignableFrom(type.GetGenericTypeDefinition())
2 голосов
/ 29 июля 2009

Помогает ли type.IsAssignable в этом случае?

РЕДАКТИРОВАТЬ: Извините, это должно было быть Type.IsAssignableFrom

...