src/HOL/Isar_Examples/Hoare_Ex.thy
author wenzelm
Tue, 20 Oct 2009 19:37:09 +0200
changeset 33026 8f35633c4922
parent 31758 src/HOL/Isar_examples/Hoare_Ex.thy@3edd5f813f01
child 37671 fa53d267dab3
permissions -rw-r--r--
modernized session Isar_Examples;
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
     1
header {* Using Hoare Logic *}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
     2
31758
3edd5f813f01 observe standard theory naming conventions;
wenzelm
parents: 25706
diff changeset
     3
theory Hoare_Ex
3edd5f813f01 observe standard theory naming conventions;
wenzelm
parents: 25706
diff changeset
     4
imports Hoare
3edd5f813f01 observe standard theory naming conventions;
wenzelm
parents: 25706
diff changeset
     5
begin
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
     6
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
     7
subsection {* State spaces *}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
     8
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
     9
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    10
 First of all we provide a store of program variables that
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    11
 occur in any of the programs considered later.  Slightly unexpected
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    12
 things may happen when attempting to work with undeclared variables.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    13
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    14
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    15
record vars =
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    16
  I :: nat
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    17
  M :: nat
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    18
  N :: nat
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    19
  S :: nat
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    20
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    21
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    22
 While all of our variables happen to have the same type, nothing
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    23
 would prevent us from working with many-sorted programs as well, or
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    24
 even polymorphic ones.  Also note that Isabelle/HOL's extensible
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    25
 record types even provides simple means to extend the state space
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    26
 later.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    27
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    28
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    29
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    30
subsection {* Basic examples *}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    31
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    32
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    33
 We look at few trivialities involving assignment and sequential
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    34
 composition, in order to get an idea of how to work with our
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    35
 formulation of Hoare Logic.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    36
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    37
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    38
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    39
 Using the basic \name{assign} rule directly is a bit cumbersome.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    40
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    41
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    42
lemma
25706
45d090186bbe accomodate to replacement of K_record by %x.c
schirmer
parents: 21226
diff changeset
    43
  "|- .{\<acute>(N_update (\<lambda>_. (2 * \<acute>N))) : .{\<acute>N = 10}.}. \<acute>N := 2 * \<acute>N .{\<acute>N = 10}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    44
  by (rule assign)
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    45
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    46
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    47
 Certainly we want the state modification already done, e.g.\ by
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    48
 simplification.  The \name{hoare} method performs the basic state
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    49
 update for us; we may apply the Simplifier afterwards to achieve
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    50
 ``obvious'' consequences as well.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    51
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    52
11704
3c50a2cd6f00 * sane numerals (stage 2): plain "num" syntax (removed "#");
wenzelm
parents: 11701
diff changeset
    53
lemma "|- .{True}. \<acute>N := 10 .{\<acute>N = 10}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    54
  by hoare
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    55
11704
3c50a2cd6f00 * sane numerals (stage 2): plain "num" syntax (removed "#");
wenzelm
parents: 11701
diff changeset
    56
lemma "|- .{2 * \<acute>N = 10}. \<acute>N := 2 * \<acute>N .{\<acute>N = 10}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    57
  by hoare
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    58
11704
3c50a2cd6f00 * sane numerals (stage 2): plain "num" syntax (removed "#");
wenzelm
parents: 11701
diff changeset
    59
lemma "|- .{\<acute>N = 5}. \<acute>N := 2 * \<acute>N .{\<acute>N = 10}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    60
  by hoare simp
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    61
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
    62
lemma "|- .{\<acute>N + 1 = a + 1}. \<acute>N := \<acute>N + 1 .{\<acute>N = a + 1}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    63
  by hoare
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    64
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
    65
lemma "|- .{\<acute>N = a}. \<acute>N := \<acute>N + 1 .{\<acute>N = a + 1}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    66
  by hoare simp
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    67
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
    68
lemma "|- .{a = a & b = b}. \<acute>M := a; \<acute>N := b .{\<acute>M = a & \<acute>N = b}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    69
  by hoare
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    70
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
    71
lemma "|- .{True}. \<acute>M := a; \<acute>N := b .{\<acute>M = a & \<acute>N = b}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    72
  by hoare simp
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    73
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    74
lemma
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
    75
