I'm trying the list example from the official Isabelle tutorial. I replaced the #
with :
and the @
with ++
to have the same syntax as Haskell. Now I get warnings about ambiguities in the AST. I know that I can hide functions with hide_const
but this doesn't work for operators in infix notation. How can I hide operators in Isabelle?
The exact warning message is:
Ambiguous input⌂ produces 2 parse trees:
("\<^const>HOL.Trueprop"
("\<^const>HOL.eq" ("\<^const>Map.map_add" ("/<^const>toylist.list.Nil") ("_position" ys))
("_position" ys)))
("\<^const>HOL.Trueprop"
("\<^const>HOL.eq" ("\<^fixed>app" ("\<^const>toylist.list.Nil") ("_position" ys)) ("_position" ys)))
Fortunately, only one parse tree is well-formed and type-correct,
but you may still want to disambiguate your grammar or your input.
Hiding an operator does not delete its notation. There is a separate command no_notation
to delete existing notations. In Isabelle/HOL, ++
is bound to map_add
as can be seen from the ambiguity warning. You can delete it as follows.
no_notation map_add (infixl "++" 100)
Note that you must repeat the exact precedence parameters with which the notation to be deleted has been declared. There is no easy way to find the notation declaration for a constant, but it is good style to declare notation close to the declaration of the constant; Ctrl-clicking on a constant takes you to its declaration.
Regarding :
, this is by default bound to Set.member
. You can delete it with no_notation Set.member ("(_/ : _)" [51, 51] 50)
.
Unless for demonstatory or exploratory purposes, I recommend not to change the default syntax of Isabelle too much. Otherwise, other Isabelle users will find it hard to read your code and your theories will not be compatible with others'. The reason is that when importing different theories, notations are merged additively. Thus, if you delete the notation ++
for map_add
in theory A
and theory B
imports the theories A
and some other theory derived from Main
but not A
, then the ambiguity for ++
is back in theory B
.
You can use the command no_notation
which takes the same arguments that were used during the notation declaration with the command notation
(or within the constant definition).
Both symbols :
and ++
are already used by Set.member
and map_add
respectively. So you have to find these notation declarations and use them in no_notation
:
no_notation Set.member ("(_/ : _)" [51, 51] 50)
no_notation map_add (infixl "++" 100)
Then you can proceed in the same way you certainly already have, and by removing the now obsolete syntax for list:
no_notation Cons (infixr "#" 65)
notation Cons (infixr ":" 65)
no_notation List.append (infixr "@" 65)
notation List.append (infixr "++" 65)
term "x : (xs ++ ys)"
The notation for Set.member
:
would not really miss as there already is the xsymbol/utf-8 notation ∈
. I think map_add
is not that used, but you could then use the free notation @
for it.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With