Будет ли будущая версия .NET поддерживать кортежи в С#?
.Net 3.5 не поддерживает кортежи. Слишком плохо, Но не уверен, поддерживает ли будущая версия .net кортежи или нет?
Ответы
Ответ 1
Я только что прочитал эту статью из журнала MSDN: Building Tuple
Вот выдержки:
Предстоящая версия 4.0 Microsoft.NET Framework вводит новый тип называемый System.Tuple. System.Tuple - это сбор фиксированного размера неоднородно типизированные данные.
Как и массив, кортеж имеет фиксированный размер, который нельзя изменить, если он были созданы. В отличие от массива, каждый элемент в кортеже может быть другим тип, а кортеж может гарантировать сильная типизация для каждого элемента.
Уже есть один пример кортеж, плавающий вокруг Microsoft.NET Framework, в System.Collections.Generic пространство имен: KeyValuePair. Хотя KeyValuePair можно рассматривать как одно и то же как Tuple, так как они оба типы, которые имеют две вещи, KeyValuePair отличается от Кортеж, потому что он вызывает отношения между двумя значениями, которые он хранит (и с полным основанием, поскольку он поддерживает Класс словаря).
Кроме того, кортежи могут быть произвольными, тогда как KeyValuePair имеет только две вещи: ключ и значение.
Хотя некоторые языки, такие как F #, имеют специальный синтаксис для кортежей, вы можете использовать новый общий тип кортежа с любого языка. Повторяя первый пример, мы видим, что, хотя полезно, кортежи могут быть слишком многословными в языках без синтаксиса для кортежа:
class Program {
static void Main(string[] args) {
Tuple<string, int> t = new Tuple<string, int>("Hello", 4);
PrintStringAndInt(t.Item1, t.Item2);
}
static void PrintStringAndInt(string s, int i) {
Console.WriteLine("{0} {1}", s, i);
}
}
Используя ключевое слово var из С# 3.0, мы можем удалить сигнатуру типа в переменной кортежа, что позволяет получить более читаемый код.
var t = new Tuple<string, int>("Hello", 4);
Мы также добавили некоторые методы factory к статическому классу Tuple, что упрощает сбор кортежей на языке, поддерживающем вывод типа, например С#.
var t = Tuple.Create("Hello", 4);
Ответ 2
#region tuples
public class Tuple<T>
{
public Tuple(T first)
{
First = first;
}
public T First { get; set; }
}
public class Tuple<T, T2> : Tuple<T>
{
public Tuple(T first, T2 second)
: base(first)
{
Second = second;
}
public T2 Second { get; set; }
}
public class Tuple<T, T2, T3> : Tuple<T, T2>
{
public Tuple(T first, T2 second, T3 third)
: base(first, second)
{
Third = third;
}
public T3 Third { get; set; }
}
public class Tuple<T, T2, T3, T4> : Tuple<T, T2, T3>
{
public Tuple(T first, T2 second, T3 third, T4 fourth)
: base(first, second, third)
{
Fourth = fourth;
}
public T4 Fourth { get; set; }
}
#endregion
И чтобы сделать объявления красивее:
public static class Tuple
{
//Allows Tuple.New(1, "2") instead of new Tuple<int, string>(1, "2")
public static Tuple<T1, T2> New<T1, T2>(T1 t1, T2 t2)
{
return new Tuple<T1, T2>(t1, t2);
}
//etc...
}
Ответ 3
Существует правильная (не быстрая) реализация С# Tuple в Lokad Shared Libraries a > (с открытым исходным кодом, конечно), который включает следующие необходимые функции:
- 2-5 реализации неизменяемых кортежей
- Правильный DebuggerDisplayAttribute
- Надлежащие проверки хеширования и равенства
- Помощники для генерации кортежей из предоставленных параметров (обобщения выводятся компилятором) и расширения для операций, основанных на коллекции.
- Производство испытания.
Ответ 4
Реализация классов Tuple или повторное использование классов F # в С# - это всего лишь половина истории - это дает вам возможность создавать кортежи с относительной легкостью, но на самом деле не синтаксический сахар, который делает их настолько приятными для использования на таких языках, как F #.
Например, в F # вы можете использовать сопоставление шаблонов для извлечения обеих частей кортежа в статусе let, например
let (a, b) = someTupleFunc
К сожалению, сделать то же самое с использованием классов F # из С# было бы гораздо менее изящным:
Tuple<int,int> x = someTupleFunc();
int a = x.get_Item1();
int b = x.get_Item2();
Кортежи представляют собой мощный метод для возврата нескольких значений из вызова функции без необходимости засорять ваш код классами throwaway или прибегать к уродливым параметрам ref или out. Однако, на мой взгляд, без синтаксического сахара, чтобы сделать их создание и доступ более элегантными, они имеют ограниченное применение.
Ответ 5
По моему мнению, функция анонимных типов не является кортежем, а очень похожей конструкцией. Вывод некоторых запросов LINQ представляет собой коллекции анонимных типов, которые ведут себя как кортежи.
Вот инструкция, которая создает типизированный кортеж:-) на лету:
var p1 = new {a = "A", b = 3};
см. http://www.developer.com/net/csharp/article.php/3589916
Ответ 6
С# поддерживает простые кортежи через generics довольно легко (согласно более раннему ответу) и с помощью "mumble typing" (одного из многих возможных улучшений языка С#), чтобы улучшить вывод типа, они могут быть очень и очень мощными.
Для чего стоит, F # поддерживает кортежи изначально, и, играя с ним, я не уверен, что (анонимные) кортежи добавляют много... то, что вы получаете в краткости, вы теряете очень быстро в ясности кода.
Для кода внутри одного метода существуют анонимные типы; для кода, выходящего за пределы метода, я думаю, что буду придерживаться простых именованных типов. Конечно, если будущий С# упростит сделать эти неизменные (хотя все еще легко работать), я буду счастлив.
Ответ 7
Мой открытый исходный код .NET Библиотека Sasa имеет кортежи в течение многих лет (наряду с множеством других функций, таких как полный анализ MIME). Я использую его в производственном кодексе в течение нескольких лет.
Ответ 8
С# 7 поддерживает кортежи изначально:
var unnamedTuple = ("Peter", 29);
var namedTuple = (Name: "Peter", Age: 29);
(string Name, double Age) typedTuple = ("Peter", 29);
Ответ 9
Если я помню классы Computer Science, правильные кортежи - это просто данные.
Если вы хотите сгруппировать данные - создайте классы, содержащие свойства.
Если вам понадобится что-то вроде KeyValuePair, тогда он есть.
Ответ 10
Здесь мой набор кортежей, они автогенерируются Python script, поэтому я, возможно, немного зашел за борт:
Ссылка на репозиторий Subversion
Вам понадобится имя пользователя/пароль, они оба гость
Они основаны на наследовании, но Tuple<Int32,String>
не будет сравниваться с Tuple<Int32,String,Boolean>
, даже если они имеют одинаковые значения для двух первых членов.
Они также реализуют GetHashCode и ToString и т.д. и множество небольших вспомогательных методов.
Пример использования:
Tuple<Int32, String> t1 = new Tuple<Int32, String>(10, "a");
Tuple<Int32, String, Boolean> t2 = new Tuple<Int32, String, Boolean>(10, "a", true);
if (t1.Equals(t2))
Console.Out.WriteLine(t1 + " == " + t2);
else
Console.Out.WriteLine(t1 + " != " + t2);
Будет выводиться:
10, a != 10, a, True
Ответ 11
Я был бы удивлен - С# - строго типизированный язык, тогда как кортежи подходят для более динамически типизированных языков. С# с течением времени дрейфует более динамично, но этот синтаксический сахар, а не реальный сдвиг в базовых типах данных.
Если вам нужно два значения в одном экземпляре, KeyValuePair < > является достойным заменителем, хотя и неуклюжим. Вы также можете создать структуру или класс, которые будут делать то же самое и могут расширяться.
Ответ 12
Чтобы сделать их полезными в хэш-таблице или словаре, вы, скорее всего, захотите предоставить перегрузки для GetHashCode и Equals.