"|- .{\<acute>M = a & \<acute>N = b}.
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
    76
    \<acute>I := \<acute>M; \<acute>M := \<acute>N; \<acute>N := \<acute>I
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
    77
    .{\<acute>M = b & \<acute>N = a}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    78
  by hoare simp
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    79
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    80
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    81
 It is important to note that statements like the following one can
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    82
 only be proven for each individual program variable.  Due to the
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    83
 extra-logical nature of record fields, we cannot formulate a theorem
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    84
 relating record selectors and updates schematically.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    85
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    86
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
    87
lemma "|- .{\<acute>N = a}. \<acute>N := \<acute>N .{\<acute>N = a}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    88
  by hoare
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    89
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
    90
lemma "|- .{\<acute>x = a}. \<acute>x := \<acute>x .{\<acute>x = a}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    91
  oops
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    92
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    93
lemma
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    94
  "Valid {s. x s = a} (Basic (\<lambda>s. x_update (x s) s)) {s. x s = n}"
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    95
  -- {* same statement without concrete syntax *}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    96
  oops
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    97
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    98
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
    99
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   100
 In the following assignments we make use of the consequence rule in
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   101
 order to achieve the intended precondition.  Certainly, the
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   102
 \name{hoare} method is able to handle this case, too.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   103
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   104
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   105
lemma "|- .{\<acute>M = \<acute>N}. \<acute>M := \<acute>M + 1 .{\<acute>M ~= \<acute>N}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   106
proof -
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   107
  have ".{\<acute>M = \<acute>N}. <= .{\<acute>M + 1 ~= \<acute>N}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   108
    by auto
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   109
  also have "|- ... \<acute>M := \<acute>M + 1 .{\<acute>M ~= \<acute>N}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   110
    by hoare
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   111
  finally show ?thesis .
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   112
qed
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   113
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   114
lemma "|- .{\<acute>M = \<acute>N}. \<acute>M := \<acute>M + 1 .{\<acute>M ~= \<acute>N}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   115
proof -
11701
3d51fbf81c17 sane numerals (stage 1): added generic 1, removed 1' and 2 on nat,
wenzelm
parents: 10838
diff changeset
   116
  have "!!m n::nat. m = n --> m + 1 ~= n"
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   117
      -- {* inclusion of assertions expressed in ``pure'' logic, *}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   118
      -- {* without mentioning the state space *}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   119
    by simp
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   120
  also have "|- .{\<acute>M + 1 ~= \<acute>N}. \<acute>M := \<acute>M + 1 .{\<acute>M ~= \<acute>N}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   121
    by hoare
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   122
  finally show ?thesis .
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   123
qed
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   124
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   125
lemma "|- .{\<acute>M = \<acute>N}. \<acute>M := \<acute>M + 1 .{\<acute>M ~= \<acute>N}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   126
  by hoare simp
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   127
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   128
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   129
subsection {* Multiplication by addition *}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   130
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   131
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   132
 We now do some basic examples of actual \texttt{WHILE} programs.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   133
 This one is a loop for calculating the product of two natural
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   134
 numbers, by iterated addition.  We first give detailed structured
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   135
 proof based on single-step Hoare rules.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   136
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   137
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   138
lemma
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   139
  "|- .{\<acute>M = 0 & \<acute>S = 0}.
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   140
      WHILE \<acute>M ~= a
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   141
      DO \<acute>S := \<acute>S + b; \<acute>M := \<acute>M + 1 OD
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   142
      .{\<acute>S = a * b}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   143
