首页 > 解决方案 > OCaml 中的 Fizbuzz 得到错误“与类型单元不兼容”

问题描述

我有以下用 OCaml 编写的 fizbuzz 程序(使用一点递归):

let rec fizbuzz_r = 
  let rec fizbuzz_rr i = 
    if i == 0 then 
      ()
    else if i mod 3 == 0 && i mod 5 != 0 then
      Printf.printf "Fizz: %d \n" i  
      fizbuzz_rr (i - 1)
    else if i mod 3 != 0 && i mod 5 == 0 then
      Printf.printf "Buzz: %d \n" i 
      fizbuzz_rr (i - 1) 
    else if i mod 5 == 0 && i mod 3 == 0 then
      Printf.printf "Fizbuzz: %d \n" i 
      fizbuzz_rr (i - 1) 
    else 
      Printf.printf "Current Number: %d \n" i 
      fizbuzz_rr (i - 1) 
    ()
  in  
    fizbuzz_rr 100

let () = fizbuzz_r 

问题是当我编译它时,我收到以下错误消息:

Error: This expression has type
         ('a -> 'b -> 'c -> 'd, out_channel, unit, unit, unit,
          'a -> 'b -> 'c -> 'd)
         CamlinternalFormatBasics.fmt
       but an expression was expected of type
         ('a -> 'b -> 'c -> 'd, out_channel, unit, unit, unit, unit)
         CamlinternalFormatBasics.fmt
       Type 'a -> 'b -> 'c -> 'd is not compatible with type unit 

但是,在我看来,嵌套函数fizbuzz_rr正确地返回了一个unit类型。我在这里想念什么?

标签: ocaml

解决方案


这个表达式:

  Printf.printf "Fizz: %d \n" i  
  fizbuzz_rr (i - 1)

Printf.printf具有带有 4 个参数的调用形式。您需要一个分号来分隔您想要的两个表达式。

但是,之后then你只能有一种表达方式。所以你需要给这两个表达式加上括号。它看起来像这样:

  . . .
else if i mod 3 == 0 && i mod 5 != 0 then (
  Printf.printf "Fizz: %d \n" i;
  fizbuzz_rr (i - 1)
) else if i mod 3 != 0 && i mod 5 == 0 then (
  . . .

最后你还有一个额外()的没有做任何事情。你应该像这样删除它:

else (
  Printf.printf "Current Number: %d \n" i ;
  fizbuzz_rr (i - 1)
)

推荐阅读