Précédent   Forum du club des développeurs et IT Pro > Autres langages > Langages fonctionnels > Haskell
Haskell Forum d'entraide sur la programmation en langage fonctionnel Haskell
Partagez cette discussion sur d'autres réseaux sociaux : Viadeo Twitter Google Facebook Digg Delicious MySpace Yahoo
Réponse
 
Outils de la discussion
Publicité
'
Vieux 22/11/2010, 22h57   #1
james-mi
Membre du Club
 
Inscription : mai 2005
Messages : 130
Détails du profil
Informations forums :
Inscription : mai 2005
Messages : 130
Points : 47
Points : 47
Par défaut Question sur Data.fromList

il y a qqch que je n'arrive pas à comprendre dans Data.Map :

1.
Code :
1
2
3
ghci > fromList [(1 ,2) ,(3 ,4) ,(3 ,2) ,(5 ,5)]
fromList [(1,2),(3,2),(5,5)]
it :: Map Integer Integer
pourquoi la valeur renvoyée est-elle "fromList ..." alors que fromList, de toute évidence, n'est pas un constructeur (pour qui la majusculle initiale est obligatoire).
cela renvoie une valeur sous la forme d'une fonction ? ? ?

2. D'autre part ,
Code :
1
2
ghci > :t fromList
fromList :: (Ord k) => [(k, a)] -> Map k a
ok, jusque là ça va ...
puis :
Code :
1
2
let myFromList = fromList
myFromList :: [((), a)] -> Map () a
On sent bien qu'on ne va pas aller loin avec un Map ()
effectivement :
Code :
1
2
3
4
5
6
7
8
9
10
11
12
ghci> myFromList [(1 ,2) ,(3 ,4) ,(3 ,2) ,(5 ,5)]


<interactive>:1:37:
    No instance for (Num ())
      arising from the literal `5' at <interactive>:1:37
    Possible fix: add an instance declaration for (Num ())
    In the expression: 5
    In the expression: (5, 5)
    In the first argument of `myFromList', namely
        `[(1, 2), (3, 4), (3, 2), (5, 5)]'
Pourquoi ne peut-on pas créer myFromList de cette manière ?

merci d'avance à ceux qui pourront m'expliquer ...
james-mi est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 23/11/2010, 09h42   #2
viro
Nouveau Membre du Club
 
Inscription : octobre 2002
Messages : 36
Détails du profil
Informations personnelles :
Localisation : France

Informations forums :
Inscription : octobre 2002
Messages : 36
Points : 27
Points : 27
Citation:
Envoyé par james-mi Voir le message
il y a qqch que je n'arrive pas à comprendre dans Data.Map :

1.
Code :
1
2
3
ghci > fromList [(1 ,2) ,(3 ,4) ,(3 ,2) ,(5 ,5)]
fromList [(1,2),(3,2),(5,5)]
it :: Map Integer Integer
pourquoi la valeur renvoyée est-elle "fromList ..." alors que fromList, de toute évidence, n'est pas un constructeur (pour qui la majusculle initiale est obligatoire).
cela renvoie une valeur sous la forme d'une fonction ? ? ?
Ce que tu vois n'est pas la valeur renvoyée, c'est sa traduction sous forme de chaine de caractères.
sous ghci, fromList [(1,etc...] devient l'équivalent de
print $ fromList ...
qui lui même est
putStrLn $ show $ fromList ....

Ensuite se pose la question : comment représenter une Map ? on peut imaginer plusieurs façons, mais les auteurs de Data.Map on retenu celle qui consiste a imprimer "fromList " puis la conversion de la map en liste.

Ce qui est marrant c'est que quand tu tapes le fromList [etc...] ghci convertit la liste en Map, puis pour afficher le résultat fait aussitôt le travail inverse.

Il n'y a pas à s'inquiéter de ca, en pratique on n'affiche pas une Map, on s'en sert pour faire des recherches.

Citation:
Envoyé par james-mi Voir le message
2. D'autre part ,
Code :
1
2
ghci > :t fromList
fromList :: (Ord k) => [(k, a)] -> Map k a
ok, jusque là ça va ...
puis :
Code :
1
2
let myFromList = fromList
myFromList :: [((), a)] -> Map () a
On sent bien qu'on ne va pas aller loin avec un Map ()
effectivement :
Code :
1
2
3
4
5
6
7
8
9
10
11
12
ghci> myFromList [(1 ,2) ,(3 ,4) ,(3 ,2) ,(5 ,5)]


<interactive>:1:37:
    No instance for (Num ())
      arising from the literal `5' at <interactive>:1:37
    Possible fix: add an instance declaration for (Num ())
    In the expression: 5
    In the expression: (5, 5)
    In the first argument of `myFromList', namely
        `[(1, 2), (3, 4), (3, 2), (5, 5)]'
Pourquoi ne peut-on pas créer myFromList de cette manière ?
A cause de la restriction de monomorphisme, ghc(i) ne peux pas inférer un type polymorphique pour myFromList.
En pratique dans un vrai programme, ghc dispose de suffisamment d'informations de contexte pour trouver un type précis pour une fonction du genre de myFromList, donc ca pose rarement un problème.

Deux façons de contourner:

1) définir myFromList comme suit :

let myFromList l = fromList l

2) virer la restriction de monomorphisme:

:set -XNoMonomorphismRestriction
let myFromList = fromList

A propos de cette restriction, j'aurais du mal à expliquer la raison, mais elle est tellement débatue qu'une recherche de monomorphisme sur google devrait donner des réponses. En anglais , par contre.
viro est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 23/11/2010, 22h42   #3
james-mi
Membre du Club
 
