| File: System\Linq\Zip.cs | Web Access |
| Project: src\runtime\src\libraries\System.Linq\src\System.Linq.csproj (System.Linq) |
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. using System.Collections.Generic; namespace System.Linq { public static partial class Enumerable { public static IEnumerable<TResult> Zip<TFirst, TSecond, TResult>(this IEnumerable<TFirst> first, IEnumerable<TSecond> second, Func<TFirst, TSecond, TResult> resultSelector) { if (first is null) { ThrowHelper.ThrowArgumentNullException(ExceptionArgument.first); } if (second is null) { ThrowHelper.ThrowArgumentNullException(ExceptionArgument.second); } if (resultSelector is null) { ThrowHelper.ThrowArgumentNullException(ExceptionArgument.resultSelector); } return ZipIterator(first, second, resultSelector); } public static IEnumerable<(TFirst First, TSecond Second)> Zip<TFirst, TSecond>(this IEnumerable<TFirst> first, IEnumerable<TSecond> second) { if (first is null) { ThrowHelper.ThrowArgumentNullException(ExceptionArgument.first); } if (second is null) { ThrowHelper.ThrowArgumentNullException(ExceptionArgument.second); } return ZipIterator(first, second); } /// <summary> /// Produces a sequence of tuples with elements from the three specified sequences. /// </summary> /// <typeparam name="TFirst">The type of the elements of the first input sequence.</typeparam> /// <typeparam name="TSecond">The type of the elements of the second input sequence.</typeparam> /// <typeparam name="TThird">The type of the elements of the third input sequence.</typeparam> /// <param name="first">The first sequence to merge.</param> /// <param name="second">The second sequence to merge.</param> /// <param name="third">The third sequence to merge.</param> /// <returns>A sequence of tuples with elements taken from the first, second, and third sequences, in that order.</returns> public static IEnumerable<(TFirst First, TSecond Second, TThird Third)> Zip<TFirst, TSecond, TThird>(this IEnumerable<TFirst> first, IEnumerable<TSecond> second, IEnumerable<TThird> third) { if (first is null) { ThrowHelper.ThrowArgumentNullException(ExceptionArgument.first); } if (second is null) { ThrowHelper.ThrowArgumentNullException(ExceptionArgument.second); } if (third is null) { ThrowHelper.ThrowArgumentNullException(ExceptionArgument.third); } return ZipIterator(first, second, third); } private static IEnumerable<(TFirst First, TSecond Second)> ZipIterator<TFirst, TSecond>(IEnumerable<TFirst> first, IEnumerable<TSecond> second) { using IEnumerator<TFirst> e1 = first.GetEnumerator(); using IEnumerator<TSecond> e2 = second.GetEnumerator(); while (e1.MoveNext() && e2.MoveNext()) { yield return (e1.Current, e2.Current); } } private static IEnumerable<TResult> ZipIterator<TFirst, TSecond, TResult>(IEnumerable<TFirst> first, IEnumerable<TSecond> second, Func<TFirst, TSecond, TResult> resultSelector) { using IEnumerator<TFirst> e1 = first.GetEnumerator(); using IEnumerator<TSecond> e2 = second.GetEnumerator(); while (e1.MoveNext() && e2.MoveNext()) { yield return resultSelector(e1.Current, e2.Current); } } private static IEnumerable<(TFirst First, TSecond Second, TThird Third)> ZipIterator<TFirst, TSecond, TThird>(IEnumerable<TFirst> first, IEnumerable<TSecond> second, IEnumerable<TThird> third) { using IEnumerator<TFirst> e1 = first.GetEnumerator(); using IEnumerator<TSecond> e2 = second.GetEnumerator(); using IEnumerator<TThird> e3 = third.GetEnumerator(); while (e1.MoveNext() && e2.MoveNext() && e3.MoveNext()) { yield return (e1.Current, e2.Current, e3.Current); } } } }