it-roy-ru.com

Примеры использования Generics в .Net (C #/VB.NET)

На каких примерах вы бы использовали дженерики в C #/VB.NET, и почему вы хотите использовать дженерики?

28
Seenu

Просто вы объявляете тип или метод с дополнительными тегами для указания общих битов:

class Foo<T> {
    public Foo(T value) {
        Value = value;
    }
    public T Value {get;private set;}
}

Выше определен универсальный тип Foo "of T", где T предоставляется вызывающей стороной. По соглашению, аргументы универсального типа начинаются с T. Если есть только один, T подойдет, в противном случае назовите их все с пользой: TSource, TValue, TListType и т.д.

В отличие от шаблонов C++, шаблоны .NET предоставляются средой выполнения (не трюками компилятора). Например:

Foo<int> foo = new Foo<int>(27);

Все T были заменены на int в приведенном выше. При необходимости вы можете ограничить общие аргументы с помощью ограничений:

class Foo<T> where T : struct {}

Теперь Foo<string> откажется компилировать - поскольку string не является структурой (тип-значения). Допустимые ограничения:

T : class // reference-type (class/interface/delegate)
T : struct // value-type except Nullable<T>
T : new() // has a public parameterless constructor
T : SomeClass // is SomeClass or inherited from SomeClass
T : ISomeInterface // implements ISomeInterface

Ограничения могут также включать другие аргументы универсального типа, например:

T : IComparable<T> // or another type argument

Вы можете иметь столько общих аргументов, сколько вам нужно:

public struct KeyValuePair<TKey,TValue> {...}

Другие вещи, чтобы отметить:

  • статические члены и т. д. определены для каждой комбинации универсального типа - поэтому статическое поле в Foo<int> отдельно от поля в Foo<float>.
  • методы также могут быть универсальными - старайтесь избегать использования тех же имен, что и класс, так как вы не сможете устранить неоднозначность
  • вложенные типы наследуют родовые типы от своих родителей

например:

class Foo<T> {
    class Bar<TInner> {} // is effectively Bar<T,TInner>, for the outer T
}
60
Marc Gravell

Пример 1: Вы хотите создать тройной класс 

Class Triple<T1, T2, T3>
{
   T1 _first;
   T2 _second;
   T3 _Third;
}

Пример 2: вспомогательный класс, который будет анализировать любое значение перечисления для данного типа данных

static public class EnumHelper<T>
{
   static public T Parse(string value)
   {
       return (T)Enum.Parse(typeof(T), value);
   }
}
6
Brijesh Mishra

Одним из распространенных и чрезвычайно полезных применений обобщений являются строго типизированные классы коллекций. Традиционно все классы коллекции должны передаваться объектам и возвращать объекты при запросе. Вы должны были обработать все преобразования типов самостоятельно. С генериками вам не нужно этого делать. У вас может быть List (Of Integer), и когда вы запрашиваете значения из него, вы получаете целые числа. Вы не получите объекты, которые затем должны быть преобразованы в целые числа.

4
Instance Hunter
    private void button1_Click_1(object sender, RoutedEventArgs e)
    {
        TextValue<string, int> foo = new TextValue<string, int>("",0);
        foo.Text = "Hi there";
        foo.Value = 3995;
        MessageBox.Show(foo.Text);
    }

    class TextValue<TText, TValue>
    {
        public TextValue(TText text, TValue value)
        {
            Text = text;
            Value = value;
        }
        public TText Text { get; set; }
        public TValue Value { get; set; }
    }
3
dewelloper

Наиболее распространенные причины и варианты использования обобщений описаны в документации MSDN, упомянутой ранее. Одно из преимуществ дженериков, которые я хотел бы добавить, заключается в том, что они могут улучшить поддержку инструментов в процессе разработки. Инструменты рефакторинга, такие как интегрированные в Visual Studio или ReSharper, полагаются на статический анализ типов для обеспечения помощи при кодировании. Поскольку дженерики обычно добавляют больше информации о типе в вашу объектную модель, для таких инструментов есть больше информации для анализа и для помощи в кодировании. 

На концептуальном уровне дженерики помогают вам решать «сквозные» задачи независимо от области применения. Независимо от того, разрабатываете ли вы финансовое приложение или книжный магазин, вам рано или поздно понадобится хранить коллекции вещей, будь то счета, книги или что-то еще. Реализация таких коллекций обычно должна практически ничего не знать о вещах, которые будут поддерживаться в этих коллекциях. Следовательно, универсальные коллекции, поставляемые с платформой .NET, являются основным примером варианта использования обобщенных элементов.

3
Sven Künzler

Основным примером будет:

class Other{
 class Generic<T>
{
  void met1(T x);
}
static void Main()
{
  Generic<int> g = new Generic<int>();
  Generic<string> s = new Generic<string>();
}
}
1
user544079
    private void button1_Click_1(object sender, RoutedEventArgs e)
    {
        TextValue<string, int> foo;
        List<TextValue<string, int>> listTextValue = new List<TextValue<string, int>>();
        for (int k = 0; k < 5; ++k)
        {
            foo = new TextValue<string, int>("",0);
            foo.Text = k.ToString();
            foo.Value = k;
            listTextValue.Add(foo);
            otherList.
            MessageBox.Show(foo.Text);
        }

    }

    class TextValue<TText, TValue>
    {
        public TextValue(TText text, TValue value){Text = text; Value = value;}
        public TText Text { get; set; }
        public TValue Value { get; set; }
    }
0
dewelloper