ocaml a'list->a'list list

ocaml a'list->a'list list - Algo - Programmation

Marsh Posté le 31-10-2008 à 18:12:16    

yop

 

enoncé :

Citation :

Ecrire la fonction chaines croissantes : int list -> int list list    qui extrait les chaınes croissantes d’une liste d’entiers. Puisque notre critere ne s’interesse qu’aux nombres d’entiers contenus dans
chacune de ces chaınes, celles-ci pourront etre retournees dans n’importe quel ordre.

 

Exemple : chaines croissantes [2 ;6 ;4 ;2 ;6 ;8 ;0 ;0 ;4] peut retourner les listes [[2 ;6] ;[4] ;[2 ;6 ;8] ;[0 ;0 ;4]] ou [[4 ;0 ;0] ;[6 ;2] ;[4] ;[8 ;2 ;6]]

 

voila ce que j'ai fait pour le moment :

Code :
  1. let rec chaines_croissantes l=
  2.  match l with
  3.    |[]->[]
  4.    |z::[]->[z]
  5.    |x::y::s-> if x<=y
  6.                then (x :: (chaines_croissantes (y::s)))
  7.                else x :: [];(chaines_croissantes(y::s));;
 

message d'erreur :

Citation :

then (x :: (chaines_croissantes (y::s))) --> Warning S: this expression should have type unit.
val chaines_croissantes : 'a list -> 'a list = <fun>     (bien sur il me renvoie pas ma list de list)

 

ça fait 3 jours que je planche sur ce truc qui doit etre tout con, mais en tant que debutant je seche
sinon j'essaye de faire un truc du genre recursivement

Citation :

# [2::3::[5];2::4::[]];;
- : int list list = [[2; 3; 5]; [4; 2]]


mais j'ai un soucis avec le ; qui separe mes deux liste dans la liste global

 

si une personne a une idée, je suis tout ouie ^^

Message cité 1 fois
Message édité par pof1 le 31-10-2008 à 18:25:57
Reply

Marsh Posté le 31-10-2008 à 18:12:16   

Reply

Marsh Posté le 31-10-2008 à 18:26:01    

Déjà ton cas de base est faux si tu dois renvoyer une liste de liste.

Reply

Marsh Posté le 31-10-2008 à 18:34:28    

pof1 a écrit :

yop
 
enoncé :

Citation :

Ecrire la fonction chaines croissantes : int list -> int list list    qui extrait les chaınes croissantes d’une liste d’entiers. Puisque notre critere ne s’interesse qu’aux nombres d’entiers contenus dans
chacune de ces chaınes, celles-ci pourront etre retournees dans n’importe quel ordre.
 
Exemple : chaines croissantes [2 ;6 ;4 ;2 ;6 ;8 ;0 ;0 ;4] peut retourner les listes [[2 ;6] ;[4] ;[2 ;6 ;8] ;[0 ;0 ;4]] ou [[4 ;0 ;0] ;[6 ;2] ;[4] ;[8 ;2 ;6]]


 
voila ce que j'ai fait pour le moment :

Code :
  1. let rec chaines_croissantes l=
  2.  match l with
  3.    |[]->[]
  4.    |z::[]->[z]
  5.    |x::y::s-> if x<=y
  6.                then (x :: (chaines_croissantes (y::s)))
  7.                else x :: [];(chaines_croissantes(y::s));;


 
message d'erreur :

Citation :

then (x :: (chaines_croissantes (y::s))) --> Warning S: this expression should have type unit.
val chaines_croissantes : 'a list -> 'a list = <fun>     (bien sur il me renvoie pas ma list de list)



Je fais pas de caml, mais ça sent le type mismatch, tes cas n'ont pas tous l'air de renvoyer le même type. Genre (x :: (chaines_croissantes (y::s))) si je ne me trompe pas ça va renvoyer une list d'int, alors que tu veux des listes de listes d'int.


---------------
Stick a parrot in a Call of Duty lobby, and you're gonna get a racist parrot. — Cody
Reply

Marsh Posté le 31-10-2008 à 18:38:58    

oui vous avez raison, la c'est en fait un essaie parmis tant d'autre, certain autre essaie etait bien typpé, mais le mieux que jai reussi ça donnait ça au final

 

chaines_croissantes [2;5;4;9;3];;
- int list list = [[2];[5];[4];[9];[3]];;

 


Message édité par pof1 le 31-10-2008 à 18:39:21
Reply

