Optimized a bit further

Added README.md
master
Frédéric BISSON 9 years ago
parent bebd8289b4
commit 07eb8a0ea5

@ -0,0 +1,91 @@
Wookie à poil dur selon Zigazou
===============================
Voici la solution de Zigazou au programming challenge du Wookie à poil dur.
Compilation
-----------
ghc -O2 wookie.hs
Utilisation
-----------
./wookie sequence.txt
Algorithme
----------
Lalgorithme suivi est naïf mais fonctionne bien sur nos machines mordernes.
Le principe consiste à partir de chaque Reads constituant la séquence finale et
de les monter comme un puzzle en regardant les pièces qui peuvent senficher sur
la dernière pièce.
Partons dun exemple basique :
abcd
efgh
cdef
ghij
La chaîne à reconstituer est donc `abcdefghij`
Pour conserver létat en cours de chacune des recherches, on travaille sur des
couples (séquence en cours, pièces restantes).
On partira avec les valeurs initiales suivantes :
[ ( [abcd], [efgh, cdef, ghij] )
, ( [efgh], [abcd, cdef, ghij] )
, ( [cdef], [abcd, efgh, ghij] )
, ( [ghij], [abcd, efgh, cdef] )
]
Ce travail est effectué par la fonction `initSequences`.
Pour chacun de ces couples, on va tester chacune des pièces restantes :
( [abcd], [efgh, cdef, ghij] )
donne donc
[ ( [abcd, efgh], [cdef, ghij] )
, ( [abcd, cdef], [efgh, ghij] )
, ( [abcd, ghij], [efgh, cdef] )
]
Sur la liste obtenue, on va virer les séquences invalides :
[ ( [abcd, efgh], [cdef, ghij] ) -- invalide, abcd et efgh ne coïncident pas
, ( [abcd, cdef], [efgh, ghij] ) -- valide !
, ( [abcd, ghij], [efgh, cdef] ) -- invalide, abcd et ghij ne coïncident pas
]
et nous donne
[ ( [abcd, cdef], [efgh, ghij] ) ]
Quand on applique cela à toutes les séquences initiales, on obtient les listes :
[ ( [abcd, cdef], [efgh, ghij] )
, ( [efgh, ghij], [abcd, cdef] )
, ( [cdef, efgh], [abcd, ghij] )
]
Note : les 4 couples nont donné naissance quà 3 couples car la séquence finale
ne peut pas commencer par ghij (il ny a aucun morceau qui permet de prolonger).
À ce stade, on repère sil existe une séquence complète (une séquence nayant
plus de morceaux restants). Si ce nest pas le cas, on répète cette étape
jusquà trouver la séquence complète.
Considérations
--------------
`wookie.hs` ne prend en compte que les morceaux se recouvrant avec au moins 3
bases. Par exemple `abcdef` et `defghi` coïncident mais pas `abcdef` et `efghij`.
Ce comportement peut être changé en modifiant `minbase`.
Lalgorithme fonctionne uniquement sil existe au moins une solution utilisant
tous les morceaux.

@ -6,6 +6,12 @@ import qualified Data.Set as Set
import Data.Maybe (catMaybes)
import Data.List (find)
{-|
Taille minimum pour le recouvrement des `Reads`
-}
minbase :: Int
minbase = 3
{-|
A `Reads` is a bit of a sequence
-}
@ -74,7 +80,7 @@ Try to add a `Reads` to a `Sequence`. The `Reads` must be a member of remaining
-}
(-+-) :: Sequence -> Reads -> Maybe Sequence
(-+-) (Sequence is sr) r
| coincide (head is) r > 2 = Just (Sequence (r:is) (delete r sr))
| coincide (head is) r >= minbase = Just (Sequence (r:is) (delete r sr))
| otherwise = Nothing
{-|
@ -86,11 +92,10 @@ next s@(Sequence _ sr) = catMaybes [ s -+- r | r <- toList sr ]
{-|
Given a `List` of `Sequence`, returns a `List` of `Sequence` with one more
`Reads` added from the remaining `Reads`. Invalid `Sequence` are filtered out
of the resulting `List`.
`Reads` added from the remaining `Reads`.
-}
nexts :: [Sequence] -> [Sequence]
nexts = filter valid . concatMap next
nexts = concatMap next
{-|
Repeat the `nexts` action until there is a complete `Sequence`.

Loading…
Cancel
Save