Inscription : mai 2005
Messages : 130
Détails du profil
Informations forums :
Inscription : mai 2005
Messages : 130
Points : 47
Points : 47
Citation:
Envoyé par viro Voir le message
Ce que tu vois n'est pas la valeur renvoyée, c'est sa traduction sous forme de chaine de caractères.
sous ghci, fromList [(1,etc...] devient l'équivalent de
print $ fromList ...
qui lui même est
putStrLn $ show $ fromList ....

Ensuite se pose la question : comment représenter une Map ? on peut imaginer plusieurs façons, mais les auteurs de Data.Map on retenu celle qui consiste a imprimer "fromList " puis la conversion de la map en liste.

Ce qui est marrant c'est que quand tu tapes le fromList [etc...] ghci convertit la liste en Map, puis pour afficher le résultat fait aussitôt le travail inverse.

Il n'y a pas à s'inquiéter de ca, en pratique on n'affiche pas une Map, on s'en sert pour faire des recherches.



A cause de la restriction de monomorphisme, ghc(i) ne peux pas inférer un type polymorphique pour myFromList.
En pratique dans un vrai programme, ghc dispose de suffisamment d'informations de contexte pour trouver un type précis pour une fonction du genre de myFromList, donc ca pose rarement un problème.

Deux façons de contourner:

1) définir myFromList comme suit :

let myFromList l = fromList l

2) virer la restriction de monomorphisme:

:set -XNoMonomorphismRestriction
let myFromList = fromList

A propos de cette restriction, j'aurais du mal à expliquer la raison, mais elle est tellement débatue qu'une recherche de monomorphisme sur google devrait donner des réponses. En anglais , par contre.
OK, merci.

Donc quand je construit mes fonctions plus compexes, et que je les évalues dans GHCi (parce que ça aide bien quand on est un peu perdu) et que ça me renvoie "fromList [(,.....),...], je sais qu'en réalité j'ai affaire à une structure Map, c'est bien ça ?
james-mi est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 24/11/2010, 08h27   #4
viro
Nouveau Membre du Club
 
Inscription : octobre 2002
Messages : 36
Détails du profil
Informations personnelles :
Localisation : France

Informations forums :
Inscription : octobre 2002
Messages : 36
Points : 27
Points : 27
Citation:
Envoyé par james-mi Voir le message
OK, merci.

Donc quand je construit mes fonctions plus compexes, et que je les évalues dans GHCi (parce que ça aide bien quand on est un peu perdu) et que ça me renvoie "fromList [(,.....),...], je sais qu'en réalité j'ai affaire à une structure Map, c'est bien ça ?
Pas forcément. Rien n'empêche qu'un autre type de donnée définisse sa méthode show par "fromList [... ]"
Après tout, ce n'est que du texte.
Donc pour en être sûr, il te faut interroger le type de ton expression; en tapant sous ghci :t mon_expression_complexe.

P.S, précision supplémentaire au sujet du problème:

Code :
1
2
let myFromList = fromList
-- myFromList :: [((), a)] -> Map () a
quand tu le compile, ghc te refuse avec le message suivant
Code :
1
2
3
4
5
6
    Ambiguous type variable `k' in the constraint:
      `Ord k' arising from a use of `fromList' at tt.hs:6:13-20
    Possible cause: the monomorphism restriction applied to the following:
      myFromList :: forall a. [(k, a)] -> Map k a (bound at tt.hs:6:0)
    Probable fix: give these definition(s) an explicit type signature
                  or use -XNoMonomorphismRestriction
Or, il te l'a accepté sous ghci, mais avec une signature bizarre. Ce qui se passe, c'est que sous ghci, il y a des règles qui font qu'un type par défaut est sélectionné quand il y a ambiguité. Dans ce cas, le type par défaut est () donc Map k a devient Map () a.

Ce sont ces règles de "type par défaut" qui sont responsables sous ghci du résultat suivant:

Code :
1
2
3
4
5
6
Prelude> :t (+)
(+) :: (Num a) => a -> a -> a
Prelude> let p=(+)
Prelude> :t p
p :: Integer -> Integer -> Integer
Prelude>
Donc Integer est le type par défaut dans ghci retenu quand il y a contrainte sur la classe Num.


Code :
1
2
3
4
5
6
7
Prelude> import Data.List
Prelude Data.List> :t sort
sort :: (Ord a) => [a] -> [a]
Prelude Data.List> let s=sort
Prelude Data.List> :t s
s :: [()] -> [()]
Prelude Data.List>
Donc () est le type par défaut retenu dans ghci quand il y a contrainte sur la classe Ord.

Code :
1
2
3
4
5
6
7
Prelude Data.List> :t show
show :: (Show a) => a -> String
Prelude Data.List>                                                                                                                                                    
Prelude Data.List> let h=show                                                                                                                                         
Prelude Data.List> :t h                                                                                                                                               
h :: () -> String                                                                                                                                                     
Prelude Data.List>
Donc () est le type par défaut retenu dans ghci quand il y a contrainte sur la classe Show.

etc, etc, etc.
viro est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 24/11/2010, 23h49   #5
james-mi
Membre du Club
 
Inscription : mai 2005
Messages : 130
Détails du profil
Informations forums :
Inscription : mai 2005
Messages : 130
Points : 47
Points : 47
Citation:
Envoyé par viro Voir le message
...
OK merci viro, ça m'éclaircit bien les idées
james-mi est déconnecté   Envoyer un message privé Réponse avec citation 00
Réponse Cette discussion est résolue.
Outils de la discussion

Navigation rapide


Fuseau horaire GMT +2. Il est actuellement 12h18.


 
 
 
 
Partenaires

Hébergement Web