Önce soyut kavramları öğrenmek ve bunlara özgü örnekleri öğrenmek arasında ayrım yapalım .
Tamamen her yerde her yerde bulunmalarının basit nedenlerinden dolayı, tüm spesifik örnekleri görmezden gelmeyeceksiniz. Aslında, soyutlamalar büyük ölçüde mevcuttur, çünkü zaten yapacağınız şeyleri belirli örneklerle birleştirirler.
Diğer yandan soyutlamaların kendisi kesinlikle faydalıdır , ancak hemen gerekli değildir. Soyutlamaları tamamen görmezden gelebilir ve sadece çeşitli türleri doğrudan kullanabilirsiniz. Sonunda onları anlamak isteyeceksiniz, ancak daha sonra her zaman geri dönebilirsiniz. Aslında, bunu yaparsanız, ona geri döndüğünüzde alnınızı tokatlayacağınızı ve uygun genel amaçlı araçları kullanmak yerine neden bu kadar zaman harcadığınızı merak edeceğinizi neredeyse garanti edebilirim.
Örnek Maybe a
olarak alalım. Bu sadece bir veri türüdür:
data Maybe a = Just a | Nothing
Her şey kendi kendini belgelemek dışında; isteğe bağlı bir değerdir. Ya "sadece" tipte bir a
şeyiniz var ya da hiçbir şeyiniz yok. Var olmayan Maybe String
bir String
değere bakmayı temsil eden bir tür arama işleviniz olduğunu varsayalım . Öyleyse, hangisinin olduğunu görmek için değer üzerinde desen eşleşmesi yaparsınız:
case lookupFunc key of
Just val -> ...
Nothing -> ...
Bu kadar!
Gerçekten, ihtiyacınız olan başka bir şey yok. Hayır Functor
veya Monad
başka bir şey yok. Bunlar Maybe a
değerleri kullanmanın yaygın yollarını ifade ederler ... ama sadece deyimdir, "tasarım kalıpları", ne derseniz deyin.
Gerçekten tamamen kaçınamayacağınız tek yer IO
, ama yine de gizemli bir kara kutu, bu yüzden ne Monad
veya ne anlama geldiğini anlamaya değmez .
Aslında, burada herkes için notlar bulunmaktadır gerçekten hakkında bilmeniz gereken IO
şimdilik:
Bir şeyin bir türü varsa IO a
, bu bir şey yapan ve bir değer veren bir prosedür olduğu anlamına gelir a
.
do
Gösterimi kullanarak bir kod bloğunuz olduğunda , şöyle bir şey yazın:
do -- ...
inp <- getLine
-- etc...
... işlemi prosedürün sağında yürütmek ve<-
sonucu soldaki ada atamak anlamına gelir .
Halbuki böyle bir şeyiniz varsa:
do -- ...
let x = [foo, bar]
-- etc...
... düz ifadenin değerini (yordam değil) =
soldaki ada atamak anlamına gelir .
Oraya bir değer atamadan bir şey koyarsanız, şöyle:
do putStrLn "blah blah, fishcakes"
... bir prosedürü yürütmek ve geri döndürdüğü her şeyi göz ardı etmek anlamına gelir. Bazı prosedürlerin türü vardır IO ()
- ()
tür, hiçbir şey söylemeyen bir tür yer tutucudur, bu nedenle prosedürün bir şey yaptığı ve bir değer döndürmediği anlamına gelir. void
Diğer dillerdeki gibi bir fonksiyon.
Aynı prosedürü birden fazla kez uygulamak farklı sonuçlar verebilir; bu bir fikir. Bu nedenle IO
, değerini bir değerden "kaldırmanın" bir yolu yoktur , çünkü içindeki bir şey IO
bir değer değildir, bir değer elde etme prosedürüdür.
Bir do
bloktaki son satır, atamasız düz bir prosedür olmalıdır, burada bu prosedürün dönüş değeri tüm blok için dönüş değeri olur. Dönüş değerinin önceden atanmış bir değeri kullanmasını istiyorsanız, return
işlev düz bir değer alır ve bu değeri döndüren bir işlem yapmama yordamı verir.
Bunun dışında özel bir şey yok IO
; bu prosedürler aslında düz değerlerdir ve bunları etrafınızdan geçirebilir ve farklı şekillerde birleştirebilirsiniz. Sadece bir şey do
denilen bir blokta idam edildiğinde bir main
şey yaparlar.
Yani, bunun gibi sıkıcı, basmakalıp bir örnek programda:
hello = do putStrLn "What's your name?"
name <- getLine
let msg = "Hi, " ++ name ++ "!"
putStrLn msg
return name
... tıpkı zorunlu bir program gibi okuyabilirsiniz. Adlı bir prosedür tanımlıyoruz hello
. Yürütüldüğünde, önce adınızı soran bir ileti yazdırmak için bir yordam yürütür; daha sonra bir girdi satırı okuyan bir prosedür yürütür ve sonucu şu şekilde atar name
; daha sonra isme bir ifade atar msg
; sonra mesajı yazdırır; daha sonra tüm bloğun sonucu olarak kullanıcının adını döndürür. A olduğundan name
, bu , a döndüren yordam olduğu String
anlamına gelir, bu nedenle türü vardır . Ve şimdi bu prosedürü tıpkı yürüttüğü gibi başka bir yerde yürütebilirsiniz .hello
String
IO String
getLine
Pfff, monadlar. Kimin onlara ihtiyacı var?