From 786abddc77505f18bcc0911feaee512ea3a4aa49 Mon Sep 17 00:00:00 2001 From: Hans-Peter Deifel <hpd@hpdeifel.de> Date: Tue, 23 Oct 2018 23:23:20 +0200 Subject: [PATCH] random-dfa: Allow to output a single DFA in multiple formats This is required to compare the running time of different applications: Since the DFAs are generated randomly, we get a new one each run and so we have to have a way of outputting multiple formats in one run. --- src/random-dfa/Main.hs | 61 +++++++++++++++++++++++------------------- 1 file changed, 34 insertions(+), 27 deletions(-) diff --git a/src/random-dfa/Main.hs b/src/random-dfa/Main.hs index 9e91457..8cd706c 100644 --- a/src/random-dfa/Main.hs +++ b/src/random-dfa/Main.hs @@ -1,7 +1,11 @@ +{-# LANGUAGE TupleSections #-} {-# LANGUAGE TemplateHaskell #-} module Main (main) where import Control.Applicative +import Control.Monad ( forM_ ) +import Data.Maybe ( listToMaybe ) +import qualified Data.List.NonEmpty as NE import qualified Data.Text.Lazy.IO as TL import qualified Data.Text.Lazy.Builder as Build @@ -44,9 +48,8 @@ instance Show OutputFormat where data Options = Options { _optStates :: Int , _optLetters :: Int - , _optFile :: Maybe FilePath - , _optOutputFormat :: OutputFormat - } + , _optOutputs :: [(OutputFormat, Maybe (NE.NonEmpty Char))] + } deriving (Show) makeLensesWith abbreviatedFields ''Options @@ -61,22 +64,13 @@ options = OptParse.auto (OptParse.metavar "M" <> OptParse.help "Size of the alphabet") ) - <*> optional - (OptParse.strArgument - (OptParse.metavar "OUTPUT_FILE" <> OptParse.help - "Name of the file where the output should be written." + <*> some + (OptParse.argument + readOutput + ( OptParse.metavar "FORMAT:[OUTPUT_FILE]..." + <> OptParse.help "FORMAT can be 'dot', 'ma' or 'valmari'" ) ) - <*> (OptParse.option - readFormat - ( OptParse.long "output-format" - <> OptParse.metavar "FORMAT" - <> OptParse.value MA - <> OptParse.help - "Syntax used for the output. Posible values are 'ma', 'valmari' or 'dot'." - <> OptParse.showDefault - ) - ) readFormat :: OptParse.ReadM OutputFormat @@ -87,6 +81,18 @@ readFormat = OptParse.maybeReader $ \case _ -> Nothing +readOutput :: OptParse.ReadM (OutputFormat, Maybe (NE.NonEmpty Char)) +readOutput = OptParse.eitherReader $ \s -> case span (/= sep) s of + ([] , _ ) -> Left "a" + (_ , []) -> Left "b" + (format, _ : file) -> (, NE.nonEmpty file) <$> case format of + "ma" -> Right MA + "dot" -> Right Dot + "valmari" -> Right Valmari + _ -> Left "c" + where sep = ':' + + main :: IO () main = do opts <- OptParse.execParser @@ -97,16 +103,17 @@ main = do ) ) - let builder = case opts ^. outputFormat of - MA -> coalgB - Dot -> dotB - Valmari -> valmariB - dfa <- randomDFA (opts ^. states) (opts ^. letters) - let text = Build.toLazyText (builder dfa) - case opts ^. file of - Nothing -> TL.putStr text - Just filename -> TL.writeFile filename text + forM_ (opts ^. outputs) $ \(outputFormat, outputFile) -> do + let builder = case outputFormat of + MA -> coalgB + Dot -> dotB + Valmari -> valmariB + + let text = Build.toLazyText (builder dfa) + case outputFile of + Nothing -> TL.putStr text + Just filename -> TL.writeFile (NE.toList filename) text - return () + return () -- GitLab