F# 以更实用的方式重写函数

F# 以更实用的方式重写函数,f#,F#,我编写了这个函数,用于计算数字的回文: let palindrome n = let mutable current = n let mutable result = 0 while(current > 0) do result <- result * 10 + current % 10 current <- current / 10 result 让回文n= 设可变电流=n 设可变结果=0 而(当前>0)则

我编写了这个函数,用于计算数字的回文:

let palindrome n = 
    let mutable current = n
    let mutable result = 0
    while(current > 0) do
        result <- result * 10 + current % 10
        current <- current / 10

    result
让回文n=
设可变电流=n
设可变结果=0
而(当前>0)则执行

结果您可以使用尾部递归函数来完成。匹配
结果的值
:如果他的值=0,则返回结果,否则在
当前
结果
上进行计算

let palindrome n =
  let rec rec_palindrome current result = match current with
    | 0 -> result
    | _ -> rec_palindrome (result * 10 + current % 10) (current / 10) 
  rec_palindrome n 0

另外,在我的版本中,这不是可变值

您可以使用尾部递归函数来实现。匹配
结果的值
:如果他的值=0,则返回结果,否则在
当前
结果
上进行计算

let palindrome n =
  let rec rec_palindrome current result = match current with
    | 0 -> result
    | _ -> rec_palindrome (result * 10 + current % 10) (current / 10) 
  rec_palindrome n 0

另外,在我的版本中,这不是可变值

你想做什么还不太清楚。给定的
回文
函数只是反转整数的位数:

> palindrome 1;;
val it : int = 1
> palindrome 12;;
val it : int = 21
> palindrome 123;;
val it : int = 321
> palindrome 9852;;
val it : int = 2589
这些都不是,但是让我们把问题分成更小的构建块

您可以轻松地将整数拆分为数字列表。事实上,拆分成相反的数字列表是我能想到的最简单的方法:

let rec revdigits i =
    let tens = i / 10
    if tens = 0
    then [i]
    else
        let ones = i % 10
        ones :: revdigits tens
这是类型为
int->int list
的函数

示例:

> revdigits 1;;
val it : int list = [1]
> revdigits 12;;
val it : int list = [2; 1]
> revdigits 123;;
val it : int list = [3; 2; 1]
> revdigits 9852;;
val it : int list = [2; 5; 8; 9]
> concat [1];;
val it : int = 1
> concat [1; 2];;
val it : int = 12
> concat [1; 2; 3];;
val it : int = 123
> concat [2; 5; 8; 9];;
val it : int = 2589
> reverse 1;;
val it : int = 1
> reverse 12;;
val it : int = 21
> reverse 123;;
val it : int = 321
> reverse 2589;;
val it : int = 9852
> digits 1;;
val it : int list = [1]
> digits 12;;
val it : int list = [1; 2]
> digits 123;;
val it : int list = [1; 2; 3]
> digits 9852;;
val it : int list = [9; 8; 5; 2]
将数字列表连接成数字也很容易:

let rec concat digits =
    match digits with
    | [] -> 0
    | h :: t -> h * int (10. ** float t.Length) + concat t
此函数的类型为
int list->int

示例:

> revdigits 1;;
val it : int list = [1]
> revdigits 12;;
val it : int list = [2; 1]
> revdigits 123;;
val it : int list = [3; 2; 1]
> revdigits 9852;;
val it : int list = [2; 5; 8; 9]
> concat [1];;
val it : int = 1
> concat [1; 2];;
val it : int = 12
> concat [1; 2; 3];;
val it : int = 123
> concat [2; 5; 8; 9];;
val it : int = 2589
> reverse 1;;
val it : int = 1
> reverse 12;;
val it : int = 21
> reverse 123;;
val it : int = 321
> reverse 2589;;
val it : int = 9852
> digits 1;;
val it : int list = [1]
> digits 12;;
val it : int list = [1; 2]
> digits 123;;
val it : int list = [1; 2; 3]
> digits 9852;;
val it : int list = [9; 8; 5; 2]
使用这些构建块,您可以轻松地编写一个与
回文
函数相同的函数:

