(* Syntaxe: object .. end peut dénoter un objet ou une classe.
 *
 * Une classe n'est pas un objet et un type de classe n'est pas un type
 * dans la même catégorie que, par exemple, int -> int ou < a : int >.
 *
 * Le type d'un objet ne mentionne que ses méthodes publiques.
 * Le type d'une classe mentionne variables d'instances et méthodes
 * privées, voire abstraites dans le cas d'une classe abstraite. *)

let o : < a : int > = object method a = 1 end
let o = (object method a = 1 end : < a : int >)

class c : object method a : int end = object
  method a = 1
end
class c' = (object
  method a = 1
end : object method a : int end)


(* L'héritage ne concerne que les classes. *)
class d = object
  inherit c as super         (* inherit o est impossible *)
  method a = super#a+1       (* même type que dans c *)
end


(* Le "sous-typage" est assez limité sur les classes.
 * On ne peut cacher une méthode publique comme on le fait sur
 * les objets. *)
class e : object method a : int end = object
  method a = 1
  (* method b = 2 *)
end