Versucht idiomatic Haskell die Paaroperationen fst und snd zu eliminieren, wie Kopf, Init, Schwanz usw.

  • Hier ist eine Funktion, die nicht direkt zu mir passt. Ich denke, ich muss das erste Mal loswerden.

     flagHolidays :: [(C.Day,Availability)] -> Handler [(C.Day,Availability)]
    flagHolidays dayPairs = do
       let days = map fst dayPairs
           yepNope = Prelude.map isHoliday days
           availability = Prelude.map flagAvailability yepNope
       return $ Prelude.zip days availability
     

    Der einzige Weg, den ich mir vorstellen kann, ist eine sehr hässliche Musterübereinstimmung entlang der Linien von (x,y):(xs,ys). Ist das Entfernen von fst sinnvoll? Wenn ja, wie kann man diese Liste von Paaren mit einem Muster anpassen?

    22 November 2011
    Michael Litchard
4 answers
  • Der Grund head, tail und init wird in idiomatischem Hashcode nicht verwendet, da sie keine Gesamtfunktionen sind - einige Eingaben verursachen einen Fehler. Das Übergeben einer leeren Liste an eine dieser Funktionen führt zu einer leeren Listenausnahme.

    fst und snd haben dieses Problem nicht, da keine Eingabe möglich ist zu den Funktionen, die eine Ausnahme verursachen. Es gibt also keinen Grund, diese Funktionen zu vermeiden.

    Ihre Funktion kann besser geschrieben werden (die anderen Kommentare geben gute Details dazu an), sind aber nicht auf die Verwendung von fst oder snd.

    22 November 2011
    David Miani
  • Machen Sie die Funktion rein und

     flagHolidays = map (second $ flagAvailability . isHoliday)
     

    Und um die eigentliche Frage zu beantworten, sofern nicht als übergeben ein Argument fst und snd wird selten verwendet.

    [Bearbeiten] Hmmm, ich habe das etwas voreilig geschrieben. Es ist falsch. Sie übergeben eine Liste von Paaren und verwenden niemals die zweite Komponente des Paars. Korrigiert, aber in derselben Richtung (und jetzt mit fst):

     flagHolidays = map ((id &&& flagAvailability . isHoliday) . fst)
     
    22 November 2011
    augustss
  • dayPairs ist eine Liste von Paaren, daher sollte days map fst dayPairs sein. Und das ist ein Ort, an dem die Verwendung von fst idiomatisch ist, als Argument für eine Funktion höherer Ordnung. Abgesehen davon wird es hauptsächlich verwendet, um die Bewertung von Paaren zu verschieben, wenn der Autor faule Muster vergessen hat.

    22 November 2011
    Daniel FischerSalik
  • Ich denke, Sie haben Recht, da die Art, wie Sie dies tun, nicht besonders idiomatisch erscheint.

    Fehler beiseite, es gibt viele bessere Möglichkeiten. Als ein paar Beispiele (wahrscheinlich nicht optimal, aber dennoch deutlich lesbarer) können Sie einen Lambda in Ihrer Map verwenden:

     return $ map (\(d,a) -> (d, flagAvailability $ isHoliday a)) dayPairs
     

    oder Sie können ein Listenverständnis verwenden:

     return [(day, flagAvailability $ isHoliday a) | (day,a) <- dayPairs]
     

    Möglicherweise gibt es eine clevere Methode Das zentrale Mapping ist völlig frei von Punkten, aber es lohnt sich vielleicht auch nicht - beide Ausdrücke machen die Operation ziemlich klar. Ich denke jedoch, dass das Entfernen der Variablen dayPairs eine Verbesserung darstellen könnte:

     flagHolidays = return . map (\(d,a) -> (d, flagAvailability $ isHoliday a))
     
    22 November 2011
    comingstorm