haskell - Haskell - 无法匹配预期类型
问题描述
所以我试图在 Haskell 中创建一个简单的文本编辑器。我已经定义了一个自定义数据类型“TextEditor”,它由两个字符集组成,一个充当光标之前的所有字符,然后下一个是光标之后的所有字符。我已经用一些文本初始化了它。
import Data.List
import System.IO
data TextEditor = TextEditor([Char],[Char]) deriving (Show)
inputLine :: TextEditor
inputLine = TextEditor("The quick br", "own fox")
moveCursorLeft :: TextEditor -> TextEditor
moveCursorLeft (TextEditor (b, a)) = (TextEditor (b++ [head (a)]) , tail(a))
尝试加载时出现此错误。
Test.hs:10:38: error:
Couldn't match expected type `TextEditor' with actual type `(TextEditor, [Char])'
* In the expression: (TextEditor (b ++ [head (a)]), tail (a))
In an equation for `moveCursorLeft':
moveCursorLeft (TextEditor (b, a))
= (TextEditor (b ++ [head (a)]), tail (a))
Test.hs:10:51: error:
* Couldn't match expected type `([Char], [Char])' with actual type `[Char]'
* In the first argument of `TextEditor', namely `(b ++ [head (a)])'
In the expression: TextEditor (b ++ [head (a)])
In the expression: (TextEditor (b ++ [head (a)]), tail (a))
我对 Haskell 非常陌生,因此将不胜感激任何帮助。
解决方案
您在第二个子句中写道:
(TextEditor (b++ [head (a)]) , tail(a))
但这意味着您不构造TextEditor
对象,而是构造(TextEditor, String)
2 元组(尽管第一个元素仍然格式错误)。确实:
(TextEditor (b++ [head (a)]) , tail(a))
您可能正在寻找:
TextEditor (b++ [head (a)] , tail(a))
尽管如此,这仍然不是一个好主意:可能a
是一个空列表,因此没有head
or tail
。
通常最好在这里执行模式匹配:
moveCursorRight :: TextEditor -> TextEditor
moveCursorRight (t@TextEditor ([], b)) = t -- I think?
moveCursorRight (TextEditor ((a:as), b)) = TextEditor (b ++ [a] , as)
但是现在它仍然非常低效,因为追加需要O(n)时间。一种常见的技术是使用两个列表,其中第一个是颠倒的,因此TextEditor ([1, 4, 2], [5, 1, 3, 0, 2])
意味着241|51302
(使用|
光标)。
然后我们可以这样写:
-- In case we reverse the first item of the 2-tuple
moveCursorRight :: TextEditor -> TextEditor
moveCursorRight (t@TextEditor (b, [])) = t
moveCursorRight (TextEditor (b, (a:as))) = TextEditor ((a:b) , as)
请注意,这实际上是在所有功能中将光标向右移动,因为我们从元组的右侧元素弹出,然后向左推。