I am trying to understand how combined ssreflect tactics should be "decomposed" (or how they are composed in the first place). One of the problems I have is to understand the order and associativity of the taticals.
Sometimes, I feel that the order is from right to left. For example
apply : AiB.
seems equivalent to
move : AiB; apply.
Ignoring the no-op move
, it's as if we are applying functions to AiB
in order, and apply : AiB.
can be viewed as apply (: AiB).
. That is, we first move AiB into the goal and then call apply
on the goal with AiB
in it.
However, I am confused in other occasions:
case: (EM (P y)) => // notPy.
According to the tutorial, this one does a case analysis on (EM (P y))
, and then //
tries to solve trivial sub-goals. Then?? move =>
introduce the remaining ones into the context? What's the order of operations here?
Let EM_
be (EM (P y))
, is it (move=> notPy (// ( case (:EM_) ) ) )
??
Am I reading this right, what is the "correct order" of tactic application?
The order is kind of twisted near notPy
and inconsistent in general. Is there a way to write the above from right to left in legitimate ssreflect?