let reverse = revdigits >> concat
此函数的类型为
int->int

示例:

> revdigits 1;;
val it : int list = [1]
> revdigits 12;;
val it : int list = [2; 1]
> revdigits 123;;
val it : int list = [3; 2; 1]
> revdigits 9852;;
val it : int list = [2; 5; 8; 9]
> concat [1];;
val it : int = 1
> concat [1; 2];;
val it : int = 12
> concat [1; 2; 3];;
val it : int = 123
> concat [2; 5; 8; 9];;
val it : int = 2589
> reverse 1;;
val it : int = 1
> reverse 12;;
val it : int = 21
> reverse 123;;
val it : int = 321
> reverse 2589;;
val it : int = 9852
> digits 1;;
val it : int list = [1]
> digits 12;;
val it : int list = [1; 2]
> digits 123;;
val it : int list = [1; 2; 3]
> digits 9852;;
val it : int list = [9; 8; 5; 2]

好处:如果你不想反转数字,你可以这样做,但我不认为这个版本是尾部递归的:

let rec digits i =
    let tens = i / 10
    if tens = 0
    then [i]
    else
        let ones = i % 10
        digits tens @ [ones]
此函数的类型为
int->int list

示例:

> revdigits 1;;
val it : int list = [1]
> revdigits 12;;
val it : int list = [2; 1]
> revdigits 123;;
val it : int list = [3; 2; 1]
> revdigits 9852;;
val it : int list = [2; 5; 8; 9]
> concat [1];;
val it : int = 1
> concat [1; 2];;
val it : int = 12
> concat [1; 2; 3];;
val it : int = 123
> concat [2; 5; 8; 9];;
val it : int = 2589
> reverse 1;;
val it : int = 1
> reverse 12;;
val it : int = 21
> reverse 123;;
val it : int = 321
> reverse 2589;;
val it : int = 9852
> digits 1;;
val it : int list = [1]
> digits 12;;
val it : int list = [1; 2]
> digits 123;;
val it : int list = [1; 2; 3]
> digits 9852;;
val it : int list = [9; 8; 5; 2]

你想做什么还不太清楚。给定的
回文
函数只是反转整数的位数:

> palindrome 1;;
val it : int = 1
> palindrome 12;;
val it : int = 21
> palindrome 123;;
val it : int = 321
> palindrome 9852;;
val it : int = 2589
这些都不是,但是让我们把问题分成更小的构建块

您可以轻松地将整数拆分为数字列表。事实上,拆分成相反的数字列表是我能想到的最简单的方法:

let rec revdigits i =
    let tens = i / 10
    if tens = 0
    then [i]
    else
        let ones = i % 10
        ones :: revdigits tens
这是类型为
int->int list
的函数

示例:

> revdigits 1;;
val it : int list = [1]
> revdigits 12;;
val it : int list = [2; 1]
> revdigits 123;;
val it : int list = [3; 2; 1]
> revdigits 9852;;
val it : int list = [2; 5; 8; 9]
> concat [1];;
val it : int = 1
> concat [1; 2];;
val it : int = 12
> concat [1; 2; 3];;
val it : int = 123
> concat [2; 5; 8; 9];;
val it : int = 2589
> reverse 1;;
val it : int = 1
> reverse 12;;
val it : int = 21
> reverse 123;;
val it : int = 321
> reverse 2589;;
val it : int = 9852
> digits 1;;
val it : int list = [1]
> digits 12;;
val it : int list = [1; 2]
> digits 123;;
val it : int list = [1; 2; 3]
> digits 9852;;
val it : int list = [9; 8; 5; 2]
将数字列表连接成数字也很容易:

