Ricerca…


Osservazioni

Cerchiamo di chiarire alcuni equivoci che i principianti potrebbero fare.

Potresti aver riscontrato funzioni come:

max :: (Ord a) => a -> a -> a  
max m n  
  | m >= n = m  
  | otherwise = n  

I principianti visualizzeranno in genere max :: (Ord a) => a -> a -> a come funzione che accetta due argomenti (valori) di tipo a e restituisce un valore di tipo a . Tuttavia, ciò che sta realmente accadendo è che max sta prendendo un argomento di tipo a e restituendo una funzione di tipo a -> a . Questa funzione accetta un argomento di tipo a e restituisce un valore finale di tipo a .

Infatti, max può essere scritto come max :: (Ord a) => a -> (a -> a)

Considera la firma del tipo di max :

Prelude> :t max  
max :: Ord a => a -> a -> a  

Prelude> :t (max 75)  
(max 75) :: (Num a, Ord a) => a -> a  

Prelude> :t (max "Fury Road")  
(max "Fury Road") :: [Char] -> [Char]  

Prelude> :t (max "Fury Road" "Furiosa")  
(max "Fury Road" "Furiosa") :: [Char]  

max 75 e max "Fury Road" potrebbero non assomigliare a funzioni, ma in realtà lo sono.

La confusione deriva dal fatto che in matematica e in molti altri linguaggi di programmazione comuni, siamo autorizzati ad avere funzioni che accettano più argomenti. Tuttavia, in Haskell, le funzioni possono prendere solo un argomento e possono restituire valori come a , o funzioni come a -> a .

Funzione di aggiunta parzialmente applicata

Possiamo usare l' applicazione parziale per "bloccare" il primo argomento. Dopo aver applicato un argomento ci rimane una funzione che si aspetta un altro argomento prima di restituire il risultato.

(+) :: Int -> Int -> Int

addOne :: Int -> Int
addOne = (+) 1

Possiamo quindi utilizzare addOne per aggiungerne uno a un Int .

> addOne 5
6
> map addOne [1,2,3]
[2,3,4]

Restituzione di una funzione applicata parzialmente

Restituire funzioni parzialmente applicate è una tecnica per scrivere codice conciso.

add :: Int -> Int -> Int
add x = (+x)

add 5 2

In questo esempio (+ x) è una funzione parzialmente applicata. Si noti che il secondo parametro della funzione di aggiunta non deve essere specificato nella definizione della funzione.

Il risultato di chiamare add 5 2 è sette.

sezioni

Il sezionamento è un modo conciso per applicare parzialmente argomenti agli operatori di infissi.

Ad esempio, se vogliamo scrivere una funzione che aggiunge "ing" alla fine di una parola, possiamo usare una sezione per definire succintamente una funzione.

> (++ "ing") "laugh"
"laughing"

Notate come abbiamo parzialmente applicato il secondo argomento. Normalmente, possiamo applicare solo parzialmente gli argomenti nell'ordine specificato.

Possiamo anche usare la sezione sinistra per applicare parzialmente il primo argomento.

> ("re" ++) "do"
"redo"

Potremmo scrivere in modo equivalente usando l'applicazione parziale normale del prefisso:

> ((++) "re") "do"
"redo"

Una nota sulla sottrazione

I principianti spesso erroneamente negano la sezione.

> map (-1) [1,2,3]
***error: Could not deduce...

Questo non funziona poiché -1 viene analizzato come il letterale -1 piuttosto che l'operatore sezionato - applicato a 1 . La funzione subtract esiste per aggirare questo problema.

> map (subtract 1) [1,2,3]
[0,1,2]


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