(* * * Copyright 2017, Data61, CSIRO * * This software may be distributed and modified according to the terms of * the BSD 2-Clause license. Note that NO WARRANTY is provided. * See "LICENSE_BSD2.txt" for details. * * @TAG(DATA61_BSD) *) theory Value_Abbreviation imports Main keywords "value_abbreviation" :: thy_decl begin text {* Computing values and saving as abbreviations. Useful in program verification to handle some configuration constant (e.g. n = 4) which may change. This mechanism can be used to give names (abbreviations) to other related constants (e.g. 2 ^ n, 2 ^ n - 1, [1 .. n], rev [1 .. n]) which may appear repeatedly. *} ML {* structure Value_Abbreviation = struct fun value_and_abbreviation mode name eval_name expr int ctxt = let val decl = (name, NONE, Mixfix.NoSyn) val expr = Syntax.read_term ctxt expr val eval_expr = case eval_name of NONE => Value_Command.value ctxt expr | SOME n => Value_Command.value_select n ctxt expr val lhs = Free (Binding.name_of name, fastype_of expr) val eq = Logic.mk_equals (lhs, eval_expr) val ctxt = Specification.abbreviation mode (SOME decl) [] eq int ctxt val pretty_eq = Syntax.pretty_term ctxt eq in Pretty.writeln pretty_eq; ctxt end val opt_evaluator = Scan.option (@{keyword "["} |-- Parse.name --| @{keyword "]"}) val _ = Outer_Syntax.local_theory' @{command_keyword value_abbreviation} "setup abbreviation for evaluated value" (Parse.syntax_mode -- Parse.binding -- opt_evaluator -- Parse.term >> (fn (((mode, name), eval_name), expr) => value_and_abbreviation mode name eval_name expr)); end *} text {* Testing it out. Unfortunately locale/experiment/notepad all won't work here because the code equation setup is all global. *} definition "value_abbreviation_test_config_constant_1 = (24 :: nat)" definition "value_abbreviation_test_config_constant_2 = (5 :: nat)" value_abbreviation (input) value_abbreviation_test_important_magic_number [simp] "((2 :: int) ^ value_abbreviation_test_config_constant_1) - (2 ^ value_abbreviation_test_config_constant_2)" value_abbreviation (input) value_abbreviation_test_range_of_options [simp] "rev [int value_abbreviation_test_config_constant_2 .. int value_abbreviation_test_config_constant_1]" end