logiccoqcurry-howard

Implications as functions in Coq?


I read that implications are functions. But I have a hard time trying to understand the example given in the above mentioned page:

The proof term for an implication P → Q is a function that takes evidence for P as input and produces evidence for Q as its output.

Lemma silly_implication : (1 + 1) = 2 → 0 × 3 = 0. Proof. intros H. reflexivity. Qed.

We can see that the proof term for the above lemma is indeed a function:

Print silly_implication. (* ===> silly_implication = fun _ : 1 + 1 = 2 => eq_refl : 1 + 1 = 2 -> 0 * 3 = 0 *)

Indeed, it's a function. But its type does not look right to me. From my reading, the proof term for P -> Q should be a function with an evidence for Q as output. Then, the output of (1+1) = 2 -> 0*3 = 0 should be an evidence for 0*3 = 0, alone, right?

But the Coq print out above shows that the function image is eq_refl : 1 + 1 = 2 -> 0 * 3 = 0, instead of eq_refl: 0 * 3 = 0. I don't understand why the hypothesis 1 + 1 = 2 should appear in the output. Can anyone help explain what is going on here?

Thanks.


Solution

  • Your understanding is correct until:

    But the Coq print out above shows that the function image is ...

    I think you misunderstand the Print command. Print shows you the term associated with a definition, along with the type of the definition. It does not show the image/output of a function.

    For example, the following prints the definition and type of the value x:

    Definition x := 5.
    Print x.
    > x = 5 
    >   : nat
    

    Similarly, the following prints the definition and type of the function f:

    Definition f := fun n => n + 2.
    Print f.
    > f = fun n : nat => n + 2
    >   : nat -> nat
    

    If you want to see the function's codomain, you have to apply the function to a value, like so:

    Definition fx := f x.
    Print fx.
    > fx = f x
    >    : nat
    

    If you want to see the image/output of a function Print won't help you. What you need is Compute. Compute takes a term (e.g. a function application) and reduces it as far as possible:

    Compute (f x).
    > = 7
    > : nat