[LRUG] Comparable Null Objects

Andy bibenu at virginmedia.com
Thu Jul 16 12:00:30 PDT 2015


On reading yesterday's mails on the subject I planned today to write a 
mail about exactly this:

 > Make a new kind of object whose sole responsibility is the (not 
entirely trivial) logic of ordering things by date when some of them may 
not have dates.

But you've saved me the job and steered the whole conversation in (what 
looks to me like) the right direction.  :)  The problem with with all 
the solutions that focus only on date is that they miss out explaining 
that extra requirement implicit in the first post: that we have extra 
logic that determines where an undated thing should appear in the sorted 
list of things. If you don't make that extra logic explicit in code then 
it's highly likely that you'll have code that needs to be explained 
further, like in comments or in tests/specs.

Andy



On 16/07/2015 10:27, tom at codon.com wrote:
> On 15 Jul 2015, at 22:44, Duncan Stuart <dgmstuart at gmail.com> wrote:
>> Do you think I'm applying the idea incorrectly or inappropriately?
> FWIW I do think you’re misapplying the idea, for the simple reason that it doesn’t really help here. The null object pattern is helpful when there’s some protocol that can sensibly be replicated by the null object; your `def to_s; 'Unknown'; end` is a good example. But there’s no easy way for a null object to conform to the expectations of Date#<=>, so it’s not going to make things better.
>
> My advice would be to avoid trickery entirely and take a different piece of advice from Sandi’s talk: extract a role. Make a new kind of object whose sole responsibility is the (not entirely trivial) logic of ordering things by date when some of them may not have dates.
>
> There are a few ways of doing this, but one example might be to have a DateRank class:
>
> DateRank = Struct.new(:maybe_date) do
>    def <=>(other)
>      if maybe_date.nil?
>        1
>      elsif other.maybe_date.nil?
>        -1
>      else
>        maybe_date <=> other.maybe_date
>      end
>    end
> end
>
> (Substitute `case maybe_date … when NoExpectedDate` for `if nil?` if you choose to use null objects for other reasons — the two ideas are orthogonal.)
>
> And then you can do `events.sort_by(&DateRank.method(:new))` or whatever.
>
> I talk about this idea a bit in http://codon.com/a-lever-for-the-mind#poker if you’re interested.
>
> Cheers,
> -Tom
> _______________________________________________
> Chat mailing list
> Chat at lists.lrug.org
> Archives: http://lists.lrug.org/pipermail/chat-lrug.org
> Manage your subscription: http://lists.lrug.org/options.cgi/chat-lrug.org
> List info: http://lists.lrug.org/listinfo.cgi/chat-lrug.org




More information about the Chat mailing list