Mercurial > cpdt > repo
comparison src/Generic.v @ 302:7b38729be069
Tweak mark-up to support coqdoc 8.3
author | Adam Chlipala <adam@chlipala.net> |
---|---|
date | Mon, 17 Jan 2011 15:12:30 -0500 |
parents | 540a09187193 |
children | d5787b70cf48 |
comparison
equal
deleted
inserted
replaced
301:f4768d5a75eb | 302:7b38729be069 |
---|---|
170 else (hhd (htl cases)) tt INil. | 170 else (hhd (htl cases)) tt INil. |
171 Eval compute in size bool_fix. | 171 Eval compute in size bool_fix. |
172 (** %\vspace{-.15in}% [[ | 172 (** %\vspace{-.15in}% [[ |
173 = fun b : bool => if b then 1 else 1 | 173 = fun b : bool => if b then 1 else 1 |
174 : bool -> nat | 174 : bool -> nat |
175 ]] *) | 175 ]] |
176 *) | |
176 | 177 |
177 Definition nat_fix : fixDenote nat nat_dt := | 178 Definition nat_fix : fixDenote nat nat_dt := |
178 fun R cases => fix F (n : nat) : R := | 179 fun R cases => fix F (n : nat) : R := |
179 match n with | 180 match n with |
180 | O => (hhd cases) tt INil | 181 | O => (hhd cases) tt INil |
188 = fix F (n : nat) : nat := match n with | 189 = fix F (n : nat) : nat := match n with |
189 | 0 => 1 | 190 | 0 => 1 |
190 | S n' => F n' + 1 | 191 | S n' => F n' + 1 |
191 end | 192 end |
192 : nat -> nat | 193 : nat -> nat |
193 ]] *) | 194 ]] |
195 *) | |
194 | 196 |
195 Definition list_fix (A : Type) : fixDenote (list A) (list_dt A) := | 197 Definition list_fix (A : Type) : fixDenote (list A) (list_dt A) := |
196 fun R cases => fix F (ls : list A) : R := | 198 fun R cases => fix F (ls : list A) : R := |
197 match ls with | 199 match ls with |
198 | nil => (hhd cases) tt INil | 200 | nil => (hhd cases) tt INil |
205 match ls with | 207 match ls with |
206 | nil => 1 | 208 | nil => 1 |
207 | _ :: ls' => F ls' + 1 | 209 | _ :: ls' => F ls' + 1 |
208 end | 210 end |
209 : forall A : Type, list A -> nat | 211 : forall A : Type, list A -> nat |
210 ]] *) | 212 ]] |
213 *) | |
211 | 214 |
212 Definition tree_fix (A : Type) : fixDenote (tree A) (tree_dt A) := | 215 Definition tree_fix (A : Type) : fixDenote (tree A) (tree_dt A) := |
213 fun R cases => fix F (t : tree A) : R := | 216 fun R cases => fix F (t : tree A) : R := |
214 match t with | 217 match t with |
215 | Leaf x => (hhd cases) x INil | 218 | Leaf x => (hhd cases) x INil |
222 match t with | 225 match t with |
223 | Leaf _ => 1 | 226 | Leaf _ => 1 |
224 | Node t1 t2 => F t1 + (F t2 + 1) | 227 | Node t1 t2 => F t1 + (F t2 + 1) |
225 end | 228 end |
226 : forall A : Type, tree A -> n | 229 : forall A : Type, tree A -> n |
227 ]] *) | 230 ]] |
231 *) | |
228 (* end thide *) | 232 (* end thide *) |
229 | 233 |
230 | 234 |
231 (** ** Pretty-Printing *) | 235 (** ** Pretty-Printing *) |
232 | 236 |
258 (** %\vspace{-.15in}% [[ | 262 (** %\vspace{-.15in}% [[ |
259 hmap | 263 hmap |
260 : forall (A : Type) (B1 B2 : A -> Type), | 264 : forall (A : Type) (B1 B2 : A -> Type), |
261 (forall x : A, B1 x -> B2 x) -> | 265 (forall x : A, B1 x -> B2 x) -> |
262 forall ls : list A, hlist B1 ls -> hlist B2 ls | 266 forall ls : list A, hlist B1 ls -> hlist B2 ls |
263 ]] *) | 267 ]] |
268 *) | |
264 | 269 |
265 Definition print T dt (pr : print_datatype dt) (fx : fixDenote T dt) : T -> string := | 270 Definition print T dt (pr : print_datatype dt) (fx : fixDenote T dt) : T -> string := |
266 fx string (hmap (B1 := print_constructor) (B2 := constructorDenote string) | 271 fx string (hmap (B1 := print_constructor) (B2 := constructorDenote string) |
267 (fun _ pc x r => printName pc ++ "(" ++ printNonrec pc x | 272 (fun _ pc x r => printName pc ++ "(" ++ printNonrec pc x |
268 ++ foldr (fun s acc => ", " ++ s ++ acc) ")" r) pr). | 273 ++ foldr (fun s acc => ", " ++ s ++ acc) ")" r) pr). |
273 Eval compute in print HNil Empty_set_fix. | 278 Eval compute in print HNil Empty_set_fix. |
274 (** %\vspace{-.15in}% [[ | 279 (** %\vspace{-.15in}% [[ |
275 = fun emp : Empty_set => match emp return string with | 280 = fun emp : Empty_set => match emp return string with |
276 end | 281 end |
277 : Empty_set -> string | 282 : Empty_set -> string |
278 ]] *) | 283 ]] |
284 *) | |
279 | 285 |
280 Eval compute in print (^ "tt" (fun _ => "") ::: HNil) unit_fix. | 286 Eval compute in print (^ "tt" (fun _ => "") ::: HNil) unit_fix. |
281 (** %\vspace{-.15in}% [[ | 287 (** %\vspace{-.15in}% [[ |
282 = fun _ : unit => "tt()" | 288 = fun _ : unit => "tt()" |
283 : unit -> string | 289 : unit -> string |
284 ]] *) | 290 ]] |
291 *) | |
285 | 292 |
286 Eval compute in print (^ "true" (fun _ => "") | 293 Eval compute in print (^ "true" (fun _ => "") |
287 ::: ^ "false" (fun _ => "") | 294 ::: ^ "false" (fun _ => "") |
288 ::: HNil) bool_fix. | 295 ::: HNil) bool_fix. |
289 (** %\vspace{-.15in}% [[ | 296 (** %\vspace{-.15in}% [[ |
290 = fun b : bool => if b then "true()" else "false()" | 297 = fun b : bool => if b then "true()" else "false()" |
291 : bool -> s | 298 : bool -> s |
292 ]] *) | 299 ]] |
300 *) | |
293 | 301 |
294 Definition print_nat := print (^ "O" (fun _ => "") | 302 Definition print_nat := print (^ "O" (fun _ => "") |
295 ::: ^ "S" (fun _ => "") | 303 ::: ^ "S" (fun _ => "") |
296 ::: HNil) nat_fix. | 304 ::: HNil) nat_fix. |
297 Eval cbv beta iota delta -[append] in print_nat. | 305 Eval cbv beta iota delta -[append] in print_nat. |
300 match n with | 308 match n with |
301 | 0%nat => "O" ++ "(" ++ "" ++ ")" | 309 | 0%nat => "O" ++ "(" ++ "" ++ ")" |
302 | S n' => "S" ++ "(" ++ "" ++ ", " ++ F n' ++ ")" | 310 | S n' => "S" ++ "(" ++ "" ++ ", " ++ F n' ++ ")" |
303 end | 311 end |
304 : nat -> string | 312 : nat -> string |
305 ]] *) | 313 ]] |
314 *) | |
306 | 315 |
307 Eval simpl in print_nat 0. | 316 Eval simpl in print_nat 0. |
308 (** %\vspace{-.15in}% [[ | 317 (** %\vspace{-.15in}% [[ |
309 = "O()" | 318 = "O()" |
310 : string | 319 : string |
311 ]] *) | 320 ]] |
321 *) | |
312 | 322 |
313 Eval simpl in print_nat 1. | 323 Eval simpl in print_nat 1. |
314 (** %\vspace{-.15in}% [[ | 324 (** %\vspace{-.15in}% [[ |
315 = "S(, O())" | 325 = "S(, O())" |
316 : string | 326 : string |
317 ]] *) | 327 ]] |
328 *) | |
318 | 329 |
319 Eval simpl in print_nat 2. | 330 Eval simpl in print_nat 2. |
320 (** %\vspace{-.15in}% [[ | 331 (** %\vspace{-.15in}% [[ |
321 = "S(, S(, O()))" | 332 = "S(, S(, O()))" |
322 : string | 333 : string |
323 ]] *) | 334 ]] |
335 *) | |
324 | 336 |
325 Eval cbv beta iota delta -[append] in fun A (pr : A -> string) => | 337 Eval cbv beta iota delta -[append] in fun A (pr : A -> string) => |
326 print (^ "nil" (fun _ => "") | 338 print (^ "nil" (fun _ => "") |
327 ::: ^ "cons" pr | 339 ::: ^ "cons" pr |
328 ::: HNil) (@list_fix A). | 340 ::: HNil) (@list_fix A). |
332 match ls with | 344 match ls with |
333 | nil => "nil" ++ "(" ++ "" ++ ")" | 345 | nil => "nil" ++ "(" ++ "" ++ ")" |
334 | x :: ls' => "cons" ++ "(" ++ pr x ++ ", " ++ F ls' ++ ")" | 346 | x :: ls' => "cons" ++ "(" ++ pr x ++ ", " ++ F ls' ++ ")" |
335 end | 347 end |
336 : forall A : Type, (A -> string) -> list A -> string | 348 : forall A : Type, (A -> string) -> list A -> string |
337 ]] *) | 349 ]] |
350 *) | |
338 | 351 |
339 Eval cbv beta iota delta -[append] in fun A (pr : A -> string) => | 352 Eval cbv beta iota delta -[append] in fun A (pr : A -> string) => |
340 print (^ "Leaf" pr | 353 print (^ "Leaf" pr |
341 ::: ^ "Node" (fun _ => "") | 354 ::: ^ "Node" (fun _ => "") |
342 ::: HNil) (@tree_fix A). | 355 ::: HNil) (@tree_fix A). |
347 | Leaf x => "Leaf" ++ "(" ++ pr x ++ ")" | 360 | Leaf x => "Leaf" ++ "(" ++ pr x ++ ")" |
348 | Node t1 t2 => | 361 | Node t1 t2 => |
349 "Node" ++ "(" ++ "" ++ ", " ++ F t1 ++ ", " ++ F t2 ++ ")" | 362 "Node" ++ "(" ++ "" ++ ", " ++ F t1 ++ ", " ++ F t2 ++ ")" |
350 end | 363 end |
351 : forall A : Type, (A -> string) -> tree A -> string | 364 : forall A : Type, (A -> string) -> tree A -> string |
352 ]] *) | 365 ]] |
366 *) | |
353 | 367 |
354 | 368 |
355 (** ** Mapping *) | 369 (** ** Mapping *) |
356 | 370 |
357 (* EX: Define a generic [map] function. *) | 371 (* EX: Define a generic [map] function. *) |
369 (** %\vspace{-.15in}% [[ | 383 (** %\vspace{-.15in}% [[ |
370 = fun (_ : Empty_set -> Empty_set) (emp : Empty_set) => | 384 = fun (_ : Empty_set -> Empty_set) (emp : Empty_set) => |
371 match emp return Empty_set with | 385 match emp return Empty_set with |
372 end | 386 end |
373 : (Empty_set -> Empty_set) -> Empty_set -> Empty_set | 387 : (Empty_set -> Empty_set) -> Empty_set -> Empty_set |
374 ]] *) | 388 ]] |
389 *) | |
375 | 390 |
376 Eval compute in map unit_den unit_fix. | 391 Eval compute in map unit_den unit_fix. |
377 (** %\vspace{-.15in}% [[ | 392 (** %\vspace{-.15in}% [[ |
378 = fun (f : unit -> unit) (_ : unit) => f tt | 393 = fun (f : unit -> unit) (_ : unit) => f tt |
379 : (unit -> unit) -> unit -> unit | 394 : (unit -> unit) -> unit -> unit |
380 ]] *) | 395 ]] |
396 *) | |
381 | 397 |
382 Eval compute in map bool_den bool_fix. | 398 Eval compute in map bool_den bool_fix. |
383 (** %\vspace{-.15in}% [[ | 399 (** %\vspace{-.15in}% [[ |
384 = fun (f : bool -> bool) (b : bool) => if b then f true else f false | 400 = fun (f : bool -> bool) (b : bool) => if b then f true else f false |
385 : (bool -> bool) -> bool -> bool | 401 : (bool -> bool) -> bool -> bool |
386 ]] *) | 402 ]] |
403 *) | |
387 | 404 |
388 Eval compute in map nat_den nat_fix. | 405 Eval compute in map nat_den nat_fix. |
389 (** %\vspace{-.15in}% [[ | 406 (** %\vspace{-.15in}% [[ |
390 = fun f : nat -> nat => | 407 = fun f : nat -> nat => |
391 fix F (n : nat) : nat := | 408 fix F (n : nat) : nat := |
392 match n with | 409 match n with |
393 | 0%nat => f 0%nat | 410 | 0%nat => f 0%nat |
394 | S n' => f (S (F n')) | 411 | S n' => f (S (F n')) |
395 end | 412 end |
396 : (nat -> nat) -> nat -> nat | 413 : (nat -> nat) -> nat -> nat |
397 ]] *) | 414 ]] |
415 *) | |
398 | 416 |
399 Eval compute in fun A => map (list_den A) (@list_fix A). | 417 Eval compute in fun A => map (list_den A) (@list_fix A). |
400 (** %\vspace{-.15in}% [[ | 418 (** %\vspace{-.15in}% [[ |
401 = fun (A : Type) (f : list A -> list A) => | 419 = fun (A : Type) (f : list A -> list A) => |
402 fix F (ls : list A) : list A := | 420 fix F (ls : list A) : list A := |
403 match ls with | 421 match ls with |
404 | nil => f nil | 422 | nil => f nil |
405 | x :: ls' => f (x :: F ls') | 423 | x :: ls' => f (x :: F ls') |
406 end | 424 end |
407 : forall A : Type, (list A -> list A) -> list A -> list A | 425 : forall A : Type, (list A -> list A) -> list A -> list A |
408 ]] *) | 426 ]] |
427 *) | |
409 | 428 |
410 Eval compute in fun A => map (tree_den A) (@tree_fix A). | 429 Eval compute in fun A => map (tree_den A) (@tree_fix A). |
411 (** %\vspace{-.15in}% [[ | 430 (** %\vspace{-.15in}% [[ |
412 = fun (A : Type) (f : tree A -> tree A) => | 431 = fun (A : Type) (f : tree A -> tree A) => |
413 fix F (t : tree A) : tree A := | 432 fix F (t : tree A) : tree A := |
414 match t with | 433 match t with |
415 | Leaf x => f (Leaf x) | 434 | Leaf x => f (Leaf x) |
416 | Node t1 t2 => f (Node (F t1) (F t2)) | 435 | Node t1 t2 => f (Node (F t1) (F t2)) |
417 end | 436 end |
418 : forall A : Type, (tree A -> tree A) -> tree A -> tree A | 437 : forall A : Type, (tree A -> tree A) -> tree A -> tree A |
419 ]] *) | 438 ]] |
439 *) | |
420 | 440 |
421 Definition map_nat := map nat_den nat_fix. | 441 Definition map_nat := map nat_den nat_fix. |
422 Eval simpl in map_nat S 0. | 442 Eval simpl in map_nat S 0. |
423 (** %\vspace{-.15in}% [[ | 443 (** %\vspace{-.15in}% [[ |
424 = 1%nat | 444 = 1%nat |
425 : nat | 445 : nat |
426 ]] *) | 446 ]] |
447 *) | |
427 | 448 |
428 Eval simpl in map_nat S 1. | 449 Eval simpl in map_nat S 1. |
429 (** %\vspace{-.15in}% [[ | 450 (** %\vspace{-.15in}% [[ |
430 = 3%nat | 451 = 3%nat |
431 : nat | 452 : nat |
432 ]] *) | 453 ]] |
454 *) | |
433 | 455 |
434 Eval simpl in map_nat S 2. | 456 Eval simpl in map_nat S 2. |
435 (** %\vspace{-.15in}% [[ | 457 (** %\vspace{-.15in}% [[ |
436 = 5%nat | 458 = 5%nat |
437 : nat | 459 : nat |
438 ]] *) | 460 ]] |
461 *) | |
439 | 462 |
440 | 463 |
441 (** * Proving Theorems about Recursive Definitions *) | 464 (** * Proving Theorems about Recursive Definitions *) |
442 | 465 |
443 (** We would like to be able to prove theorems about our generic functions. To do so, we need to establish additional well-formedness properties that must hold of pieces of evidence. *) | 466 (** We would like to be able to prove theorems about our generic functions. To do so, we need to establish additional well-formedness properties that must hold of pieces of evidence. *) |
521 fx nat | 544 fx nat |
522 (hmake | 545 (hmake |
523 (fun (x : constructor) (_ : nonrecursive x) | 546 (fun (x : constructor) (_ : nonrecursive x) |
524 (r : ilist nat (recursive x)) => foldr plus 1%nat r) dt) t > 0) v | 547 (r : ilist nat (recursive x)) => foldr plus 1%nat r) dt) t > 0) v |
525 | 548 |
526 ]] *) | 549 ]] |
550 *) | |
527 | 551 |
528 apply dok; crush. | 552 apply dok; crush. |
529 (** [[ | 553 (** [[ |
530 H : forall i : fin (recursive c), | 554 H : forall i : fin (recursive c), |
531 fx nat | 555 fx nat |