Search code examples
c#.net-corelanguage-design

Why does the ValueTuple.Create 8-tuple overload wrap the last parameter in another ValueTuple?


Looking through the source code (decompiled using JetBrains Rider 2019.1.2) of System.ValueTuple I noticed that the method that creates an 8-tuple wraps the last parameter in a tuple of its own. What is the point of wrapping an element in a 1-tuple?

public static ValueTuple<T1, T2, T3, T4, T5, T6, T7, ValueTuple<T8>> Create<T1, T2, T3, T4, T5, T6, T7, T8>(
    T1 item1,
    T2 item2,
    T3 item3,
    T4 item4,
    T5 item5,
    T6 item6,
    T7 item7,
    T8 item8)
{
    return new ValueTuple<T1, T2, T3, T4, T5, T6, T7, ValueTuple<T8>>(item1, item2, item3, item4, item5, item6, item7, ValueTuple.Create<T8>(item8));
}

Decompilation header:

// Decompiled with JetBrains decompiler
// Type: System.ValueTuple
// Assembly: System.Private.CoreLib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e
// MVID: CE11CF72-ED8D-4122-8743-9D6985631221
// Assembly location: C:\Program Files\dotnet\shared\Microsoft.NETCore.App\3.0.0-preview3-27503-5\System.Private.CoreLib.dll

Solution

  • A ValueTuple is a type with the ability to store 7 values and say 'and I will put the leftovers in another ValueType here' (i.e. the Rest property).

    I still don't understand what is the advantage of wrapping the last parameter in another ValueTuple. For example, why not force the programmer declare a custom type and use it instead?

    For two reasons:

    a) If you do that, you effectively went from 7 to 8 types / values. But that doesn't solve the problem. What about 9? 10?

    b) Having Rest be ValueType means you can support as many types as you want. And the code that deals with the first 7 can be the same as the code that deals with the next 7 etc etc. Since it is ValueType all the way down.

    Also, note that if you already have a ValueType as the eight parameter, call the constructor rather than Tuple.Create (to avoid wrapping the ValueTuple in another ValueTuple).