Question

HI.

Voici ce que je veux faire:

    str2 = "91";
    str1 = "19";
    var testQuery = from c1 in str1
                    from c2 in str2
                    select new {c1, c2};
    foreach (var enumerable in testQuery)
    {
        Console.WriteLine(enumerable.c1 + " | " + enumerable.c2);
    }

Ce que je veux:

9 | 1
1 | 9

Ce que je reçois vraiment:

1 | 9
1 | 1
9 | 9
9 | 1

Le code est un exemple pur. Il peut parcourir des tableaux ou une autre collection. Cela fera aussi d’autres choses, mais elles n’ont aucun rapport avec ce problème.

Sans linq, je pourrais faire quelque chose comme ceci:

    for (int i = 0; i < str1.Length -1; i++)
    {
        Console.WriteLine(str1[i] + " | " + str2[i]);
    }

Mais je veux une requête capable de faire tout ce dont j'ai besoin à la place.

Dois-je vraiment créer ma propre méthode d'énumération qui utilise le rendement pour créer ce que je veux?

EDIT: par demande: Voici un exemple de ce que j'aimerais pouvoir faire:

    str1 = "91";
    str2 = "19";

    char[] digitX = str1.ToString().Reverse().ToArray();
    char[] digitY = str2.ToString().Reverse().ToArray();

    var q = digitX.Select((c1, i) => new {c1 = c1 - '0', c2 = digitY[i] - '0' });

Je voudrais tirer l'inverse, etc. dans la requête réelle. Alors je garde tout cela rassemblé. Extra: Je serais ravi de pouvoir tirer cela avec la syntaxe à la manière d'une couche de sucre. Au lieu d’une chaîne de méthodes, c’est.

Était-ce utile?

La solution

Vous pouvez utiliser:

var testQuery = str1.Select( (c,i) => new {c, str2[i]} );

Modifier:

Au vu de votre nouvelle question, vous devriez pouvoir faire:

var q = str1.Reverse().Select((c1, i) => new { c1 = c1 - '0', c2 = str2[str2.Length - i - 1] - '0' });

Autres conseils

Mon autre réponse est moins utile qu'elle ne pourrait l'être car la fonction Enumerable.Zip a été ajoutée dans la version 4.

Alors, voici comment rouler le vôtre:

public static class EnumerableExtensions
{
    public static IEnumerable<TResult> Zip<TFirst, TSecond, TResult>(
                                           IEnumerable<TFirst> first,
                                           IEnumerable<TSecond> second,
                                           Func<TFirst, TSecond, TResult> resultSelector)
    {
        using(var firstEnum = first.GetEnumerator())
        using(var secondEnum = second.GetEnumerator())
        {
            while(firstEnum.MoveNext() && secondEnum.MoveNext())
            {
                yield return resultSelector(firstEnum.Current, secondEnum.Current);
            }
        }
    }
}

Utilisez Enumerable.Zip . Votre premier exemple peut être réécrit à partir de:

str2 = "91";
str1 = "19";
var testQuery = from c1 in str1
                from c2 in str2
                select new {c1, c2};
foreach (var enumerable in testQuery)
{
    Console.WriteLine(enumerable.c1 + " | " + enumerable.c2);
}

à

str2 = "91";
str1 = "19";
var strings = Enumerable.Zip(c1, c2, (a, b) => a + " | " + b);
foreach (var str in strings)
{
    Console.WriteLine(str);
}
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top