Listing 4: Letting prototype classes provide their own traits by default

template<typename Proto>
class prototype_traits
{
public:
  typedef Proto::stored_type 
    stored_type;
  typedef Proto::cloning_result_type 
    cloning_result_type;
  
  enum
  { destroy_prototypes = Proto::destroy_prototypes, };

  static cloning_result_type Clone(const stored_type& p)
  { return Proto::Clone(p); }

  static void Destroy(const stored_type& p)
  { Proto::Destroy(p); }
};

class Gadget
{
public:
  typedef Gadget* stored_type;
  typedef Gadget cloning_result_type;
  
  enum { destroy_prototypes = true, };

  static cloning_result_type Clone(stored_type p)
  { return p->Clone(); }

  static void Destroy(stored_type p)
  { delete p; }

  // ...
};
— End of Listing —