haskell - 无法将类型“(Char, Int)”与“[Char]”匹配错误
haskell - Couldn't match type ‘(Char, Int)’ with ‘[Char]’ error
我正在编写一个函数来扩展字符串
示例:
foo "a4b4"
应该回馈:
"aaaabbbb"
这是我的代码:
foo :: String -> String
foo (x:xs) = let curent = fooHelp(x, read $ charToString( xs !! 0 ) :: Int)
in x : (curent) ++ foo (tail xs)
fooHelp:
fooHelp :: String -> Int -> String
fooHelp x n
| n >= 3 = x ++ fooHelp x (n - 1)
| n == 2 = x
| n == 1 = ""
和 charToString:
charToString :: Char -> String
charToString c = [c]
它需要 x 并将其附加到当前。在当前的 fooHelp 中将返回扩展的 String
示例:foo "a4b4"
然后 x = "a"
、xs = "4b4"
、xs !! 0 = '4'
read $ charToString( xs !! 0 ) :: Int)
会将 char '4'
转换为 int 4
并将其与 x("a") -> fooHelp(x, 4)
一起传递给 fooHelp 并返回 "aaa" .然后 x : current
应该返回 "aaaa"
因为 x = "a"
和当前 "aaa"
然后用 ++ foo tail xs
递归调用 xs ="b4"
并且它应该重复这个过程。
我收到错误:
test.hs:173:34: error:
• Couldn't match type ‘(Char, Int)’ with ‘[Char]’
Expected type: String
Actual type: (Char, Int)
• In the first argument of ‘fooHelp’, namely
‘(x, read $ charToString (xs !! 0) :: Int)’
In the expression:
fooHelp (x, read $ charToString (xs !! 0) :: Int)
In an equation for ‘curent’:
curent = fooHelp (x, read $ charToString (xs !! 0) :: Int)
|
173 | foo (x:xs) = let curent = fooHelp(x, read $ charToString( xs !! 0 ) :: Int)
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
我哪里弄错了?我测试了函数 fooHelp,它可以很好地处理 foo 中的参数。
正在测试 fooHelp:
xs = "4b4"
test = read $ charToString( xs !!0 ) :: Int
*Main> test
4
表达式 fooHelp(x, read $ charToString( xs !! 0 ) :: Int)
试图将单个参数 — (Char, Int)
对 — 传递给 fooHelp
,这是错误的。据推测,您想改写:
fooHelp (charToString x) (read $ charToString( xs !! 0 ) :: Int)
一个典型的错误是调用像 f (x1, x2)
这样的函数。在 Haskell 函数中有 一个 参数,通常这是 而不是 一个元组。
您的 fooHelper
函数的类型为:
fooHelp :: String -> (Int -> String)
所以它是一个接受 String
的函数,而 returns 是一个将 Int
s 映射到 String
s 的函数。因此,您应该像这样调用该函数:
(fooHelp x) (read $ charToString( xs !! 0 ) :: Int)
或更简洁:
(fooHelp x) (read $ charToString( xs !! 0 ) :: Int)
但现在类型仍然不匹配:x
是 Char
,不是 String
,您可以将其包装在列表中,如:
fooHelp [x] (read $ charToString( xs !! 0 ) :: Int)
喜欢:
foo :: String -> String
foo (x:xs) = let curent = fooHelp [x] (read $ charToString( xs !! 0 ) :: Int)
in x : (curent) ++ foo (tail xs)
但是这个函数仍然有一个问题:我们遍历字符串,所以最终我们会得到一个空字符串,而 foo
没有这种情况。在这种情况下,我们需要 return 空字符串,例如:
foo :: String -> String
foo (x:xs) = let curent = fooHelp [x] (read $ charToString( xs !! 0 ) :: Int)
in x : (curent) ++ foo (tail xs)
foo [] = ""
但还是不够优雅。我们在这里执行了很多不必要的操作,比如将字符包装成字符串等
我们可以使用replicate :: Int -> a -> [a]
函数来重复一个字符给定的次数。例如:
Prelude> replicate 3 'a'
"aaa"
另外digitToInt :: Char -> Int
函数可以将一个数字字符解析为对应的Int
:
Prelude Data.Char> digitToInt '3'
3
所以我们在这里可以使用这两个来每次获取字符串的前两个字符,并使用 replicate (digitToInt k) x
生成一个字符串,其中 x
si 重复请求的时间量,并且对字符串的其余部分执行递归,例如:
import Data.Char(digitToInt)
foo :: String -> String
foo (x:k:xs) = replicate (digitToInt k) x ++ foo xs
foo _ = ""
我正在编写一个函数来扩展字符串
示例:
foo "a4b4"
应该回馈:
"aaaabbbb"
这是我的代码:
foo :: String -> String
foo (x:xs) = let curent = fooHelp(x, read $ charToString( xs !! 0 ) :: Int)
in x : (curent) ++ foo (tail xs)
fooHelp:
fooHelp :: String -> Int -> String
fooHelp x n
| n >= 3 = x ++ fooHelp x (n - 1)
| n == 2 = x
| n == 1 = ""
和 charToString:
charToString :: Char -> String
charToString c = [c]
它需要 x 并将其附加到当前。在当前的 fooHelp 中将返回扩展的 String
示例:foo "a4b4"
然后 x = "a"
、xs = "4b4"
、xs !! 0 = '4'
read $ charToString( xs !! 0 ) :: Int)
会将 char '4'
转换为 int 4
并将其与 x("a") -> fooHelp(x, 4)
一起传递给 fooHelp 并返回 "aaa" .然后 x : current
应该返回 "aaaa"
因为 x = "a"
和当前 "aaa"
然后用 ++ foo tail xs
递归调用 xs ="b4"
并且它应该重复这个过程。
我收到错误:
test.hs:173:34: error:
• Couldn't match type ‘(Char, Int)’ with ‘[Char]’
Expected type: String
Actual type: (Char, Int)
• In the first argument of ‘fooHelp’, namely
‘(x, read $ charToString (xs !! 0) :: Int)’
In the expression:
fooHelp (x, read $ charToString (xs !! 0) :: Int)
In an equation for ‘curent’:
curent = fooHelp (x, read $ charToString (xs !! 0) :: Int)
|
173 | foo (x:xs) = let curent = fooHelp(x, read $ charToString( xs !! 0 ) :: Int)
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
我哪里弄错了?我测试了函数 fooHelp,它可以很好地处理 foo 中的参数。
正在测试 fooHelp:
xs = "4b4"
test = read $ charToString( xs !!0 ) :: Int
*Main> test
4
表达式 fooHelp(x, read $ charToString( xs !! 0 ) :: Int)
试图将单个参数 — (Char, Int)
对 — 传递给 fooHelp
,这是错误的。据推测,您想改写:
fooHelp (charToString x) (read $ charToString( xs !! 0 ) :: Int)
一个典型的错误是调用像 f (x1, x2)
这样的函数。在 Haskell 函数中有 一个 参数,通常这是 而不是 一个元组。
您的 fooHelper
函数的类型为:
fooHelp :: String -> (Int -> String)
所以它是一个接受 String
的函数,而 returns 是一个将 Int
s 映射到 String
s 的函数。因此,您应该像这样调用该函数:
(fooHelp x) (read $ charToString( xs !! 0 ) :: Int)
或更简洁:
(fooHelp x) (read $ charToString( xs !! 0 ) :: Int)
但现在类型仍然不匹配:x
是 Char
,不是 String
,您可以将其包装在列表中,如:
fooHelp [x] (read $ charToString( xs !! 0 ) :: Int)
喜欢:
foo :: String -> String
foo (x:xs) = let curent = fooHelp [x] (read $ charToString( xs !! 0 ) :: Int)
in x : (curent) ++ foo (tail xs)
但是这个函数仍然有一个问题:我们遍历字符串,所以最终我们会得到一个空字符串,而 foo
没有这种情况。在这种情况下,我们需要 return 空字符串,例如:
foo :: String -> String
foo (x:xs) = let curent = fooHelp [x] (read $ charToString( xs !! 0 ) :: Int)
in x : (curent) ++ foo (tail xs)
foo [] = ""
但还是不够优雅。我们在这里执行了很多不必要的操作,比如将字符包装成字符串等
我们可以使用replicate :: Int -> a -> [a]
函数来重复一个字符给定的次数。例如:
Prelude> replicate 3 'a'
"aaa"
另外digitToInt :: Char -> Int
函数可以将一个数字字符解析为对应的Int
:
Prelude Data.Char> digitToInt '3'
3
所以我们在这里可以使用这两个来每次获取字符串的前两个字符,并使用 replicate (digitToInt k) x
生成一个字符串,其中 x
si 重复请求的时间量,并且对字符串的其余部分执行递归,例如:
import Data.Char(digitToInt)
foo :: String -> String
foo (x:k:xs) = replicate (digitToInt k) x ++ foo xs
foo _ = ""