recursionocaml

Why this recursion example in ocaml doesn't work for negative number?


In the Think Ocaml book the author gave this example:

let rec countdown n = 
    if n <= 0 then 
      ( print_string "Blastoff!"; 
        print_newline()) 
    else ( print_int n; print_newline(); 
       countdown (n-1); ());;

The function takes an int and returns a unit. However, the code suppose to work on negative numbers as mentioned in the book but it doesn't. The logic of the code seems fine and nothing wrong with it. I thought I would share it with people who know Ocaml to see what is wrong here.


Solution

  • Writing

    countdown -1
    

    doesn't mean what you expect it to mean. The problem is that - is an infix operator with the following signature:

    # (-);;
    - : int -> int -> int = <fun>
    

    As you can see it is a function taking 2 integer arguments and returning an integer. It's the subtraction "a - b". The above statement will be parsed as:

    (countdown) - (1)
    

    And countdown has type int -> unit instead of the expected type int.

    What you want instead is the unary minus that negates a number. The ocaml grammar is written so that an expression starting with - uses the unary minus but any minus in the middle of an expression is the binary minus. So you have to write one of the following:

    countdown (-1)
    countdown ~-1