let rec concat digits =
    match digits with
    | [] -> 0
    | h :: t -> h * int (10. ** float t.Length) + concat t
此函数的类型为
int list->int

示例:

> revdigits 1;;
val it : int list = [1]
> revdigits 12;;
val it : int list = [2; 1]
> revdigits 123;;
val it : int list = [3; 2; 1]
> revdigits 9852;;
val it : int list = [2; 5; 8; 9]
> concat [1];;
val it : int = 1
> concat [1; 2];;
val it : int = 12
> concat [1; 2; 3];;
val it : int = 123
> concat [2; 5; 8; 9];;
val it : int = 2589
> reverse 1;;
val it : int = 1
> reverse 12;;
val it : int = 21
> reverse 123;;
val it : int = 321
> reverse 2589;;
val it : int = 9852
> digits 1;;
val it : int list = [1]
> digits 12;;
val it : int list = [1; 2]
> digits 123;;
val it : int list = [1; 2; 3]
> digits 9852;;
val it : int list = [9; 8; 5; 2]
使用这些构建块,您可以轻松地编写一个与
回文
函数相同的函数:

let reverse = revdigits >> concat
此函数的类型为
int->int

示例:

> revdigits 1;;
val it : int list = [1]
> revdigits 12;;
val it : int list = [2; 1]
> revdigits 123;;
val it : int list = [3; 2; 1]
> revdigits 9852;;
val it : int list = [2; 5; 8; 9]
> concat [1];;
val it : int = 1
> concat [1; 2];;
val it : int = 12
> concat [1; 2; 3];;
val it : int = 123
> concat [2; 5; 8; 9];;
val it : int = 2589
> reverse 1;;
val it : int = 1
> reverse 12;;
val it : int = 21
> reverse 123;;
val it : int = 321
> reverse 2589;;
val it : int = 9852
> digits 1;;
val it : int list = [1]
> digits 12;;
val it : int list = [1; 2]
> digits 123;;
val it : int list = [1; 2; 3]
> digits 9852;;
val it : int list = [9; 8; 5; 2]

好处:如果你不想反转数字,你可以这样做,但我不认为这个版本是尾部递归的:

let rec digits i =
    let tens = i / 10
    if tens = 0
    then [i]
    else
        let ones = i % 10
        digits tens @ [ones]
此函数的类型为
int->int list

示例:

> revdigits 1;;
val it : int list = [1]
> revdigits 12;;
val it : int list = [2; 1]
> revdigits 123;;
val it : int list = [3; 2; 1]
> revdigits 9852;;
val it : int list = [2; 5; 8; 9]
> concat [1];;
val it : int = 1
> concat [1; 2];;
val it : int = 12
> concat [1; 2; 3];;
val it : int = 123
> concat [2; 5; 8; 9];;
val it : int = 2589
> reverse 1;;
val it : int = 1
> reverse 12;;
val it : int = 21
> reverse 123;;
val it : int = 321
> reverse 2589;;
val it : int = 9852
> digits 1;;
val it : int list = [1]
> digits 12;;
val it : int list = [1; 2]
> digits 123;;
val it : int list = [1; 2; 3]
> digits 9852;;
val it : int list = [9; 8; 5; 2]

当你测试你的函数时,你能给出一些结果吗?据我所知,这个函数只是“反转”输入:例如8921变成1298。这几乎不是回文。你到底想让函数做什么?如果你有可以工作的东西,codereview.se更合适。@Mark Seemann:你说得对,我的函数名不合适。我可能应该称之为“ReverseEnumber”。当你测试你的函数时,你能给出一些结果吗?据我所知,这个函数只是“反转”输入:例如8921变成1298。这几乎不是回文。你到底想让函数做什么?如果你有可以工作的东西,codereview.se更合适。@Mark Seemann:你说得对,我的函数名不合适。我应该称之为“反向枚举器”。谢谢,比我的解决方案好多了!谢谢,比我的解决方案好多了!