Ricerca…


Osservazioni

La maggior parte delle funzioni Haskell vengono chiamate con il nome della funzione seguito da argomenti (notazione prefisso). Per le funzioni che accettano due argomenti come (+), a volte ha senso fornire un argomento prima e dopo la funzione (infisso).

Preludio

Logico

&& è logico AND, || è logico OR.

== è l'uguaglianza, /= non-uguaglianza, < / <= minore e > / >= operatori maggiori.

Operatori aritmetici

Gli operatori numerici + , - e / comportano in gran parte come ci si aspetterebbe. (La divisione funziona solo su numeri frazionari per evitare problemi di arrotondamento - la divisione intera deve essere eseguita con quot o div ). Più inusuali sono i tre operatori di exponentiation di Haskell:

  • ^ prende una base di qualsiasi tipo di numero con un potere integrale non negativo. Funziona semplicemente con la moltiplicazione ( veloce ) iterata. Per esempio

    4^5  ≡  (4*4)*(4*4)*4
    
  • ^^ fa lo stesso nel caso positivo, ma funziona anche per gli esponenti negativi. Per esempio

    3^^(-2)  ≡  1 / (2*2)
    

    A differenza di ^ , questo richiede un tipo di base frazionale (cioè 4^^5 :: Int non funzionerà, solo 4^5 :: Int o 4^^5 :: Rational ).

  • ** implementa l'esponenziazione numero reale. Questo funziona per argomenti molto generali, ma è più costoso rispetto a ^ o ^^ e generalmente incorre in piccoli errori in virgola mobile.

    2**pi  ≡  exp (pi * log 2)
    

elenchi

Esistono due operatori di concatenazione:

  • : (pronuncia cons ) anteporre un singolo argomento prima di una lista. Questo operatore è in realtà un costruttore e può quindi essere utilizzato anche per associare la stringa ("inverse construct") a un elenco.

  • ++ concatena intere liste.

    [1,2] ++ [3,4]  ≡  1 : 2 : [3,4]  ≡  1 : [2,3,4]  ≡  [1,2,3,4]
    

!! è un operatore di indicizzazione.

[0, 10, 20, 30, 40] !! 3  ≡  30

Si noti che gli elenchi di indicizzazione sono inefficienti (complessità O ( n ) invece di O (1) per gli array o O (log n ) per le mappe ); In Haskell è generalmente preferito decostruire le liste piegando la corrispondenza del modello anziché l'indicizzazione.

Controllo del flusso

  • $ è un operatore di applicazioni di funzione.

    f $ x  ≡  f x
           ≡  f(x)  -- disapproved style
    

    Questo operatore è usato principalmente per evitare parentesi. Ha anche una versione rigorosa $! , che forza l'argomento da valutare prima di applicare la funzione.

  • . compone le funzioni.

    (f . g) x  ≡  f (g x)  ≡  f $ g x
    
  • >> sequenze azioni monadiche. Ad esempio writeFile "foo.txt" "bla" >> putStrLn "Done." scriverà prima su un file, quindi stamperà un messaggio sullo schermo.

  • >>= fa lo stesso, accettando anche un argomento da passare dalla prima azione alla seguente. readLn >>= \x -> print (x^2) attenderà che l'utente inserisca un numero, quindi readLn >>= \x -> print (x^2) il quadrato di quel numero sullo schermo.

Operatori personalizzati

In Haskell, puoi definire qualsiasi operatore di infissi che ti piace. Ad esempio, potrei definire l'operatore elenco-inviluppo come

(>+<) :: [a] -> [a] -> [a]
env >+< l = env ++ l ++ env

GHCi> "**">+<"emphasis"
"**emphasis**"

Si dovrebbe sempre dare a tali operatori una dichiarazione di fissità , come

infixr 5 >+<

(che significherebbe >+< binds strettamente come ++ e : do).

Trovare informazioni sugli operatori infissi

Poiché gli hasnee sono così comuni in Haskell, dovrai regolarmente controllare la loro firma, ecc. Fortunatamente, questo è semplice come per qualsiasi altra funzione:

  • I motori di ricerca Haskell Hayoo e Hoogle possono essere utilizzati per operatori infissi, come per qualsiasi altra cosa definita in alcune librerie.

  • In GHCi o IHaskell, è possibile utilizzare la :i e :t (i nfo e t ipo) le direttive per imparare le proprietà di base di un operatore. Per esempio,

    Prelude> :i +
    class Num a where
      (+) :: a -> a -> a
      ...
          -- Defined in ‘GHC.Num’
    infixl 6 +
    Prelude> :i ^^
    (^^) :: (Fractional a, Integral b) => a -> b -> a
          -- Defined in ‘GHC.Real’
    infixr 8 ^^
    

    Questo mi dice che ^^ lega più strettamente di + , entrambi prendono tipi numerici come loro elementi, ma ^^ richiede che l'esponente sia integrale e la base sia frazionaria.
    Meno dettagliato :t richiede l'operatore tra parentesi, come

    Prelude> :t (==)
    (==) :: Eq a => a -> a -> Bool
    


Modified text is an extract of the original Stack Overflow Documentation
Autorizzato sotto CC BY-SA 3.0
Non affiliato con Stack Overflow