comparison src/Firstorder.v @ 156:be15ed0a8bae

De Bruijn
author Adam Chlipala <adamc@hcoop.net>
date Sun, 02 Nov 2008 13:51:51 -0500
parents b31ca896f211
children 2022e3f2aa26
comparison
equal deleted inserted replaced
155:b31ca896f211 156:be15ed0a8bae
6 * The license text is available at: 6 * The license text is available at:
7 * http://creativecommons.org/licenses/by-nc-nd/3.0/ 7 * http://creativecommons.org/licenses/by-nc-nd/3.0/
8 *) 8 *)
9 9
10 (* begin hide *) 10 (* begin hide *)
11 Require Import List String. 11 Require Import Arith String List.
12 12
13 Require Import Tactics. 13 Require Import Tactics.
14 14
15 Set Implicit Arguments. 15 Set Implicit Arguments.
16 (* end hide *) 16 (* end hide *)
339 -> nil |-e e' : t. 339 -> nil |-e e' : t.
340 intros; eapply preservation'; eauto. 340 intros; eapply preservation'; eauto.
341 Qed. 341 Qed.
342 342
343 End Concrete. 343 End Concrete.
344
345
346 (** * De Bruijn Indices *)
347
348 Module DeBruijn.
349
350 Definition var := nat.
351 Definition var_eq := eq_nat_dec.
352
353 Inductive exp : Set :=
354 | Const : bool -> exp
355 | Var : var -> exp
356 | App : exp -> exp -> exp
357 | Abs : exp -> exp.
358
359 Inductive type : Set :=
360 | Bool : type
361 | Arrow : type -> type -> type.
362
363 Infix "-->" := Arrow (right associativity, at level 60).
364
365 Definition ctx := list type.
366
367 Reserved Notation "G |-v x : t" (no associativity, at level 90, x at next level).
368
369 Inductive lookup : ctx -> var -> type -> Prop :=
370 | First : forall t G,
371 t :: G |-v O : t
372 | Next : forall x t t' G,
373 G |-v x : t
374 -> t' :: G |-v S x : t
375
376 where "G |-v x : t" := (lookup G x t).
377
378 Hint Constructors lookup.
379
380 Reserved Notation "G |-e e : t" (no associativity, at level 90, e at next level).
381
382 Inductive hasType : ctx -> exp -> type -> Prop :=
383 | TConst : forall G b,
384 G |-e Const b : Bool
385 | TVar : forall G v t,
386 G |-v v : t
387 -> G |-e Var v : t
388 | TApp : forall G e1 e2 dom ran,
389 G |-e e1 : dom --> ran
390 -> G |-e e2 : dom
391 -> G |-e App e1 e2 : ran
392 | TAbs : forall G e' dom ran,
393 dom :: G |-e e' : ran
394 -> G |-e Abs e' : dom --> ran
395
396 where "G |-e e : t" := (hasType G e t).
397
398 Hint Constructors hasType.
399
400 Lemma weaken_lookup : forall G' v t G,
401 G |-v v : t
402 -> G ++ G' |-v v : t.
403 induction 1; crush.
404 Qed.
405
406 Hint Resolve weaken_lookup.
407
408 Theorem weaken_hasType' : forall G' G e t,
409 G |-e e : t
410 -> G ++ G' |-e e : t.
411 induction 1; crush; eauto.
412 Qed.
413
414 Theorem weaken_hasType : forall e t,
415 nil |-e e : t
416 -> forall G', G' |-e e : t.
417 intros; change G' with (nil ++ G');
418 eapply weaken_hasType'; eauto.
419 Qed.
420
421 Theorem weaken_hasType_closed : forall e t,
422 nil |-e e : t
423 -> forall G, G |-e e : t.
424 intros; rewrite (app_nil_end G); apply weaken_hasType; auto.
425 Qed.
426
427 Theorem weaken_hasType1 : forall e t,
428 nil |-e e : t
429 -> forall t', t' :: nil |-e e : t.
430 intros; change (t' :: nil) with ((t' :: nil) ++ nil);
431 apply weaken_hasType; crush.
432 Qed.
433
434 Hint Resolve weaken_hasType_closed weaken_hasType1.
435
436 Section subst.
437 Variable e1 : exp.
438
439 Fixpoint subst (x : var) (e2 : exp) : exp :=
440 match e2 with
441 | Const b => Const b
442 | Var x' =>
443 if var_eq x' x
444 then e1
445 else Var x'
446 | App e1 e2 => App (subst x e1) (subst x e2)
447 | Abs e' => Abs (subst (S x) e')
448 end.
449
450 Variable xt : type.
451
452 Lemma subst_eq : forall t G1,
453 G1 ++ xt :: nil |-v length G1 : t
454 -> t = xt.
455 induction G1; inversion 1; crush.
456 Qed.
457
458 Implicit Arguments subst_eq [t G1].
459
460 Lemma subst_eq' : forall t G1 x,
461 G1 ++ xt :: nil |-v x : t
462 -> x <> length G1
463 -> G1 |-v x : t.
464 induction G1; inversion 1; crush;
465 match goal with
466 | [ H : nil |-v _ : _ |- _ ] => inversion H
467 end.
468 Qed.
469
470 Hint Resolve subst_eq'.
471
472 Lemma subst_neq : forall v t G1,
473 G1 ++ xt :: nil |-v v : t
474 -> v <> length G1
475 -> G1 |-e Var v : t.
476 induction G1; inversion 1; crush.
477 Qed.
478
479 Hint Resolve subst_neq.
480
481 Hypothesis Ht' : nil |-e e1 : xt.
482
483 Lemma hasType_push : forall dom G1 e' ran,
484 dom :: G1 |-e subst (length (dom :: G1)) e' : ran
485 -> dom :: G1 |-e subst (S (length G1)) e' : ran.
486 trivial.
487 Qed.
488
489 Hint Resolve hasType_push.
490
491 Theorem subst_hasType : forall G e2 t,
492 G |-e e2 : t
493 -> forall G1, G = G1 ++ xt :: nil
494 -> G1 |-e subst (length G1) e2 : t.
495 induction 1; crush;
496 try match goal with
497 | [ |- context[if ?E then _ else _] ] => destruct E
498 end; crush; eauto 6;
499 try match goal with
500 | [ H : _ |-v _ : _ |- _ ] =>
501 rewrite (subst_eq H)
502 end; crush.
503 Qed.
504
505 Theorem subst_hasType_closed : forall e2 t,
506 xt :: nil |-e e2 : t
507 -> nil |-e subst O e2 : t.
508 intros; change O with (length (@nil type)); eapply subst_hasType; eauto.
509 Qed.
510 End subst.
511
512 Hint Resolve subst_hasType_closed.
513
514 Notation "[ x ~> e1 ] e2" := (subst e1 x e2) (no associativity, at level 80).
515
516 Inductive val : exp -> Prop :=
517 | VConst : forall b, val (Const b)
518 | VAbs : forall e, val (Abs e).
519
520 Hint Constructors val.
521
522 Reserved Notation "e1 ==> e2" (no associativity, at level 90).
523
524 Inductive step : exp -> exp -> Prop :=
525 | Beta : forall e1 e2,
526 App (Abs e1) e2 ==> [O ~> e2] e1
527 | Cong1 : forall e1 e2 e1',
528 e1 ==> e1'
529 -> App e1 e2 ==> App e1' e2
530 | Cong2 : forall e1 e2 e2',
531 val e1
532 -> e2 ==> e2'
533 -> App e1 e2 ==> App e1 e2'
534
535 where "e1 ==> e2" := (step e1 e2).
536
537 Hint Constructors step.
538
539 Lemma progress' : forall G e t, G |-e e : t
540 -> G = nil
541 -> val e \/ exists e', e ==> e'.
542 induction 1; crush; eauto;
543 try match goal with
544 | [ H : _ |-e _ : _ --> _ |- _ ] => inversion H
545 end;
546 repeat match goal with
547 | [ H : _ |- _ ] => solve [ inversion H; crush; eauto ]
548 end.
549 Qed.
550
551 Theorem progress : forall e t, nil |-e e : t
552 -> val e \/ exists e', e ==> e'.
553 intros; eapply progress'; eauto.
554 Qed.
555
556 Lemma preservation' : forall G e t, G |-e e : t
557 -> G = nil
558 -> forall e', e ==> e'
559 -> nil |-e e' : t.
560 induction 1; inversion 2; crush; eauto;
561 match goal with
562 | [ H : _ |-e Abs _ : _ |- _ ] => inversion H
563 end; eauto.
564 Qed.
565
566 Theorem preservation : forall e t, nil |-e e : t
567 -> forall e', e ==> e'
568 -> nil |-e e' : t.
569 intros; eapply preservation'; eauto.
570 Qed.
571
572 End DeBruijn.