wwffwfwf/app/Main.hs

69 lines
2.6 KiB
Haskell
Raw Normal View History

2024-09-27 00:19:59 +02:00
-- wwffwfwf - generates truth tables from logic expressions
-- Copyright (C) 2024 VegOwOtenks
--
-- This program is free software: you can redistribute it and/or modify
-- it under the terms of the GNU Affero General Public License as published by
-- the Free Software Foundation, either version 3 of the License, or
-- (at your option) any later version.
--
-- This program is distributed in the hope that it will be useful,
-- but WITHOUT ANY WARRANTY; without even the implied warranty of
-- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-- GNU Affero General Public License for more details.
--
-- You should have received a copy of the GNU Affero General Public License
-- along with this program. If not, see <https://www.gnu.org/licenses/>.
--
-- contact me via vegowotenks at jossco dot de
2024-09-17 11:42:58 +02:00
module Main (main) where
import Lib
2024-09-17 16:01:09 +02:00
import qualified Data.Set as Set
import qualified Data.Map as Map
import Data.Either (rights, lefts)
import Data.List (intercalate)
parseInputLine :: Int -> String -> Either ParseError Expression
parseInputLine n s = parseFullString ("stdin:" ++ show n) s
title :: [String] -> String
2024-10-18 10:00:54 +02:00
title ns = " " ++ intercalate " # " ns
2024-09-17 16:01:09 +02:00
header :: [Int] -> String
2024-10-18 10:00:54 +02:00
header ws = intercalate "#" . map (flip replicate '#' . (+2) ) $ ws
2024-09-17 16:01:09 +02:00
row :: [Int] -> [Bool] -> String
2024-10-18 10:00:54 +02:00
row ws rs = intercalate "#" $ (zipWith row' ws rs)
2024-09-17 16:01:09 +02:00
where
row' :: Int -> Bool -> String
row' w b = replicate (left+1) ' ' ++ (if b then "1" else "0") ++ replicate (right+1) ' '
where
left = (w-1) `div` 2
right = (w-1) - left
2024-09-17 11:42:58 +02:00
main :: IO ()
2024-09-17 16:01:09 +02:00
main = do
equation_strings <- fmap lines getContents
let equation_expressions = zipWith parseInputLine [0..] equation_strings
-- TODO: Show proper error messages
_ <- mapM putStrLn . map show . lefts $ equation_expressions
let variable_names = Set.toAscList . Set.unions . map collectVariableNames . rights $ equation_expressions
let value_combinations = mapM (const [True, False]) [1..length variable_names]
let value_maps = map Map.fromList $ zipWith (zipWith (,)) (cycle [variable_names]) value_combinations
let expression_strings = variable_names ++ equation_strings
let column_widths = map length expression_strings
putStrLn . title $ expression_strings
putStrLn . header $ column_widths
let expressions = rights $ map (parseFullString "<internal>") variable_names ++ equation_expressions
let results = map (\m -> map (evaluate m) expressions) value_maps
mapM_ putStrLn . map (row column_widths) $ results