如何仅将任一侧作为参数传递 Haskell
How to pass only one side of either as a parameter Haskell
我的功能之一 returns:
parse :: Int -> String -> Either String JsonLikeValue
而其他的以JsonLikeValue
为参数:
convert :: Int -> JsonLikeValue -> Either InvalidState To
JsonLikeValue
是自定义数据类型:
data JsonLikeValue = JLString String | JLInt Int | JLArray [JsonLikeValue] deriving (Show, Eq)
当我打电话时:
convert num (parse size message)
它给出以下内容:
Couldn't match expected type ‘JsonLikeValue’
with actual type ‘Either String JsonLikeValue’
如何避免这种情况并且只将右侧作为参数传递?
提前致谢:)
编辑: 标记为答案的解决方案非常有帮助,因为它考虑了所有可能的结果,而且由于我不是专家,但看起来更专业,所以它看一看很重要
但足以解决所需提取的是:
extractValue :: Either String JsonLikeValue -> JsonLikeValue
extractValue a = case a of
Left e -> JLArray []
Right r -> r
在 Right
的情况下,它 return 是唯一的值,在 Left
的情况下,它 return 是必需的数据类型。请注意,这仅在您 100% 确定参数将 return Right
值时才有效。否则,请检查下面的答案。
评论中的另一个注意事项是使用 Data.Either
中的 fromRight
第一个问题是我们需要 return 一些东西,以防 parse
值 return 成为 Left …
值。例如,我们可以创建一个将两个“错误”组合在一起的函数:
myfunction :: Int -> Int -> String -> Either <b>(Either String InvalidState)</b> To
myfunction = …
我们可以利用模式匹配来解压 Right
的值,然后使用 convert
函数,如:
myfunction :: Int -> Int -> String -> Either <b>(Either String InvalidState)</b> To
myfunction size num message = go (parse size message)
where go (Left e) = Left (Left e)
go (Right jlv) = pp (convert num jlv)
pp (Left e) = Left (Right e)
pp (Right r) = Right r
这里go
检查parse size message
值的结果,如果是Left e
,我们returnLeft (Left e)
。如果它是一个 Right jlv
(其中包含 jlv
和 JsonLikeValue
),我们因此调用 convert num jlv
.
我们仍然需要 post-process 使用 pp
函数的结果。 convert num jlv
的类型为 Either InvalidState To
,我们需要将其转换为 Either (Either String InvalidState) To
。为此,我们将 Left e
转换为 Left (Right e)
,将 Right r
转换为 Right r
。注意body中的Right
是Either (Either String InvalidState) To
类型的数据构造函数,而head中的Right
是Either InvalidState To
类型的数据构造函数,所以两者是不一样。
我的功能之一 returns:
parse :: Int -> String -> Either String JsonLikeValue
而其他的以JsonLikeValue
为参数:
convert :: Int -> JsonLikeValue -> Either InvalidState To
JsonLikeValue
是自定义数据类型:
data JsonLikeValue = JLString String | JLInt Int | JLArray [JsonLikeValue] deriving (Show, Eq)
当我打电话时:
convert num (parse size message)
它给出以下内容:
Couldn't match expected type ‘JsonLikeValue’
with actual type ‘Either String JsonLikeValue’
如何避免这种情况并且只将右侧作为参数传递? 提前致谢:)
编辑: 标记为答案的解决方案非常有帮助,因为它考虑了所有可能的结果,而且由于我不是专家,但看起来更专业,所以它看一看很重要
但足以解决所需提取的是:
extractValue :: Either String JsonLikeValue -> JsonLikeValue
extractValue a = case a of
Left e -> JLArray []
Right r -> r
在 Right
的情况下,它 return 是唯一的值,在 Left
的情况下,它 return 是必需的数据类型。请注意,这仅在您 100% 确定参数将 return Right
值时才有效。否则,请检查下面的答案。
评论中的另一个注意事项是使用 Data.Either
fromRight
第一个问题是我们需要 return 一些东西,以防 parse
值 return 成为 Left …
值。例如,我们可以创建一个将两个“错误”组合在一起的函数:
myfunction :: Int -> Int -> String -> Either <b>(Either String InvalidState)</b> To
myfunction = …
我们可以利用模式匹配来解压 Right
的值,然后使用 convert
函数,如:
myfunction :: Int -> Int -> String -> Either <b>(Either String InvalidState)</b> To
myfunction size num message = go (parse size message)
where go (Left e) = Left (Left e)
go (Right jlv) = pp (convert num jlv)
pp (Left e) = Left (Right e)
pp (Right r) = Right r
这里go
检查parse size message
值的结果,如果是Left e
,我们returnLeft (Left e)
。如果它是一个 Right jlv
(其中包含 jlv
和 JsonLikeValue
),我们因此调用 convert num jlv
.
我们仍然需要 post-process 使用 pp
函数的结果。 convert num jlv
的类型为 Either InvalidState To
,我们需要将其转换为 Either (Either String InvalidState) To
。为此,我们将 Left e
转换为 Left (Right e)
,将 Right r
转换为 Right r
。注意body中的Right
是Either (Either String InvalidState) To
类型的数据构造函数,而head中的Right
是Either InvalidState To
类型的数据构造函数,所以两者是不一样。