似乎我一遍又一遍地使用一种模式,我想抽象出一个函数。模式背后的想法是,我可能有一些东西,如果没有,我可以尝试生产它。 这是我对命名感兴趣的函数的一些OCaml代码,但问题不是OCaml特定的。我找了一个Haskell先例,但是我没有在Data.Maybe模块中看到这样的函数,并且hoogle没有帮助:http://www.haskell.org/hoogle/?hoogle=Maybe+b+-%3E+%28a+-%3E+Maybe+b%29+-%3E+a+-%3E+Maybe+b。
let my_function a f arg = match a with
| None -> f arg
| Some _ -> a
这几乎就像有一个默认的潜在价值,但如果我们已经有一个值,它就不需要生成默认值。
修改
我需要这种类型的原因是我有一个要解决的组合问题和一组解决它的启发式(比如h1和h2)。 h1比h2快。但是,这些启发式方法都不能保证找到解决方案。所以我将它们链接起来并按顺序尝试。像
这样的东西match my_function (h1 problem) h2 problem with
| None -> "bad luck"
| Some solution -> "hurray"
答案 0 :(得分:10)
听起来像Alternative
模式:
a <|> f arg
答案 1 :(得分:3)
怎么样:
fromMaybe (f arg) a
请参阅:http://www.haskell.org/hoogle/?hoogle=fromMaybe
此外,在Haskell中,f arg
只有在a
为Nothing
时才有可能被计算,因为Haskell是懒惰的,与OCaml不同。
答案 2 :(得分:3)
在Haskell表示法中,您的函数基本上是
func :: Maybe a -> (b -> Maybe a) -> b -> Maybe a
func a f arg = case a of
Nothing -> f arg
Just _ -> a
请注意,您只使用组合f
中的输入arg
和f arg
,因此您可以简化为
helper :: Maybe a -> Maybe a -> Maybe a
helper a b = case a of
Nothing -> b
_ -> a
func a f arg = helper a (f arg)
也就是说,如果助手有值,则助手会生成a
,否则会产生b
。但您可以根据maybe
Data.Maybe
来撰写
helper :: Maybe a -> Maybe a -> Maybe a
helper a b = maybe b id a
func a f arg = helper a (f arg)
然后如果你想要你可以内联帮助器的定义
func a f arg = maybe (f arg) id a
所以我认为你没有一个已经存在的模式,但它是maybe
函数的一个简单变体,它已经存在。
答案 3 :(得分:1)
查看编辑中描述的一般问题,也许您会对(使用OCaml核心库)感兴趣:
let heuristics = [lazy(h0 "problem"); lazy(h1 "problem"); lazy(h2 "problem")];;
let result = List.find heuristics (fun z -> Option.is_some (Lazy.force z));;
只需先创建一个启发式列表,然后找到第一个生成有效解决方案的列表。