proof -
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   144
  let "|- _ ?while _" = ?thesis
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   145
  let ".{\<acute>?inv}." = ".{\<acute>S = \<acute>M * b}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   146
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   147
  have ".{\<acute>M = 0 & \<acute>S = 0}. <= .{\<acute>?inv}." by auto
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   148
  also have "|- ... ?while .{\<acute>?inv & ~ (\<acute>M ~= a)}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   149
  proof
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   150
    let ?c = "\<acute>S := \<acute>S + b; \<acute>M := \<acute>M + 1"
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   151
    have ".{\<acute>?inv & \<acute>M ~= a}. <= .{\<acute>S + b = (\<acute>M + 1) * b}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   152
      by auto
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   153
    also have "|- ... ?c .{\<acute>?inv}." by hoare
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   154
    finally show "|- .{\<acute>?inv & \<acute>M ~= a}. ?c .{\<acute>?inv}." .
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   155
  qed
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   156
  also have "... <= .{\<acute>S = a * b}." by auto
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   157
  finally show ?thesis .
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   158
qed
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   159
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   160
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   161
 The subsequent version of the proof applies the \name{hoare} method
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   162
 to reduce the Hoare statement to a purely logical problem that can be
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   163
 solved fully automatically.  Note that we have to specify the
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   164
 \texttt{WHILE} loop invariant in the original statement.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   165
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   166
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   167
lemma
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   168
  "|- .{\<acute>M = 0 & \<acute>S = 0}.
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   169
      WHILE \<acute>M ~= a
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   170
      INV .{\<acute>S = \<acute>M * b}.
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   171
      DO \<acute>S := \<acute>S + b; \<acute>M := \<acute>M + 1 OD
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   172
      .{\<acute>S = a * b}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   173
  by hoare auto
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   174
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   175
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   176
subsection {* Summing natural numbers *}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   177
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   178
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   179
 We verify an imperative program to sum natural numbers up to a given
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   180
 limit.  First some functional definition for proper specification of
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   181
 the problem.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   182
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   183
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   184
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   185
 The following proof is quite explicit in the individual steps taken,
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   186
 with the \name{hoare} method only applied locally to take care of
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   187
 assignment and sequential composition.  Note that we express
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   188
 intermediate proof obligation in pure logic, without referring to the
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   189
 state space.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   190
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   191
15912
nipkow
parents: 15569
diff changeset
   192
declare atLeast0LessThan[symmetric,simp]
15569
1b3115d1a8df fixed proof
nipkow
parents: 15049
diff changeset
   193
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   194
theorem
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   195
  "|- .{True}.
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   196
      \<acute>S := 0; \<acute>I := 1;
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   197
      WHILE \<acute>I ~= n
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   198
      DO
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   199
        \<acute>S := \<acute>S + \<acute>I;
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   200
        \<acute>I := \<acute>I + 1
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   201
      OD
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   202
      .{\<acute>S = (SUM j<n. j)}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   203
  (is "|- _ (_; ?while) _")
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   204
proof -
15049
82fb87151718 more summation syntax
nipkow
parents: 13473
diff changeset
   205
  let ?sum = "\<lambda>k::nat. SUM j<k. j"
82fb87151718 more summation syntax
nipkow
parents: 13473
diff changeset
   206
  let ?inv = "\<lambda>s i::nat. s = ?sum i"
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   207
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   208
  have "|- .{True}. \<acute>S := 0; \<acute>I := 1 .{?inv \<acute>S \<acute>I}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   209
  proof -
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   210
    have "True --> 0 = ?sum 1"
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   211
      by simp
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   212
    also have "|- .{...}. \<acute>S := 0; \<acute>I := 1 .{?inv \<acute>S \<acute>I}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   213
      by hoare
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   214
    finally show ?thesis .
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   215
  qed
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   216
  also have "|- ... ?while .{?inv \<acute>S \<acute>I & ~ \<acute>I ~= n}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   217
  proof
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   218
    let ?body = "\<acute>S := \<acute>S + \<acute>I; \<acute>I := \<acute>I + 1"
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   219
    have "!!s i. ?inv s i & i ~= n -->  ?inv (s + i) (i + 1)"
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   220
      by simp
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   221
    also have "|- .{\<acute>S + \<acute>I = ?sum (\<acute>I + 1)}. ?body .{?inv \<acute>S \<acute>I}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   222
      by hoare
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   223
    finally show "|- .{?inv \<acute>S \<acute>I & \<acute>I ~= n}. ?body .{?inv \<acute>S \<acute>I}." .
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   224
  qed
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   225
  also have "!!s i. s = ?sum i & ~ i ~= n --> s = ?sum n"
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   226
    by simp
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   227
  finally show ?thesis .
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   228
qed
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   229
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   230
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   231
 The next version uses the \name{hoare} method, while still explaining
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   232
 the resulting proof obligations in an abstract, structured manner.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   233
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   234
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   235
theorem
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   236
  "|- .{True}.
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   237
      \<acute>S := 0; \<acute>I := 1;
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   238
      WHILE \<acute>I ~= n
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   239
      INV .{\<acute>S = (SUM j<\<acute>I. j)}.
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   240
      DO
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   241
        \<acute>S := \<acute>S + \<acute>I;
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   242
        \<acute>I := \<acute>I + 1
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   243
      OD
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   244
      .{\<acute>S = (SUM j<n. j)}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   245
proof -
15049
82fb87151718 more summation syntax
nipkow
parents: 13473
diff changeset
   246
  let ?sum = "\<lambda>k::nat. SUM j<k. j"
