0
(** **** Exercise: 3 stars, standard, optional (ev_plus_plus)

    This exercise just requires applying existing lemmas.  No
    induction or even case analysis is needed, though some of the
    rewriting may be tedious. *)

Theorem ev_plus_plus : forall n m p,
  even (n+m) -> even (n+p) -> even (m+p).
Proof.
  intros n m p H1 H2.

Here is what I got:

1 subgoal (ID 89)

n, m, p : nat
H1 : even (n + m)
H2 : even (n + p)
============================
even (m + p)

I have proven the previous theorem:

Theorem ev_ev__ev : forall n m,
  even (n+m) -> even n -> even m.

And wanted to apply it to H1, but

apply ev_ev__ev in H1.

gives an error:

Error: Unable to find an instance for the variable m.

Why can't it find "m" in the expression even (n + m)? How to fix?

Update

apply ev_ev__ev with (m:=m) in H1.

gives a very strange result:

2 subgoals (ID 90)

n, m, p : nat
H1 : even m
H2 : even (n + p)
============================
even (m + p)

subgoal 2 (ID 92) is:
 even (n + m + m)

I thought that it will transform H1 to 2 hypothesis:

H11 : even n
H12 : even m

But instead it gave 2 subgoals, the second that we need to prove is more complicated than the initial one:

even (n + m + m)

What's happening here?

user4035
  • 22,508
  • 11
  • 59
  • 94
  • No, you will not get `H11` and `H12` by applying `ev_ev__ev`. You can only get the hypothesis `even n -> even m`. – larsr May 26 '19 at 09:14

3 Answers3

2

The statement forall n m, even (n+m) -> even n -> even m. does not mean "if we have that (n + m) is even then we have both that n is even and that m is even" (this is false, consider n = m = 1). Instead it means "if we have that (n+m) is even, and we have that n is even, then we have that m is even".

There is no way to get H11 : even n and H12 : even m just from H1 : even (n + m) without assuming a contradiction. I would suggest figuring out how to prove your theorem with pen and paper before trying to prove it in Coq.

Jason Gross
  • 5,928
  • 1
  • 26
  • 53
1

Because Coq can't figure out what value it should give for m. You can apply the tactic eapply ev_ev__ev in H1. and see the goals

  n, m, p : nat
  H2 : even (n + p)
  H1 : even ?m
  ============================
  even (m + p)

subgoal 2 (ID 17) is:
 even (n + m + ?m)

Coq has instantiated the m with a meta variable ?m, and you need to give a witness for this meta variable in the end to finish the proof.

Second approach is just apply the tactic with instantiating the value of m apply ev_ev__ev with (m := m) in H1.

You can see more on apply with tactics in software-foundations https://softwarefoundations.cis.upenn.edu/lf-current/Tactics.html

keep_learning
  • 1,057
  • 5
  • 14
  • @user4035 Sorry, I did not check it for couple of days. I did not pay attention to proof details, but I was more focused on making sure that apply tactic succeed. – keep_learning May 28 '19 at 06:06
1

The thing that is happening is that Coq unifies H1 with the even n argument of ev_ev__ev instead of the even (n+m).

You can tell Coq exactly where you want H1 to go, and use _ wildcards for the places where you let Coq work out the details.

You probably wanted this the term ev_ev__ev n m H1 with type even n -> even m but your apply produced the term ev_ev__ev (n+m) m _ H1 which also left you with some more stuff to prove. To take a look at the proof context, do

Check ev_ev__ev (n+m) m _ H1.
larsr
  • 5,447
  • 19
  • 38