import Data.Monoid
outputList :: Int -> Int -> [Maybe Int]
outputList = mconcat [getRow, getColumn, getBlock]
Zasługujesz wyjaśnienia.
Po pierwsze, wyraźnie zaznaczę, że wszystkie te funkcje mają ten sam typ.
outputList, getRow, getColumn, getBlock :: Int -> Int -> [Maybe Int]
Zacznijmy od oryginalnej definicji.
outputList x y = concat . map ($ y) $ map ($ x) [getRow,getColumn,getBlock]
Te funkcje powodują, że [Maybe Int]
, a lista wszystkiego jest monidoidalna. Monologicznie łączenie list jest takie samo jak łączenie list, więc możemy zastąpić concat
przez mconcat
.
outputList x y = mconcat . map ($ y) $ map ($ x) [getRow,getColumn,getBlock]
Inną rzeczą, która jest monoid jest funkcją, jeśli jego wynik jest monoid. Oznacza to, że jeżeli b
jest monoidem, wówczas a -> b
jest również monoidem. Monologicznie łączenie funkcji jest takie samo, jak wywoływanie funkcji o tym samym parametrze, a następnie łączenie wyników w sposób monoidalny.
Więc możemy uprościć do
outputList x = mconcat $ map ($ x) [getRow,getColumn,getBlock]
A potem znowu do
outputList = mconcat [getRow,getColumn,getBlock]
Skończyliśmy!
Typeclassopedia has a section about monoids, choć w tym przypadku nie jestem pewien, że to dodaje, że znacznie poza documentation for Data.Monoid.
Nawiasem mówiąc, są jakieś statyki jak długo to trwa, dopóki pytanie dotyczące Haskell odpowiedzi? Mam wrażenie, że prawie wszystkie pytania Haskella odpowiadają na 90 procent niemal natychmiast. Chociaż nie mówi to nic o jakości odpowiedzi, moim zdaniem mają one również dość wysoką jakość. –
@JanChristiansen: Możesz odpowiedzieć na to za pomocą eksploratora danych wymiany stosów, jeśli chcesz. Zrobiłem bardzo przybliżone przybliżenie (filtrowanie oczywistych wartości odstających, ignorowanie samo-odpowiedzi, i c.), A typowy (tj. Mediana) czas wynosił około 20 minut do momentu opublikowania pierwszej odpowiedzi. –