Marsh Posté le 31-10-2008 à 19:14:22    

Je pense que tu as besoin de deux fonctions, une de base qui détecte une suite ascendante (ce que tu as, globalement) et une appelée par celle ci qui va renvoyer la liste ascendante et le reste de la liste.


---------------
Stick a parrot in a Call of Duty lobby, and you're gonna get a racist parrot. — Cody
Reply

Marsh Posté le 31-10-2008 à 19:24:46    

En Haskell, ça donne un truc du genre:

Code :
  1. growing [] = []
  2. growing [x] = [[x]]
  3. growing (x1:x2:xs)
  4.    | x1 <= x2 =
  5.        let (ys, zs) = growSpan (x1:x2:xs)
  6.        in ys : growing zs
  7.    | otherwise =
  8.        [x1] : growing (x2:xs)
  9.  
  10. growSpan xs = _growSpan xs []
  11.    where
  12.      _growSpan [x] serie = (reverse (x:serie), [])
  13.      _growSpan (x1:x2:xs) serie
  14.              | x1 <= x2 =
  15.                  _growSpan (x2:xs) (x1:serie)
  16.              | otherwise =
  17.                  (reverse (x1:serie), x2:xs)


et à l'appel:

*Main> growing [2,6,4,2,6,8,0,0,4]
[[2,6],[4],[2,6,8],[0,0,4]]


Ca a l'air d'être bon.


Message édité par masklinn le 31-10-2008 à 19:25:40

---------------
Stick a parrot in a Call of Duty lobby, and you're gonna get a racist parrot. — Cody
Reply

Marsh Posté le 01-11-2008 à 01:58:05    

haaaaa un grand merci a toi, tu m'as dirigé dans la bonne direction, j'ai fini par y arriver (au bout de 3heure d'acharnement dans cette voie)
pfiuuuuuuuu, hé bah dit donc

 

voila ce que ça donne en ocamL

 
Code :
  1. let rec chaines_croissante l=
  2.      if l=[]
  3.      then []
  4.       else
  5.         let rec morceau l1=
  6.            match l1 with
  7.             |[]->([],[])
  8.             |z::[]->([z],[])
  9.             |x::y::s ->
  10.                 if x<=y
  11.                  then let (a,b) = morceau (y::s) in (x::a,b)
  12.                  else (x::[],y::s)
  13.         in let (a,b)=(morceau l)
  14.         in  a::chaines_croissante b;;
 

apparemment le Haskell est un langage proche du caml, étant donné ton expérience, pourquoi le préfères tu au caml?


Message édité par pof1 le 01-11-2008 à 02:03:04
Reply

Marsh Posté le 01-11-2008 à 10:07:55    

pas vraiment de raison, je trouve la syntaxe ML moche et quand je me demandais quel langage fonctionnel typé statiquement essayer j'ai trouve des gens faisant du haskell (online) rapidement.
 
Rien d'objectif donc et sur certains points ocaml>haskell (vitesse d'exécution par exemple)
 
Au oui, haskell n'est pas un langage strict (au niveau du modèle d'évaluation) ce qui a des conséquences intéressantes.
Et il est pur, ce qui a des conséquences complexifiantes :D


---------------
Stick a parrot in a Call of Duty lobby, and you're gonna get a racist parrot. — Cody
Reply

Marsh Posté le 01-11-2008 à 10:23:17    

Masklinn >> J'ai une question : ne pourrais-tu pas éviter les reverse ?
En Prolog pour faire ça on parcourt la liste complète et on construit le résultat à partir de la fin en étudiant à chaque fois le nombre courant et celui qui vient d'être inséré dans la liste résultat.

Reply

Marsh Posté le 01-11-2008 à 10:45:32    

Trap D a écrit :

Masklinn >> J'ai une question : ne pourrais-tu pas éviter les reverse ?


Peut-être, mais je vois pas spécialement l'intérêt de s'embêter pour ça.

 

edit: et en construisant en partant de la fin, on risque de perdre le tail-rec. Construire le résultat en inversé et reverse à la fin est un idiôme fonctionnel standard, je vois pas pourquoi s'embêter.


Message édité par masklinn le 01-11-2008 à 14:33:02

---------------
Stick a parrot in a Call of Duty lobby, and you're gonna get a racist parrot. — Cody
Reply

Marsh Posté le 01-11-2008 à 10:45:32   

Reply

Marsh Posté le 01-11-2008 à 18:09:23    

Je préfère ce genre d'explications.

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed