Haskell-如何更改节目以获得正确的输出
我已经定义了这些数据类型,我正在尝试创建和打印这些数据类型Haskell-如何更改节目以获得正确的输出,haskell,Haskell,我已经定义了这些数据类型,我正在尝试创建和打印这些数据类型 type TNonTerminal = String -- will be creating own ones where [A-Z] won't be enough type TTerminals = Char type TSymbols = String -- both terminals and nonterminals data Rule = Rule { leftSide :: TNonTerminal ,
type TNonTerminal = String -- will be creating own ones where [A-Z] won't be enough
type TTerminals = Char
type TSymbols = String -- both terminals and nonterminals
data Rule = Rule
{ leftSide :: TNonTerminal
, rightSide :: [TSymbols]
} deriving (Eq)
data RightLinearGrammar = RLG
{ nonterminals :: [TNonTerminal]
, terminals :: [TTerminals]
, firstNonterminal :: TNonTerminal
, rules :: [Rule]
} deriving (Eq)
所以我还创建了那些Show实例
instance Show Rule where
show (Rule ls rs) = show ls ++ "->" ++ show rs ++ "\n"
instance Show RightLinearGrammar where
show (RLG n t fn r) = show n ++ "\n" ++ show t ++ "\n" ++ show fn ++ "\n" ++ show r ++ "\n"
我得到了这个输出(为了澄清,我创建了rightlineargramar类型,并调用了putStr$show rlg
):
我应该如何更改代码以获得更好的输出
A,B
a,b,c
A
A->aaB
A->ccB
B->bB
B->#
默认情况下,
show
在字符串周围加引号,在列表周围加括号。如果您只是返回到用逗号或换行符连接字符串和列表,您应该会得到预期的输出:
导入数据列表(插入)
实例显示规则在哪里
显示(规则ls rs)=ls++“->”+++插入“,”rs
实例Show rightlineargramar,其中
show(RLG n t fn r)=插入“,”n++“\n“++t++”\n“++fn++”\n“++”(插入“\n”$map show r)++”\n”
您或者需要将类型同义词替换为newtypes
,并在其上定义show
,以执行所需操作,或者更可能的是将实例中对show
的调用替换为对自定义格式化程序函数的调用
注意:show
确实不是您尝试执行的正确功能,因为它通常会生成输出,您可以将其粘贴回ghci
,可以说应该仅限于此用途。您可以轻松定义自己的函数,并按如下方式使用它:
formatRule :: Rule -> String
formatRule (Rule ls rs) = ls ++ "->" ++ concat (intersperse "," rs) ++ "\n"
formatRightLinearGrammar :: RightLinearGrammar -> String
formatRightLinearGrammar (RLG n t fn r) =
concat (intersperse "," n) ++ "\n"
++ intersperse ',' t ++ "\n"
++ fn ++ "\n"
++ concat (map formatRule r)
注意:对于大型语法来说,这将是相当低效的;你可能想考虑把它改写为
formatRule :: Rule -> String -> String
formatRule (Rule ls rs) = (ls++) . ("->"++) . concatDS (intersperse "," rs) . ("\n"++)
formatRightLinearGrammar :: RightLinearGrammar -> String
formatRightLinearGrammar (RLG n t fn r) =
concatDS (intersperse "," n) $ ("\n"++) $
(intersperse ',' t ++) $ ("\n"++) $
(fn++) $ ("\n"++) $
foldr formatRule "" r
concatDS ss s' = foldr (++) s' ss
这很有效。我不知道像intersperse和concat这样的函数存在。我只是更新了它,使用了
interlate
,这是concat$intersperse xss
formatRule :: Rule -> String -> String
formatRule (Rule ls rs) = (ls++) . ("->"++) . concatDS (intersperse "," rs) . ("\n"++)
formatRightLinearGrammar :: RightLinearGrammar -> String
formatRightLinearGrammar (RLG n t fn r) =
concatDS (intersperse "," n) $ ("\n"++) $
(intersperse ',' t ++) $ ("\n"++) $
(fn++) $ ("\n"++) $
foldr formatRule "" r
concatDS ss s' = foldr (++) s' ss