(* lire un dictionnaire contenu dans un fichier *) let lire_dict fn = let ic=open_in fn in let rec aux dict = let mot = input_line ic in if mot="__FIN__" then (close_in ic;dict) else aux (mot::dict) in aux [] ;; (* associer a chaque mot sa signature *) let explode s = let n = String.length s in let rec aux l = function 0 -> l | n -> aux (String.get s (n-1)::l) (n-1) in aux [] n;; let signe_mot m = List.sort compare (explode m);; let sign dict = List.rev_map (fun m -> m,signe_mot m) dict;; (* trier sur la signature *) let trie sdict = List.sort (fun (m,s) -> fun (m',s') -> compare s s') sdict;; (* produire la liste des listes des mots anagrammes *) let rec meme_sign ((sign,lanas) as prev) = function [] -> lanas,[] | ((m,sign')::rest) as l -> if sign<>sign' then lanas,l else meme_sign (sign,m::lanas) rest let rec scan_signs l = function [] -> l | (m,sign)::rest -> let manas,rest' = meme_sign (sign,[m]) rest in scan_signs (manas::l) rest' let groupe tsdict = scan_signs [] tsdict;; (* imprimer les anagrammes *) let imprime_anas lanas = List.iter (fun l -> List.iter (fun m -> print_string (m^" ")) l; print_newline()) lanas;; (* on met tout ensemble *) let anagrammes fn = let dict = lire_dict fn in let tsdict = trie (sign dict) in let anas = List.filter (fun l -> List.length l > 1) (groupe tsdict) in let sanas = List.sort compare (List.map (fun l -> List.sort compare l) anas) in imprime_anas sanas ;;