Difference between revisions of "Coding patterns"

From Liberty Eiffel Wiki
Jump to navigation Jump to search
(first coding patterns)
 
m
 
(8 intermediate revisions by 3 users not shown)
Line 1: Line 1:
  +
[[Category: Design Pattern]]
 
Coding Patterns are a group of useful insights on how to implement things.
 
Coding Patterns are a group of useful insights on how to implement things.
   
 
== Singleton ==
 
== Singleton ==
To me, the best way to achieve a singleton is almost the standard Eiffel pattern: a singleton holder with a once function, and the pattern itself with a creation clause limitted to the singleton holder. An interesting thing is that I usually make the singleton holder '''expanded''', this way I don't have to make it a singleton too ;-)
+
To me, the best way to achieve a singleton is almost the standard Eiffel pattern: a singleton holder with a once function, and the pattern itself with a creation clause limited to the singleton holder. An interesting thing is that I usually make the singleton holder '''expanded''', this way I don't have to make it a singleton too ;-)
   
 
expanded class SINGLETON_HOLDER
 
expanded class SINGLETON_HOLDER
Line 20: Line 21:
 
end
 
end
 
end
 
end
  +
  +
The other solution is the classic holder you either inherit or, preferably, insert.
  +
  +
Which do you prefer: expanded or insert?
   
 
== Multi-typed ==
 
== Multi-typed ==
Line 67: Line 72:
 
You can see such a pattern in action in <tt>[http://gforge.inria.fr/plugins/scmsvn/viewcvs.php/trunk/lib/storage/collection/linked_list.e?root=smarteiffel&view=markup LINKED_LIST]</tt> where it is used to collect unused cells (look at ''common_free_nodes'' which contains <tt>[http://gforge.inria.fr/plugins/scmsvn/viewcvs.php/trunk/lib/storage/internal/any_linked_list_node.e?root=smarteiffel&view=auto ANY_LINKED_LIST_NODE]</tt> of which <tt>[http://gforge.inria.fr/plugins/scmsvn/viewcvs.php/trunk/lib/storage/internal/linked_list_node.e?root=smarteiffel&view=auto LINKED_LIST_NODE]</tt> is a conformant heir).
 
You can see such a pattern in action in <tt>[http://gforge.inria.fr/plugins/scmsvn/viewcvs.php/trunk/lib/storage/collection/linked_list.e?root=smarteiffel&view=markup LINKED_LIST]</tt> where it is used to collect unused cells (look at ''common_free_nodes'' which contains <tt>[http://gforge.inria.fr/plugins/scmsvn/viewcvs.php/trunk/lib/storage/internal/any_linked_list_node.e?root=smarteiffel&view=auto ANY_LINKED_LIST_NODE]</tt> of which <tt>[http://gforge.inria.fr/plugins/scmsvn/viewcvs.php/trunk/lib/storage/internal/linked_list_node.e?root=smarteiffel&view=auto LINKED_LIST_NODE]</tt> is a conformant heir).
   
Another example is <tt>[http://gforge.inria.fr/plugins/scmsvn/viewcvs.php/trunk/lib/kernel/internal/internals.e?root=smarteiffel&view=auto INTERNALS]</tt>.
+
Another example is <tt>INTERNALS[https://github.com/LibertyEiffel/Liberty/blob/master/src/lib/kernel/internal/internals.e]</tt>.

Latest revision as of 12:11, 5 July 2024

Coding Patterns are a group of useful insights on how to implement things.

Singleton

To me, the best way to achieve a singleton is almost the standard Eiffel pattern: a singleton holder with a once function, and the pattern itself with a creation clause limited to the singleton holder. An interesting thing is that I usually make the singleton holder expanded, this way I don't have to make it a singleton too ;-)

expanded class SINGLETON_HOLDER
feature {ANY}
   singleton: SINGLETON is
      once
         create Result.make
      end
end
class SINGLETON is
create {SINGLETON_HOLDER}
   make
feature {}
   make is
      do
      end
end

The other solution is the classic holder you either inherit or, preferably, insert.

Which do you prefer: expanded or insert?

Multi-typed

It is becoming quite usual to have a few classes that want to "talk" to "any" class. But you cannot use the ANY class since most classes insert it and anyway it could not hold expanded classes. In that case you use a generic class, which can hold anything that inserts its generic constraint.

An emerging coding pattern is the following:

deferred class TALKABLE
feature {ANY}
   talk is
      do
      end
end
deferred class UNTYPED_TALKER
feature {ANY}
   make_it_talk is
      do
      end
end
class TYPED_TALK[O_->TALKABLE]
inherit
   UNTYPED_TALK

create {ANY}
   set_item

feature {ANY}
   item: O_

   set_item (a_item: like item) is
      require
         a_item /= Void
      do
         item := a_item
      ensure
         item = a_item
      end

   make_it_talk is
      do
         item.talk
      end
end

You can see such a pattern in action in LINKED_LIST where it is used to collect unused cells (look at common_free_nodes which contains ANY_LINKED_LIST_NODE of which LINKED_LIST_NODE is a conformant heir).

Another example is INTERNALS[1].