275 |
275 |
276 syntax |
276 syntax |
277 "_Numerals" :: "xnum_token \<Rightarrow> 'a" ("_") |
277 "_Numerals" :: "xnum_token \<Rightarrow> 'a" ("_") |
278 |
278 |
279 parse_translation {* |
279 parse_translation {* |
280 let |
280 let |
281 fun num_of_int n = if n > 0 then case IntInf.quotRem (n, 2) |
281 fun num_of_int n = if n > 0 then case IntInf.quotRem (n, 2) |
282 of (0, 1) => Const (@{const_name One}, dummyT) |
282 of (0, 1) => Const (@{const_name One}, dummyT) |
283 | (n, 0) => Const (@{const_name Dig0}, dummyT) $ num_of_int n |
283 | (n, 0) => Const (@{const_name Dig0}, dummyT) $ num_of_int n |
284 | (n, 1) => Const (@{const_name Dig1}, dummyT) $ num_of_int n |
284 | (n, 1) => Const (@{const_name Dig1}, dummyT) $ num_of_int n |
285 else raise Match; |
285 else raise Match; |
286 fun numeral_tr [Free (num, _)] = |
286 fun numeral_tr [Free (num, _)] = |
287 let |
287 let |
288 val {leading_zeros, value, ...} = Lexicon.read_xnum num; |
288 val {leading_zeros, value, ...} = Lexicon.read_xnum num; |
289 val _ = leading_zeros = 0 andalso value > 0 |
289 val _ = leading_zeros = 0 andalso value > 0 |
290 orelse error ("Bad numeral: " ^ num); |
290 orelse error ("Bad numeral: " ^ num); |
291 in Const (@{const_name of_num}, @{typ num} --> dummyT) $ num_of_int value end |
291 in Const (@{const_name of_num}, @{typ num} --> dummyT) $ num_of_int value end |
292 | numeral_tr ts = raise TERM ("numeral_tr", ts); |
292 | numeral_tr ts = raise TERM ("numeral_tr", ts); |
293 in [(@{syntax_const "_Numerals"}, numeral_tr)] end |
293 in [(@{syntax_const "_Numerals"}, K numeral_tr)] end |
294 *} |
294 *} |
295 |
295 |
296 typed_print_translation (advanced) {* |
296 typed_print_translation {* |
297 let |
297 let |
298 fun dig b n = b + 2 * n; |
298 fun dig b n = b + 2 * n; |
299 fun int_of_num' (Const (@{const_syntax Dig0}, _) $ n) = |
299 fun int_of_num' (Const (@{const_syntax Dig0}, _) $ n) = |
300 dig 0 (int_of_num' n) |
300 dig 0 (int_of_num' n) |
301 | int_of_num' (Const (@{const_syntax Dig1}, _) $ n) = |
301 | int_of_num' (Const (@{const_syntax Dig1}, _) $ n) = |
302 dig 1 (int_of_num' n) |
302 dig 1 (int_of_num' n) |
303 | int_of_num' (Const (@{const_syntax One}, _)) = 1; |
303 | int_of_num' (Const (@{const_syntax One}, _)) = 1; |
304 fun num_tr' ctxt T [n] = |
304 fun num_tr' ctxt T [n] = |
305 let |
305 let |
306 val k = int_of_num' n; |
306 val k = int_of_num' n; |
307 val t' = Syntax.const @{syntax_const "_Numerals"} $ Syntax.free ("#" ^ string_of_int k); |
307 val t' = Syntax.const @{syntax_const "_Numerals"} $ Syntax.free ("#" ^ string_of_int k); |
308 in |
308 in |
309 case T of |
309 case T of |
310 Type (@{type_name fun}, [_, T']) => |
310 Type (@{type_name fun}, [_, T']) => |
311 if not (Printer.show_type_constraint ctxt) andalso can Term.dest_Type T' then t' |
311 if not (Printer.show_type_constraint ctxt) andalso can Term.dest_Type T' then t' |
312 else Syntax.const @{syntax_const "_constrain"} $ t' $ Syntax_Phases.term_of_typ ctxt T' |
312 else Syntax.const @{syntax_const "_constrain"} $ t' $ Syntax_Phases.term_of_typ ctxt T' |
313 | T' => if T' = dummyT then t' else raise Match |
313 | T' => if T' = dummyT then t' else raise Match |
314 end; |
314 end; |
315 in [(@{const_syntax of_num}, num_tr')] end |
315 in [(@{const_syntax of_num}, num_tr')] end |
316 *} |
316 *} |
317 |
317 |
318 |
318 |
319 subsection {* Class-specific numeral rules *} |
319 subsection {* Class-specific numeral rules *} |
320 |
320 |