【问题标题】:F# custom append functionF# 自定义追加函数
【发布时间】:2017-09-21 04:53:59
【问题描述】:

我有一个将 list2 附加到 list1 的自定义函数。

let append ls1 ls2 =
    let rec loop ls ls1 ls2 =
        match ls1, ls2 with
        | _, hd::tl -> 
            loop (hd::ls) ls1 tl
        | hd::tl, _ -> loop (hd::ls) tl ls2
        | _ -> ls
    loop [] ls1 ls2

它工作正常。但问题是当我调用函数时

let appended = append [1;2;3;4;5] [6;7;8;9;10]

它不是返回[1;2;3;4;5;6;7;8;9;10]而是返回

[5;4;3;2;1;10;9;8;7;6]

它反转两个列表。

【问题讨论】:

  • 你的问题是什么?如果是关于错误的结果,请再想一想,记住hd :: tl 就像将hd 附加到tl 的头部,而不是附加到它的末尾
  • 想要的结果是 [1;2;3;4;5;6;7;8;9;10]
  • 这个问题与昨天的问题有何不同?请在那里查看答案。

标签: list function recursion design-patterns f#


【解决方案1】:

以下代码适合我

let rec append list1 list2 = 
   match list1, list2 with
    | hd::tl, _ -> hd::(append  tl list2)
    | _, hd::tl -> hd::(append list1 tl)
    | _ -> []

以下代码的输出是:

   let List1 = [1; 3; 5];
    let List2 = [7]
    printf "%A" append List1 List2

[1; 3; 5; 7] 

【讨论】:

    【解决方案2】:

    您需要反转列表。 解决问题的一种方法是考虑rev 函数的外观。 这是第一次尝试:

    let rec rev lst =
        match lst with 
        | h::t -> (rev t)@[h]
        | [] -> []
    

    这个函数反转一个列表,但是现在让我们做另一个使用累加器的版本,这意味着我们将在最后一行使用一个加法参数来代替空列表:

    let rec rev lst acc =
        match lst with 
        | h::t -> rev t (h::acc)
        | [] -> acc
    

    所以现在我们必须将空列表作为参数传递:

    rev [1..4] [];;
    

    验证它:int list = [4; 3; 2; 1]

    您可能想知道为什么我们需要这样一个函数,这个函数是 tail recursive 但这不是您的问题,您正在寻找附加两个列表。事实证明,这就是您正在寻找的功能的 90%。

    如果不是传递一个空列表,而是传递第二个列表:

    rev [1..4] [5..8];;
    

    验证它:int list = [4; 3; 2; 1个; 5个; 6; 7; 8]

    非常接近,但是是的,第一个列表是反转的,好的,但是我们有这个可以反转列表的功能,所以让我们反转第一个列表:

    rev (rev [1..4] []) [5..8] ;;
    

    验证它:int list = [1; 2; 3; 4; 5个; 6; 7; 8]

    太好了,现在这个rev 可以成为我们的loop 函数:

    let append lst1 lst2 = 
        let rec rev lst acc =
            match lst with 
            | h::t -> rev t (h::acc)
            | [] -> acc
        rev (rev lst1 []) lst2
    

    按预期工作,但请注意,我们只是调用了两次参数化的rev 函数。希望您了解函数式编程如何允许您组合函数以解决不同的问题。在这种情况下,我们将一个函数与其自身相结合。

    【讨论】:

      猜你喜欢
      • 2019-12-16
      • 2016-11-03
      • 1970-01-01
      • 2014-09-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多