问题
What is a "Quotient type pattern" in Isabelle?
I couldn't find any explanation over the internet.
回答1:
It would be better if you would quote a little from where you saw the phrase. I know of "pattern matching," and I know of "quotient type," but I don't know of "quotient type pattern."
I prefer not to ask for clarification, and then wait, so I pick two of the three words, "quotient type." If I'm on the wrong track, it's still a worthy subject, and a big and important part of Isabelle/HOL.
There is the quotient_type
keyword, and it allows you to define a new type with an equivalence relation.
It is part of the quotient package, described starting on page 248 of isar-ref.pdf. There happens to be a Wiki page, Quotient_type.
A more involved description is given by Brian Hufmann and Ondřej Kunčar. Go to Kunčar's web page and look at the two PDFs titled Lifting and Transfer: A Modular Design for Quotients in Isabelle/HOL, which are not exactly the same.
It happens to be that lifting and quotient types are heavily related, and not easy to understand, which is why I try to study a little here and there, like right now, to get a better understanding of it all.
Integers and Rationals in HOL Are Quotient Types, I Pick One as an Example, Integers
You can start by looking Int.thy.
For a quotient type, you need an equivalence relation, which defines a set, and intrel
is what is used to define that set for type int
.
definition intrel :: "(nat * nat) => (nat * nat) => bool" where
"intrel = (%(x, y) (u, v). x + v = u + y)"
This is the classic definition of the integers, based on the natural numbers. Integers are ordered pairs of natural numbers (and sets as I describe below), and they're equal by that definition.
For example, informally, (2,3) = (4,5)
because 2 + 5 = 4 + 3
.
I'm boring you, and you're waiting for the good stuff. Here's part of it, the use of quotient_type
:
quotient_type int = "nat * nat" / "intrel"
morphisms Rep_Integ Abs_Integ
Those two morphisms come into play, if you want to strain your brain, and really understand what's going on, which I do. There are lots of functions and simp rules that quotient_type
generates, and you have to do a lot of work to find it all, such as with the find_theorems
command.
An Abs
function abstracts an ordered pair to an int
. Check these out:
lemma "Abs_Integ(1,0) = (1::int)"
by(metis one_int_def)
lemma "Abs_Integ(x,0) + Abs_Integ(y,0) ≥ (0::int)"
by(smt int_def)
They show that an int
really is an ordered pair, under the hood of the engine.
Now I show the explicit types of those morphisms, along with Abs_int
and Rep_int
, which show int
not only as an ordered pair, but as a set of ordered pairs.
term "Abs_int :: (nat * nat) set => int"
term "Abs_Integ :: (nat * nat) => int"
term "Rep_int :: int => (nat * nat) set"
term "Rep_Integ :: int => (nat * nat)"
I'm boring you again, but I have an emotional need to show some more examples. Two positive integers are equal if the components of the ordered pairs differ by one, such as these:
lemma "Abs_Integ(1,0) = Abs_Integ(3,2)"
by(smt nat.abs_eq split_conv)
lemma "Abs_Integ(4,3) = Abs_Integ(3,2)"
by(smt nat.abs_eq split_conv)
What would you expect if you added Abs_Integ(4,3)
and Abs_Integ(3,2)
? This:
lemma "Abs_Integ(2,3) + Abs_Integ(3,4) = Abs_Integ(2 + 3, 3 + 4)"
by(metis plus_int.abs_eq plus_int_def split_conv)
That plus_int
in the proof is defined in Int.thy, on line 44.
lift_definition plus_int :: "int => int => int"
is "%(x, y) (u, v). (x + u, y + v)"
What is this lifting all about? That would put me at "days into" this explanation, and I'm only just starting to understand it a little.
The find_theorems
shows there's lots of stuff hidden, as I said:
thm "plus_int.abs_eq"
find_theorems name: "Int.plus_int*"
More examples, but these are to emphasize that, under the hood of the engine, an int
ties back into an equivalence class as a set, where I'm using intrel
above to define the sets right:
term "Abs_int::(nat * nat) set => int"
term "Abs_int {(x,y). x + 3 = 2 + y}" (*(2,3)*)
term "Abs_int {(x,y). x + 4 = 3 + y}" (*(3,4)*)
lemma "Abs_int {(x,y). x + 3 = 2 + y} = Abs_int {(x,y). x + 100 = 99 + y}"
by(auto)
That auto
proof was easy, but there's no magic coming through for me on this next one, even though it's simple.
lemma "Abs_int {(x,y). x + 3 = 2 + y} + Abs_int {(x,y). x + 4 = 3 + y}
= Abs_int {(x,y). x + 7 = 5 + y}"
apply(auto simp add: plus_int.abs_eq plus_int_def intrel_def)
oops
It could be that all I need to do is tap into something that's not a simp rule by default.
If quotient_type
is not the "quotient type pattern" you're talking about, at least I got something out of it by seeing all what find_theorems
returns about Int.plus_int*
above.
来源:https://stackoverflow.com/questions/23478260/what-is-a-quotient-type-pattern-in-isabelle