F#:在非空列表中查找更大值的递归函数

F#: recursive function to find bigger value in non empty list

我需要 F# 中的递归函数,它可以为我提供非空列表的最大值。 示例:

biggest [2;4;5;3;9;3] 

应该return9

更新 1

我正在学习递归函数,这是书中的练习,没有答案。我认为在这里问是可以的,但似乎这不是一个好主意。好吧,我没有写任何代码示例,所以它看起来像是一个懒人的家庭作业。无论如何,这是我最好的尝试:

let rec highest l = 
    match l with 
    |[] -> 0 
    |x::y::xs -> if x > y then highest x::xs
                 else highest y::xs 

但这行不通。我不能使用 F# 函数,这当然是为了学习目的。很抱歉让您浪费了一些时间,感谢您的帮助。

回答之前:这个问题很奇怪,Whosebug 可能不是最好的地方。

  • 如果用于生产代码,请使用 List.max。 (抛开双关语,递归不是它自己的回报......)
  • 如果是家庭作业,请尝试理解递归,而不是将您的练习委托给互联网上的随机人员。
  • 如果是 puzzle/code 高尔夫,这是错误的站点,要求是什么可能会更清楚。

无论如何,这个可以按帖子回答,满足以下要求:

  • 解决方案是尾递归的,而不仅仅是递归的。显然我不想写一个函数来替换 List.max 只是为了不必要地增加堆栈。
  • 问题代码中调用的函数 biggest 直接 是递归函数,没有其他参数。如果我从字面上看这个问题,这似乎是一个要求,所以我不允许使用累加器。

List.max is implemented with a mutating loop and therefore doesn't qualify (link goes to F# source code)。所以这需要一个自定义实现:

let rec biggest = function
    | h1 :: h2 :: t -> biggest ((max h1 h2) :: t)
    | [result] -> result
    | [] -> failwith "list empty"

这是一个非常奇怪的解决方案,但它可以满足要求并且适用于长列表。

经过几天的思考并在学校的一些帮助下,我想到了这个,它是 Vandroiy 的解决方案的替代解决方案:

let rec max_value l =
    match l with
    |[] -> []
    |[x] -> [x]
    |(x::y::xs) ->  if x<y then max_value (y::xs)
                    else max_value (x::xs)

非常感谢