Почему C# и VB имеют дженерики? Какую пользу они приносят? Дженерики, FTW

с Википедия:

Generic программирование-это стиль компьютерное программирование, в котором алгоритмы написаны в терминах будет указано позднее типов затем создается при необходимости конкретных типов в качестве параметров и был пионером Ada, который появился в 1983 году. Этот подход позволяет писать общие функции или типы, отличающиеся только набором типы, на которых они работают при использовании, таким образом, сокращение дублирование.

дженерики дают возможность определять типы, которые указаны позже. Вам не нужно бросать элементы в тип, чтобы использовать их, потому что они уже набраны.

Почему C# и VB имеют дженерики? Какую пользу они приносят? Какую пользу вы находите от их использования?

что другие языки также имеют дженерики?

15 ответов


C# и VB имеют дженерики, чтобы воспользоваться поддержкой дженериков в базовой среде CLR (или наоборот?). Они позволяют писать код на статически типизированном языке, который может применяться к нескольким типам без перезаписи кода для каждого типа, для которого вы их используете (среда выполнения сделает это за вас) или иным образом используя


лично я думаю, что они позволяют сэкономить много времени. Я все еще использую .NET Framework 1.1, и каждый раз, когда вам нужна определенная коллекция, вам нужно создать строго типизированную коллекцию, реализуя CollectionBase. С дженериками вам просто нужно объявить свою коллекцию так List<MyObject> и это делается.


рассмотрим эти сигнатуры метода:

//Old and busted
public abstract class Enum
{
  public static object Parse(Type enumType, string value);
}
//To call it:
MyEnum x = (MyEnum) Enum.Parse(typeof(MyEnum), someString);

//New and groovy
public abstract class Enum
{
  public static T Parse<T>(string value);
}

//To call it:
MyEnum x = Enum.Parse<MyEnum>(someString);

Look ma: нет манипуляции с типом времени выполнения.


с MSDN:

дженерики обеспечивают решение ограничение в более ранних версиях среда CLR и C# язык, в котором обобщение выполненный путем бросать типы К и из объекта универсального базового типа. Создавая универсальный класс, вы можете создание коллекции, безопасной для типов во время компиляции.

читать остальную часть этой статьи, чтобы увидеть некоторые примеры того, как дженерики может улучшить читаемость и производительность кода.


вероятно самая общяя польза для них сильно набирается артефакты ArrayList. В .NET 1.1 вам придется либо привести все от объекта к желаемому типу, либо использовать что-то вроде CodeSmith для создания строго типизированного ArrayList.

кроме того, они помогают уменьшить бокс. Опять же, в .NET 1.x, если вы попытаетесь использовать ArrayList с типом значения, вы закончите боксом и распаковкой объектов повсюду. Дженерики избегают этого, позволяя вам определить Тип, будь то ссылка или значение.

есть и другие удобные для них использования, обработчики событий, запросы LINQ и т. д.


дженерики в .NET отлично подходят для коллекций объектов. Вы можете определить свой тип объекта, как хотите, и иметь, скажем, список без написания кода для этого, и иметь доступ ко всем эффективным функциям общей коллекции .NET List, будучи типобезопасным для T. Это отличный материал.


дженерики построены на концепции шаблонов в C++, если вы не знакомы с ними.

его способ реализовать алгоритм или структуру данных, но задерживая фактический тип, на котором он используется.

список может быть назначен с любым типом по вашему выбору int, string и даже пользовательские типы тип назначается при построении списка. Но вы сможете использовать операции списка add remove и т. д.

вы действительно можете сэкономить много усилий по кодированию привыкаю к дженерикам. И вам не нужно боксировать и распаковывать между типами.

Java также имеет дженерики. Они называются подстановочными знаками.


дженерики в .net, такие как методы наследования и расширения, позволяют уменьшить дублирование кода. Позвольте мне объяснить в порядке рефакторинга.

Если все классы с общим предком имеют общий метод, Поместите общий метод в общий предок классов (наследственность).

Если некоторые классы имеют общий метод, который использует публичный контракт для достижения некоторого результата, сделайте общий метод методом расширения в этом публичном контракте.

Если некоторые несколько методов или классов имеют один и тот же код, который отличается только типами, на которые действуют (особенно если детали типа не имеют отношения к работе метода), собирают эти методы или классы в общий.


Они повышают производительность для коллекций с использованием типов значений, так как не требуется бокс/распаковка. Они намного чище в использовании, так как вам не придется приводить объект (например, с помощью ArrayList) к нужному типу, а также они помогают обеспечить безопасность типов.


самое большое преимущество дженериков над непатентованными типами в C# (не Java, Java-это другая история) заключается в том, что они намного быстрее. JIT генерирует лучший машинный код, который он может придумать для данного типа. List<int> на самом деле это список ints, а не целочисленных объектов, обертывающих int. Это делает общие типы удивительно быстрыми, а также безопасными, что может помочь вам обнаружить огромное количество ошибок во время компиляции:)


общий пример коллекций. например, набор типа T, как метод Add(T) и метод t get (). Тот же код, разные типы безопасных коллекций.

C++, D, Ada и другие имеют шаблоны, суперсет дженериков, которые делают это немного другой ошибкой, получают тот же конечный результат (а затем некоторые).

IIRC Java имеет дженерики, но я не делаю Java.


самый простой способ объяснить это, чтобы дать пример. Предположим, вам нужны две хэш-таблицы: одна, которая сопоставляет объекты типа string с типом int, и другая, которая сопоставляет объекты типа string с типом double. Вы можете определить Hashtable, а затем использовать типы K и V. Без дженериков вам придется использовать тип "object", который, помимо того, что должен быть отлит, чтобы быть значимым, отказывается от безопасности типов. Просто создайте экземпляр Hashtable и Hashtable, и у вас есть хэш-таблицы с правильной проверкой типов и все.


Java также имеет дженерики. C++ есть шаблоны.

динамические языки, такие как Perl и Javascript, не имеют ограничений того же типа, поэтому они получают в основном те же преимущества с меньшим количеством работы.


в Objective-C вы можете использовать протоколы для достижения целей дженериков. Однако, поскольку язык слабо типизирован, это обычно не так важно, как при борьбе с системой типов, чтобы использовать один путь кода для многих типов.


лично я большой поклонник дженериков из-за всего кода, который мне не нужно писать.

что такое инверсия управления?