Добавьте два Списка другой длины в c#

var number = 3200;
var hexString = number.toString(16);

Эти 16 являются основанием и существует 16 значений в шестнадцатеричном числе:-)

17
задан 28 July 2009 в 02:55
поделиться

10 ответов

Вы можете легко использовать модифицированную операцию "zip", но ничего встроенного. Примерно так:

    static void Main() {
        var a = new List<int> { 1, 2, 3 };
        var b = new List<int> { 1, 2, 3, 4, 5 };
        foreach (var c in a.Merge(b, (x, y) => x + y)) {
            Console.WriteLine(c);
        }
    }
    static IEnumerable<T> Merge<T>(this IEnumerable<T> first,
            IEnumerable<T> second, Func<T, T, T> operation) {
        using (var iter1 = first.GetEnumerator())
        using (var iter2 = second.GetEnumerator()) {
            while (iter1.MoveNext()) {
                if (iter2.MoveNext()) {
                    yield return operation(iter1.Current, iter2.Current);
                } else {
                    yield return iter1.Current;
                }
            }
            while (iter2.MoveNext()) {
                yield return iter2.Current;
            }
        }
    }
23
ответ дан 30 November 2019 в 10:31
поделиться

В этом случае не имеет значения, имеют ли списки одинаковую или разную длину. В библиотеке классов .NET нет метода Enumerable.Zip для объединения двух последовательностей (он входит только в .NET 4.0), и вам в любом случае понадобится что-то подобное. Таким образом, вам нужно написать цикл или свой собственный Zip (который по-прежнему будет включать цикл).

Есть несколько приемов, позволяющих сжать все это в одном запросе LINQ без циклов, включая присоединиться к индексам, но это будет очень медленно и бессмысленно.

0
ответ дан 30 November 2019 в 10:31
поделиться

Что случилось с 1 и дополнительными 2 и 3 ? Если вы ищете разные значения:

var one = new List<int> { 1, 2, 3 };
var two = new List<int> { 1, 2, 3, 4, 5 };

foreach (var x in one.Union(two)) Console.Write("{0} ", x);

даст вам 1 2 3 4 5

Если вы ищете только второй список, добавленный к первому, то:

foreach(var x in one.Concat(two)) // ...

даст вам 1 2 3 1 2 3 4 5

Правка : О, понятно, вы ищете что-то вроде Zip , но которое возвращает лишние части. Попробуйте следующее:

public static IEnumerable<V> Zip<T, U, V>(
    this IEnumerable<T> one,
    IEnumerable<U> two,
    Func<T, U, V> f)
{
    using (var oneIter = one.GetEnumerator()) {
        using (var twoIter = two.GetEnumerator()) {
            while (oneIter.MoveNext()) {
                twoIter.MoveNext();
                yield return f(oneIter.Current,
                    twoIter.MoveNext() ?
                        twoIter.Current :
                        default(U));
            }

            while (twoIter.MoveNext()) {
                yield return f(oneIter.Current, twoIter.Current);
            }
        }
    }
}

, а вот функция, которая больше похожа на обычную zip-функцию, которая не возвращает дополнительных:

public static IEnumerable<V> Zip<T, U, V>(
    this IEnumerable<T> one,
    IEnumerable<U> two,
    Func<T, U, V> f)
{
    using (var oneIter = one.GetEnumerator()) {
        using (var twoIter = two.GetEnumerator()) {
            while (oneIter.MoveNext()) {
                yield return f(oneIter.Current,
                    twoIter.MoveNext() ?
                        twoIter.Current :
                        default(U));
            }
        }
    }
}

Пример использования:

var one = new List<int>  { 1, 2, 3, 4, 5};
var two = new List<char> { 'h', 'e', 'l', 'l', 'o' };

foreach (var x in one.Zip(two, (a,b) => new {A = a, B =b }))
    Console.WriteLine("{0} => '{1}'", x.A, x.B);

Результат:

1 => 'h'
2 => 'e'
3 => 'l'
4 => 'l'
5 => 'o'

0
ответ дан 30 November 2019 в 10:31
поделиться

Моя реализация с использованием цикла:

List<double> shorter, longer;
if (a.Count > b.Count)
{
    shorter = b; longer = a
}
else
{
    shorter = a; longer = b;
}

List<double> result = new List<double>(longer);
for (int i = 0; i < shorter.Count; ++i)
{
     result[i] += shorter[i];
}
-3
ответ дан 30 November 2019 в 10:31
поделиться

Ниже приведено решение вашей проблемы.

List<double> a = new List<double>{1,2,3};
List<double> b = new List<double>{1,2,3,4,5};

List<double> sum = new List<double>();
int max = Math.Min(a.Count, b.Count);
for (int i = 0; i < max; i++){
    sum.Add(a[i] + b[i]);
}

if (a.Count < b.Count)
    for (int i = max i < b.Count)
        sum.Add(b[i]);
else
    for (int i = max i < a.Count)
    sum.Add(a[i]);
1
ответ дан 30 November 2019 в 10:31
поделиться
Enumerable.Range(0, new[] { a.Count, b.Count }.Max())
    .Select(n => a.ElementAtOrDefault(n) + b.ElementAtOrDefault(n));
7
ответ дан 30 November 2019 в 10:31
поделиться

Использование оператора .NET 4.0 Zip :

var sums = b.Zip(a, (x, y) => x + y)
            .Concat(b.Skip(a.Count()));

Если вы хотите обобщить это, проверьте, какой содержит больше элементов и используйте его как букву «b» выше.

14
ответ дан 30 November 2019 в 10:31
поделиться

Уродливое решение LINQ:

var sum = Enumerable.Range(0, (a.Count > b.Count) ? a.Count : b.Count)
    .Select(i => (a.Count > i && b.Count > i) ? a[i] + b[i] : (a.Count > i) ? a[i] : b[i]);
1
ответ дан 30 November 2019 в 10:31
поделиться

Как насчет этого:

List<double> doubles = Enumerable.Range(0, Math.Max(a.Count, b.Count))
    .Select(x => (a.Count > x ? a[x] : 0) + (b.Count > x ? b[x] : 0))
    .ToList();
2
ответ дан 30 November 2019 в 10:31
поделиться

Вот еще 3:

Сделайте списки одинакового размера, а затем просто выберите.

(a.Count < b.Count ? a : b).AddRange(new double[Math.Abs(a.Count - b.Count)]);
var c = a.Select((n, i) => n + b[i]);

Не делайте их одинакового размера, а просматривайте самые длинные и проверяйте конец диапазона на самых коротких (сохраните shortList.Count для легкого увеличения производительности):

var longList = a.Count > b.Count ? a : b;
var shortList = longList == a ? b : a;
var c = longList.Select((n, i) => n + (shortList.Count > i ? shortList[i] : 0));

Возьмите , пока можете, затем Пропустить и Союз , остальные:

var c = a.Take(Math.Min(a.Count, b.Count))
         .Select((n, i) => n + b[i])
         .Union(a.Skip(Math.Min(a.Count, b.Count));
0
ответ дан 30 November 2019 в 10:31
поделиться
Другие вопросы по тегам:

Похожие вопросы: