Salut!
Je cherche à réaliser une horloge pour jouer aux échecs.
Il s'agit juste d'afficher deux compteurs, un pour les blancs l'autre pour les noirs.
Chaque compteur est incrémenté alternativement en frappant sur la barre espace.
Facile?
Pas si sur! Il y a des entrées, des sorties, des compteurs... Toutes choses qu'Haskell n'aimes pas trop.
Comment l'auriez vous fait?
J'ai voulu utiliser la paresse d'Haskell.
L'idée est de créer une liste paresseuse des dates auquelles on tape sur la barre espace.
On passe ensuite cette liste à une fonction d'affichage qui en extrait les affichages de compteurs.
Quelques préliminaires:
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24 {-# LANGUAGE GeneralizedNewtypeDeriving, TypeSynonymInstances, NoMonomorphismRestriction, FlexibleInstances, FlexibleContexts, FunctionalDependencies, TypeSynonymInstances, MultiParamTypeClasses, EmptyDataDecls, UndecidableInstances, ScopedTypeVariables#-} module Main (main) where import Control.Arrow import Data.Maybe import Data.IORef import Control.Concurrent import Text.Printf import Data.Time import Data.List import System.IO.Unsafe import System.IODans ce code cela vous a jaillit à la figure, horreur, un unsafePerformIO!!
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39 data Chrono = Chrono !NominalDiffTime !NominalDiffTime deriving (Eq, Show) data Couleur = Blanc | Noir deriving (Eq, Show) evens [] = [] evens [x] = [x] evens (x:_:xs) = x : evens xs odds [] = [] odds [x] = [] odds (_:x:xs) = x : odds xs --sépare une liste en éléments pairs et impairs cleave xs = (evens xs, odds xs) --times elapsed in each turns by white or black timetables l = cleave $ zipWith diffUTCTime (tail l) l --current chrono for white and black from the list of timestamps times :: [UTCTime] -> Chrono times l = uncurry Chrono $ times' l where times' l = (sum *** sum) (timetables l) --list of timestamps each time we press space bar buildList :: [IO UTCTime] buildList = (getChar >> getCurrentTime) : buildList --HORREUR on utilise unsafePerformIO!! unsafeList :: [UTCTime] unsafeList = map unsafePerformIO buildList timesClock = map times (drop 2 (inits unsafeList)) main = do hSetBuffering stdin NoBuffering hSetBuffering stdout NoBuffering hSetEcho stdout False mapM print timesClock putStrLn "fin"
Comment s'en débarrasser?
Toutes les tentatives que j'ai faites soit n'affichaient rien, soit affichaient une infinité de chrono à zéro.
Partager