#if NET20 || NET30 || NET35 || !NET_4_6 using System.Collections; using System.Collections.Generic; using System.Globalization; namespace System { [Serializable] public class Tuple : IStructuralEquatable, IStructuralComparable, IComparable { private readonly T1 _item1; private readonly T2 _item2; private readonly T3 _item3; private readonly T4 _item4; private readonly T5 _item5; private readonly T6 _item6; private readonly T7 _item7; private readonly TRest _rest; public Tuple(T1 item1, T2 item2, T3 item3, T4 item4, T5 item5, T6 item6, T7 item7, TRest rest) { CheckType(rest); _item1 = item1; _item2 = item2; _item3 = item3; _item4 = item4; _item5 = item5; _item6 = item6; _item7 = item7; _rest = rest; } public T1 Item1 { get { return _item1; } } public T2 Item2 { get { return _item2; } } public T3 Item3 { get { return _item3; } } public T4 Item4 { get { return _item4; } } public T5 Item5 { get { return _item5; } } public T6 Item6 { get { return _item6; } } public T7 Item7 { get { return _item7; } } public TRest Rest { get { return _rest; } } public override bool Equals(object obj) { return ((IStructuralEquatable)this).Equals(obj, EqualityComparer.Default); } public override int GetHashCode() { return ((IStructuralEquatable)this).GetHashCode(EqualityComparer.Default); } int IStructuralComparable.CompareTo(object other, IComparer comparer) { return CompareTo(other, comparer); } bool IStructuralEquatable.Equals(object other, IEqualityComparer comparer) { var tuple = other as Tuple; if (tuple == null) { return false; } return comparer.Equals(_item1, tuple._item1) && comparer.Equals(_item2, tuple._item2) && comparer.Equals(_item3, tuple._item3) && comparer.Equals(_item4, tuple._item4) && comparer.Equals(_item5, tuple._item5) && comparer.Equals(_item6, tuple._item6) && comparer.Equals(_item7, tuple._item7) && comparer.Equals(_rest, tuple._rest); } int IStructuralEquatable.GetHashCode(IEqualityComparer comparer) { var hash = comparer.GetHashCode(_item1); hash = (hash << 5) - hash + comparer.GetHashCode(_item2); hash = (hash << 5) - hash + comparer.GetHashCode(_item3); hash = (hash << 5) - hash + comparer.GetHashCode(_item4); hash = (hash << 5) - hash + comparer.GetHashCode(_item5); hash = (hash << 5) - hash + comparer.GetHashCode(_item6); hash = (hash << 5) - hash + comparer.GetHashCode(_item7); hash = (hash << 5) - hash + comparer.GetHashCode(_rest); return hash; } int IComparable.CompareTo(object obj) { return CompareTo(obj, Comparer.Default); } public override string ToString() { var restString = _rest.ToString(); return string.Format(CultureInfo.InvariantCulture, "({0}, {1}, {2}, {3}, {4}, {5}, {6}, {7})", _item1, _item2, _item3, _item4, _item5, _item6, _item7, restString.Substring(1, restString.Length - 2)); } private static void CheckType(TRest rest) { if (!ReferenceEquals(rest, null)) { if (typeof(TRest).IsGenericType) { var type = typeof(TRest).GetGenericTypeDefinition(); if ( type == typeof(Tuple<>) || type == typeof(Tuple<,>) || type == typeof(Tuple<,,>) || type == typeof(Tuple<,,,>) || type == typeof(Tuple<,,,,>) || type == typeof(Tuple<,,,,,>) || type == typeof(Tuple<,,,,,,>) || type == typeof(Tuple<,,,,,,,>) ) { return; } } } throw new ArgumentException("The last element of an eight element tuple must be a Tuple.", "rest"); } private int CompareTo(object other, IComparer comparer) { if (other == null) { return 1; } var tuple = other as Tuple; if (tuple == null) { throw new ArgumentException("other"); } var result = comparer.Compare(_item1, tuple._item1); if (result == 0) { result = comparer.Compare(_item2, tuple._item2); } if (result == 0) { result = comparer.Compare(_item3, tuple._item3); } if (result == 0) { result = comparer.Compare(_item4, tuple._item4); } if (result == 0) { result = comparer.Compare(_item5, tuple._item5); } if (result == 0) { result = comparer.Compare(_item6, tuple._item6); } if (result == 0) { result = comparer.Compare(_item7, tuple._item7); } if (result == 0) { result = comparer.Compare(_item7, tuple._item7); } return result; } } } #endif