RIS.nominalsetoid: Nominal sets up-to equivalence.


Require Import tools atoms PeanoNat Nat bijection.

Set Implicit Arguments.

Definitions

Section s.
We fix a decidable set of atoms.
  Context {atom : Set}{A : Atom atom}.

We use the notation π x for the group action of a nominal setoid, and x for its support.
  Class ActionSetoid (X : Set) := actoid : perm X X.
  Infix " ⊙ " := actoid (at level 50).
  Class SupportSetoid {A : Atom atom} (X : Set) := suppoid : X list atom.
  Notation " ⌈ x ⌉ " := (suppoid x).

A nominal setoid is a set X equipped with a relation , an action and a support function _ satisfying the following axioms:
  Class NominalSetoid (X : Set) (equiv : SemEquiv X) (act : ActionSetoid X)
        (supp : SupportSetoid X) :=
    {
      
is an equivalence relation;
      eq_equivalence :> Equivalence sequiv;
     
equivalent elements have equivalent support : if xy, then a∈⌈x a∈⌈y;
      eq_support :> Proper (sequiv ==> (@equivalent atom)) suppoid;
      
the action in compatible with the equivalence relation ;
      eq_act_proper π :> Proper (sequiv ==> sequiv) (actoid π);
      
the remaining axioms are the same as for nominal sets, except that equality of elements in X has been substituted with .
      action_invariant_eq : (x : X) π, (π x = x) (π x) x;
      support_action_eq : x π, π x πx;
      action_compose_eq : x π π', π (π' x) (π++π') x
    }.


The following observations are straightforward to check directly from the axioms we just listed.
  Remark actoid_pinv_p {X : Set} `{NominalSetoid X}:
     π x, π (π x) x.

  Remark actoid_p_pinv {X : Set} `{NominalSetoid X}:
     π x, π (π x) x.

Permutations that are equivalent as functions yield the same action (even if they are syntactically different): if for every atom a we have π a = π' a and if xy, then π⊙x≃π'⊙y.
  Global Instance eq_act {X : Set} `{NominalSetoid X} :
    Proper (sequiv ==> sequiv ==> sequiv) actoid.

  Lemma minimal_support_eq {X: Set} `{NominalSetoid X} l x :
    ( π, ( a, a l π a = a) π x x) x l.

  Remark ActionSetoid_ext_In {X:Set} `{NominalSetoid X}:
     π π' x, ( a, a x π a = π' a) π x π' x.

End s.


Lifting the structure to lists

Section list.
Let us fix a nominal setoid S over a set of atoms Atom.
  Context {atom : Set}{A: Atom atom}.
  Context {S : Set} {eqS : SemEquiv S} {actS : ActionSetoid _ A S}
          {suppS : SupportSetoid _ A S}.
  Context {N: NominalSetoid A S}.

We define the action of π on a list by apply π pointwise.
  Global Instance actoid_lists : ActionSetoid _ A (list S):=
    fun π lmap (fun xπx) l.


To compute the support of a list, we compute the support of each element, take the union of those, and remove duplicates.
  Global Instance SupportSetoidList : SupportSetoid _ A (list S) :=
    fun l{{flat_map suppoid l}}.

Two lists are equivalent if they have the same length, and if their elements are pointwise equivalent. For instance if l=l1...ln and m=m1...mn, then lm if and only if 1<=in, limi.
  Fixpoint semeq_list (l1 l2 : list S) :=
    match (l1,l2) with
    | ([],[])True
    | (a::l1,b::l2)(ab) semeq_list l1 l2
    | (_::_,[]) | ([],_::_)False
    end.

  Instance SemEquiv_listS : SemEquiv (list S) := semeq_list.


It is a simple matter to check that the operations we have defined indeed define a nominal setoid structure over list S.
  Global Instance NominalSetoid_list : NominalSetoid A (list S).


End list.