Zoeken…


Functiesamenstellingen met meerdere kanalen

Arrow is, vaag gesproken, de klasse van morfismen die soortgelijke functies samenstellen, met zowel seriële compositie als "parallelle compositie". Hoewel het het meest interessant is als een generalisatie van functies, is de Arrow (->) instantie zelf al behoorlijk nuttig. Bijvoorbeeld de volgende functie:

spaceAround :: Double -> [Double] -> Double
spaceAround x ys = minimum greater - maximum smaller
 where (greater, smaller) = partition (>x) ys

kan ook worden geschreven met pijlcombinators:

spaceAround x = partition (>x) >>> minimum *** maximum >>> uncurry (-)

Dit soort compositie kan het best worden gevisualiseerd met een diagram:

                       ──── minimum ────
                   ╱           *            ╲
──── partition (>x) >>>        *        >>>  uncurry (-) ───
                   ╲           *            ╱
                       ──── maximum ──── 

Hier,

  • De operator >>> is slechts een omgedraaide versie van het gewone . compositie-operator (er is ook een <<< -versie die van rechts naar links componeert). Het leidt de gegevens van de ene verwerkingsstap naar de volgende.

  • de uitgaande geeft aan dat de gegevensstroom is opgesplitst in twee "kanalen". In termen van Haskell-types wordt dit gerealiseerd met tupels:

    partition (>x) :: [Double] -> ([Double], [Double])
    

    splitst de stroom in twee [Double] kanalen, terwijl

    uncurry (-) :: (Double,Double) -> Double
    

    voegt twee Double kanalen samen.

  • *** is de parallelle compositie-operator. Het laat maximum en minimum onafhankelijk werken op verschillende kanalen van de gegevens. Voor functies is de handtekening van deze operator

    (***) :: (b->c) -> (β->γ) -> (b,β)->(c,γ)
    

Tenminste in de categorie Hask (dwz in de Arrow (->) instantie), berekent f f***g feitelijk f en g parallel zoals in, op verschillende threads. In theorie zou dit echter wel mogelijk zijn.



Modified text is an extract of the original Stack Overflow Documentation
Licentie onder CC BY-SA 3.0
Niet aangesloten bij Stack Overflow