src/HOL/ex/Word_Type.thy
changeset 66815 93c6632ddf44
parent 66806 a4e82b58d833
child 67816 2249b27ab1dd
equal deleted inserted replaced
66814:a24cde9588bb 66815:93c6632ddf44
     9     "HOL-Library.Type_Length"
     9     "HOL-Library.Type_Length"
    10 begin
    10 begin
    11 
    11 
    12 subsection \<open>Truncating bit representations of numeric types\<close>
    12 subsection \<open>Truncating bit representations of numeric types\<close>
    13 
    13 
    14 class semiring_bits = unique_euclidean_semiring_parity +
    14 class semiring_bits = semiring_parity +
    15   assumes semiring_bits: "(1 + 2 * a) mod of_nat (2 * n) = 1 + 2 * (a mod of_nat n)"
    15   assumes semiring_bits: "(1 + 2 * a) mod of_nat (2 * n) = 1 + 2 * (a mod of_nat n)"
    16 begin
    16 begin
    17 
    17 
    18 definition bitrunc :: "nat \<Rightarrow> 'a \<Rightarrow> 'a"
    18 definition bitrunc :: "nat \<Rightarrow> 'a \<Rightarrow> 'a"
    19   where bitrunc_eq_mod: "bitrunc n a = a mod of_nat (2 ^ n)"
    19   where bitrunc_eq_mod: "bitrunc n a = a mod of_nat (2 ^ n)"
    25 lemma bitrunc_0 [simp]:
    25 lemma bitrunc_0 [simp]:
    26   "bitrunc 0 a = 0"
    26   "bitrunc 0 a = 0"
    27   by (simp add: bitrunc_eq_mod)
    27   by (simp add: bitrunc_eq_mod)
    28 
    28 
    29 lemma bitrunc_Suc [simp]:
    29 lemma bitrunc_Suc [simp]:
    30   "bitrunc (Suc n) a = bitrunc n (a div 2) * 2 + a mod 2"
    30   "bitrunc (Suc n) a = bitrunc n (a div 2) * 2 + of_bool (odd a)"
    31 proof -
    31 proof -
    32   define b and c
    32   have "1 + 2 * (a div 2) mod (2 * 2 ^ n) = (a div 2 * 2 + a mod 2) mod (2 * 2 ^ n)"
    33     where "b = a div 2" and "c = a mod 2"
    33     if "odd a"
    34   then have a: "a = b * 2 + c" 
    34     using that semiring_bits [of "a div 2" "2 ^ n"]
    35     and "c = 0 \<or> c = 1"
    35       by (simp add: algebra_simps odd_iff_mod_2_eq_one mult_mod_right)
    36     by (simp_all add: div_mult_mod_eq parity)
    36   also have "\<dots> = a mod (2 * 2 ^ n)"
    37   from \<open>c = 0 \<or> c = 1\<close>
    37     by (simp only: div_mult_mod_eq)
    38   have "bitrunc (Suc n) (b * 2 + c) = bitrunc n b * 2 + c"
    38   finally show ?thesis
    39   proof
    39     by (simp add: bitrunc_eq_mod algebra_simps mult_mod_right)
    40     assume "c = 0"
       
    41     moreover have "(2 * b) mod (2 * 2 ^ n) = 2 * (b mod 2 ^ n)"
       
    42       by (simp add: mod_mult_mult1)
       
    43     ultimately show ?thesis
       
    44       by (simp add: bitrunc_eq_mod ac_simps)
       
    45   next
       
    46     assume "c = 1"
       
    47     with semiring_bits [of b "2 ^ n"] show ?thesis
       
    48       by (simp add: bitrunc_eq_mod ac_simps)
       
    49   qed
       
    50   with a show ?thesis
       
    51     by (simp add: b_def c_def)
       
    52 qed
    40 qed
    53 
    41 
    54 lemma bitrunc_of_0 [simp]:
    42 lemma bitrunc_of_0 [simp]:
    55   "bitrunc n 0 = 0"
    43   "bitrunc n 0 = 0"
    56   by (simp add: bitrunc_eq_mod)
    44   by (simp add: bitrunc_eq_mod)
    57 
    45 
    58 lemma bitrunc_plus:
    46 lemma bitrunc_plus:
    59   "bitrunc n (bitrunc n a + bitrunc n b) = bitrunc n (a + b)"
    47   "bitrunc n (bitrunc n a + bitrunc n b) = bitrunc n (a + b)"
    60   by (simp add: bitrunc_eq_mod mod_add_eq)
    48   by (simp add: bitrunc_eq_mod mod_simps)
    61 
    49 
    62 lemma bitrunc_of_1_eq_0_iff [simp]:
    50 lemma bitrunc_of_1_eq_0_iff [simp]:
    63   "bitrunc n 1 = 0 \<longleftrightarrow> n = 0"
    51   "bitrunc n 1 = 0 \<longleftrightarrow> n = 0"
    64   by (induct n) simp_all
    52   by (simp add: bitrunc_eq_mod)
    65 
    53 
    66 end
    54 end
    67 
    55 
    68 instance nat :: semiring_bits
    56 instance nat :: semiring_bits
    69   by standard (simp add: mod_Suc Suc_double_not_eq_double)
    57   by standard (simp add: mod_Suc Suc_double_not_eq_double)
   111     by (simp add: signed_bitrunc_eq_bitrunc odd_iff_mod_2_eq_one)
    99     by (simp add: signed_bitrunc_eq_bitrunc odd_iff_mod_2_eq_one)
   112 qed
   100 qed
   113 
   101 
   114 lemma signed_bitrunc_Suc [simp]:
   102 lemma signed_bitrunc_Suc [simp]:
   115   "signed_bitrunc (Suc n) k = signed_bitrunc n (k div 2) * 2 + k mod 2"
   103   "signed_bitrunc (Suc n) k = signed_bitrunc n (k div 2) * 2 + k mod 2"
   116   using zero_not_eq_two by (simp add: signed_bitrunc_eq_bitrunc algebra_simps)
   104   by (simp add: odd_iff_mod_2_eq_one signed_bitrunc_eq_bitrunc algebra_simps)
   117 
   105 
   118 lemma signed_bitrunc_of_0 [simp]:
   106 lemma signed_bitrunc_of_0 [simp]:
   119   "signed_bitrunc n 0 = 0"
   107   "signed_bitrunc n 0 = 0"
   120   by (simp add: signed_bitrunc_eq_bitrunc bitrunc_eq_mod)
   108   by (simp add: signed_bitrunc_eq_bitrunc bitrunc_eq_mod)
   121 
   109