Monadi (ohjelmointi)

Monad  on erityinen tietotyyppi toiminnallisissa ohjelmointikielissä , jolle on mahdollista asettaa pakollinen järjestys tiettyjen toimintojen suorittamiseksi tallennetuille arvoille [1] . Monadien avulla voit asettaa toimintojen järjestyksen, suorittaa operaatioita sivuvaikutuksineen ja muita toimintoja, joita on vaikea tai mahdoton toteuttaa toiminnallisessa ohjelmointiparadigmassa muilla tavoilla.

Monadin käsite ja termi tulee alun perin kategoriateoriasta , jossa se määritellään funktoriksi , jolla on lisärakenne. 1980-luvun lopulla ja 1990-luvun alussa alkanut tutkimus osoitti, että monadit pystyivät tuomaan näennäisesti erilaisia ​​tietotekniikan ongelmia yhdeksi toiminnalliseksi malliksi. Kategoriateoria asettaa myös useita muotovaatimuksia.[ mitä? ] , niin sanotut monadiset lait , joita kaikkien monadien on noudatettava ja joita voidaan käyttää monadisen koodin tarkistamiseen .

Kuvaus

Monadeja käytetään yleisimmin toiminnallisissa ohjelmointikielissä . Laisalla arviointimallilla vähennysjärjestys on tuntematon. Laskenta 1 + 3 + 6voidaan pienentää esimerkiksi arvoon 1 + 9tai 4 + 6. Monadit mahdollistavat alennuksen tilaamisen. Siksi on ironinen väite, että monadit ovat tapa ylikuormittaa puolipisteoperaattoria.

Monadi on kontti, joka tallentaa mielivaltaisen tyypin arvon. Sillä on oltava sidosfunktio, joka ottaa kaksi argumenttia: monadin nykyinen arvo ja funktio, joka ottaa nykyisen monadin tyypin arvon ja palauttaa uuden monadin. Sidosfunktion kutsumisen tulos on uusi monadi, joka saadaan soveltamalla ensimmäistä argumenttia toiseen. Tältä Java imperatiivisen kielen monadi ja yksi sen toteutuksista, Maybe -säiliö, voisivat näyttää:

tuonti java.util.function.Function ; rajapinta Monad < T > { < U > Monad < U > bind ( Function < T , Monad < U >> f ); } luokka Ehkä < T > toteuttaa Monadin < T > { yksityinen finaali Tval ; _ julkinen Ehkä ( T val ) { this . val = val ; } public T getVal () { return val ; } @Ohita julkinen < U > Monadi < U > sidos ( Function < T , Monad < U >> f ) { if ( val == null ) return new Ehkä < U > ( null ); paluu f . soveltaa ( val ); } } public class MonadApp { public static void main ( String [] args ) { Ehkä < Integer > x = new Ehkä <> ( 5 ); Monadi < Kokonaisluku > y = x . sitoa ( v -> new Ehkä <> ( v + 1 )) . sitoa ( v -> new Ehkä <> ( v * 2 )); Järjestelmä . ulos . println ( (( Ehkä < Kokonaisluku > ) y ). getVal () ); } }

Java 8:ssa käyttöönotetut toiminnalliset rajapinnat mahdollistavat monadin kaltaisen käyttöliittymän toteuttamisen.

Haskellissa _

Monad-luokka on vakiomoduulissa Prelude. Tämän luokan toteutus vaatii minkä tahansa yhden parametrin tyypin (sukutyyppi * -> *). Monadilla on neljä menetelmää

luokka Funktio f jossa fmap :: ( a -> b ) -> f a -> f b luokka Funktio f => Applikatiivinen f jossa puhdas :: a -> f a ( <*> ) :: f ( a -> b ) -> f a -> f b ( *> ) :: f a -> f b -> f b ( <* ) :: f a -> f b -> f a -- m :: * -> * luokka Applikatiivinen m => Monadi m missä ( >>= ) :: m a -> ( a -> m b ) -> m b ( >> ) :: m a -> m b -> m b -- oletusarvoisesti toteutettu: a >> b = a >>= \_ -> b return :: a -> m a -- = puhdas epäonnistuminen :: Merkkijono -> m a -- sivukutsut errorWithoutStackTrace oletuksena

Menetelmä returnvoi olla hämmentävä ohjelmoijille, jotka tuntevat pakottavat kielet: se ei keskeytä laskentaa, vaan vain pakkaa tyypin mielivaltaisen arvon amonadiin m. Menetelmällä failei ole mitään tekemistä monadien teoreettisen luonteen kanssa, mutta sitä käytetään, jos monadisessa arvioinnissa ilmenee kuvionsovitusvirhe. [2] ). Operaattori >>=on sitova funktio. Operaattori >> on operaattorin erikoistapaus >>=, jota käytetään, kun sitomisen tulos ei ole meille tärkeä.

Jotkut tyypit, jotka toteuttavat Monad-luokan:

  • IO, käytetään toimintoihin, joissa on sivuvaikutuksia. IO-konstruktorit ovat piilossa ohjelmoijalta, eikä monadin purkutoimintoja ole. Tämä estää likaisten toimintojen kutsumisen puhtaista toiminnoista.
  • Maybe. Arviointi keskeytyy, jos Nothing-arvo vastaanotetaan.
  • [] (список). Laskenta keskeytyy, kun lista on tyhjä. Jos luettelo ei ole tyhjä, operaattori >>=kutsuu funktion jokaiselle luettelon elementille.
  • Reader.
  • Writer.
  • State. Mahdollisuuksien lisäksi Reader mahdollistaa tilan muuttamisen.

Kielessä on myös do-notaatio, joka on kätevämpi tapa kirjoittaa monadisia funktioita. Tässä esimerkissä se f1käyttää do-notaatiota, mutta f2kirjoitetaan käyttämällä sidosoperaattoreita:

f1 = do s <- getLine putStrLn $ "Hei " ++ s putStrLn "Hyvästi" f2 = getLine >>= ( \ s -> putStrLn $ "Hei " ++ s ) >> putStrLn "Hyvästi"

Muistiinpanot

  1. Dushkin-FP, 2008 , s. 215.
  2. Jevgeni Kirpitšev. Monadit Haskellissa . Monadit ovat "joidenkin tuttujen idiomien yleistys ja myös toinen menetelmä niiden abstraktioimiseksi".

Linkit

Oppaat

Muut artikkelit

Kirjallisuus

  • Dushkin R.V. Turvallisuus // Ohjelmointitemppuja // Toiminnot // Kielen syntaksi ja idiomit // Haskell Language Reference / Chap. toim. D. A. Movchan. - M. : DMK Press , 2008. - S. 37-38. — 554 s. - 1500 kappaletta.  - ISBN 5-94074-410-9 , BBC 32.973.26-018.2, UDC 004.4.
  • Dushkin R. V. Funktionaalinen ohjelmointi Haskellissa. — M. : DMK Press, 2008. — 609 s. — ISBN 5-94074-335-8 .
  • Peyton-Jones, Simon . 8. Luento: Standard Beginning (Prelude) // Haskell Language and Libraries 98 .
  • Erkok Levent. Arvorekursio monadisissa laskelmissa. Oregon Graduate Institute. - 2002. - 162 s.