82fb87151718 more summation syntax
nipkow
parents: 13473
diff changeset
   247
  let ?inv = "\<lambda>s i::nat. s = ?sum i"
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   248
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   249
  show ?thesis
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   250
  proof hoare
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   251
    show "?inv 0 1" by simp
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   252
  next
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   253
    fix s i assume "?inv s i & i ~= n"
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   254
    thus "?inv (s + i) (i + 1)" by simp
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   255
  next
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   256
    fix s i assume "?inv s i & ~ i ~= n"
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   257
    thus "s = ?sum n" by simp
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   258
  qed
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   259
qed
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   260
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   261
text {*
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   262
 Certainly, this proof may be done fully automatic as well, provided
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   263
 that the invariant is given beforehand.
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   264
*}
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   265
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   266
theorem
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   267
  "|- .{True}.
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   268
      \<acute>S := 0; \<acute>I := 1;
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   269
      WHILE \<acute>I ~= n
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   270
      INV .{\<acute>S = (SUM j<\<acute>I. j)}.
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   271
      DO
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   272
        \<acute>S := \<acute>S + \<acute>I;
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   273
        \<acute>I := \<acute>I + 1
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   274
      OD
10838
9423817dee84 use \<acute>;
wenzelm
parents: 10148
diff changeset
   275
      .{\<acute>S = (SUM j<n. j)}."
10148
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   276
  by hoare auto
739327964a5c Hoare logic in Isar;
wenzelm
parents:
diff changeset
   277
18193
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   278
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   279
subsection{* Time *}
13473
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   280
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   281
text{*
18193
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   282
  A simple embedding of time in Hoare logic: function @{text timeit}
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   283
  inserts an extra variable to keep track of the elapsed time.
13473
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   284
*}
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   285
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   286
record tstate = time :: nat
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   287
18193
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   288
types 'a time = "\<lparr>time :: nat, \<dots> :: 'a\<rparr>"
13473
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   289
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   290
consts timeit :: "'a time com \<Rightarrow> 'a time com"
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   291
primrec
18193
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   292
  "timeit (Basic f) = (Basic f; Basic(\<lambda>s. s\<lparr>time := Suc (time s)\<rparr>))"
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   293
  "timeit (c1; c2) = (timeit c1; timeit c2)"
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   294
  "timeit (Cond b c1 c2) = Cond b (timeit c1) (timeit c2)"
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   295
  "timeit (While b iv c) = While b iv (timeit c)"
13473
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   296
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   297
record tvars = tstate +
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   298
  I :: nat
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   299
  J :: nat
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   300
18193
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   301
lemma lem: "(0::nat) < n \<Longrightarrow> n + n \<le> Suc (n * n)"
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   302
  by (induct n) simp_all
13473
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   303
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   304
lemma "|- .{i = \<acute>I & \<acute>time = 0}.
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   305
 timeit(
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   306
 WHILE \<acute>I \<noteq> 0
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   307
 INV .{2*\<acute>time + \<acute>I*\<acute>I + 5*\<acute>I = i*i + 5*i}.
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   308
 DO
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   309
   \<acute>J := \<acute>I;
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   310
   WHILE \<acute>J \<noteq> 0
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   311
   INV .{0 < \<acute>I & 2*\<acute>time + \<acute>I*\<acute>I + 3*\<acute>I + 2*\<acute>J - 2 = i*i + 5*i}.
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   312
   DO \<acute>J := \<acute>J - 1 OD;
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   313
   \<acute>I := \<acute>I - 1
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   314
 OD
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   315
 ) .{2*\<acute>time = i*i + 5*i}."
18193
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   316
  apply simp
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   317
  apply hoare
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   318
      apply simp
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   319
     apply clarsimp
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   320
    apply clarsimp
20432
07ec57376051 lin_arith_prover: splitting reverted because of performance loss
webertj
parents: 20272
diff changeset
   321
   apply arith
18193
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   322
   prefer 2
13473
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   323
   apply clarsimp
18193
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   324
  apply (clarsimp simp: nat_distrib)
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   325
  apply (frule lem)
13473
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   326
  apply arith
18193
54419506df9e tuned document;
wenzelm
parents: 16417
diff changeset
   327
  done
13473
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   328
194e8d2cbe0f Added time example at the end.
nipkow
parents: 11704
diff changeset
   329
end