2014-04-09 11 views
6

Jeśli mam tablicę wyników Golf:Jak mogę wybrać minimalną pod-sekwencję za pomocą LINQ?

-3, +5, -3, 0, +1, +8, 0, +6, +2, -8, +5 

Muszę znaleźć sekwencję trzech sąsiednich liczb, które mają minimalną sumę. W tym przykładzie, pod-sekwencji będzie:

[-3, +5, -3] 
[+5, -3, 0] 
[-3, 0, +1] 
... etc ... 
[+2, -8, +5] 

a minimalna sekwencja będzie [-3, 0, +1] o sumę -2.

+6

Czy potrzebuję wiedzy o golfie, aby to zrozumieć? Ponieważ nie jestem do końca pewien, co próbujesz zrobić. – Habib

+0

Niestety - według najlepszych wyników mam na myśli najniższe wyniki (im więcej ujemnych - tym lepiej). Przez spójność rozumiem wyniki, które są ze sobą powiązane (obok siebie). – user3515324

+0

Skąd bierze się pierwsza trójka? Twój pożądany wynik zawiera wszystko. Poza tym zawiera dwa '-3'. Dlaczego? –

Odpowiedz

5

Można użyć tej kwerendy LINQ:

int[] golfResult = { -3, +5, -3, 0, +1, +8, 0, +6, +2, -8, +5 }; 
var combinations = from i in Enumerable.Range(0, golfResult.Length - 2) 
        select new { 
         i1 = golfResult[i], 
         i2 = golfResult[i + 1], 
         i3 = golfResult[i + 2], 
        }; 
var min = combinations.OrderBy(x => x.i1 + x.i2 + x.i3).First(); 
int[] minGolfResult = { min.i1, min.i2, min.i3 }; // -3, 0, +1 

Oczywiście trzeba sprawdzić, czy istnieją co najmniej trzy wyniki w tablicy.

+1

Ta ostatnia linia to trochę składni C#, z którą nigdy wcześniej się nie spotkałem :) – Rawling

1

Jeśli naprawdę chcesz to zrobić w LINQ, można przejść w ten sposób:

int length = 3; 
var scores = new List<int>() { -3, +5, -3, 0, +1, +8, 0, +6, +2, -8, +5 }; 
var results = 
    scores 
    .Select((value, index) => new 
    { 
     Value = scores.Skip(index - length + 1).Take(length).Sum(), 
     Index = index - length + 1 
    }) 
    .Skip(length - 1) 
    .OrderBy(x => x.Value) 
    .First() 
    .Index; 

Stwarza drugą listę, która sumuje wszystkie długość elementów poprzedzających, a następnie sortuje je. Masz

2

Nie jestem pewien, dlaczego zrobiłbyś to z LINQ. Myślę, że prostsze iteracyjne rozwiązanie jest łatwiejsze do zrozumienia:

int[] scores = new[] { -3, 5, -3, 0, 1, 8, 0, 6, 2, -8, 5 }; 

int minimumSubsequence = int.MaxValue; 
int minimumSubsequenceIndex = -1; 

for (int i = 0; i < scores.Length - 2; i++) 
{ 
    int sum = scores[i] + scores[i + 1] + scores[i + 2]; 

    if (sum < minimumSubsequence) 
    { 
     minimumSubsequence = sum; 
     minimumSubsequenceIndex = i; 
    } 
} 

// minimumSubsequenceIndex is index of the first item in the minimum subsequence 
// minimumSubsequence is the minimum subsequence's sum. 
+0

Dowiedziałem się o czymś innym, ale to jest dokładne rozwiązanie, które zamierzałem zasugerować, aczkolwiek zawinięte w funkcję z parametrem dla długość pod-sekwencji i zwracanie tylko indeksu pod-sekwencji. – Anthony

Powiązane problemy