Up to Main Index                              Up to Journal for July, 2012

                      JOURNAL FOR MONDAY 9TH JULY, 2012
______________________________________________________________________________

SUBJECT: I feel a disturbance in my code...
   DATE: Mon Jul  9 22:02:49 BST 2012

Didn't get much time for coding this weekend, however I did manage to watch
some more Google I/O 2012 videos and catchup with the golang go nuts mailing
list[1].

Ever since then I had an uneasy feeling that something wasn't quite as it
should be with the code for my prototype. This evening I made some
experimental changes and had a nice surprise!

When composing object via embedding I was using something like:


  type Item struct {
    *thing.Thing
    weight units.Weight
  }


This involves two structs - one for Item and a pointer to a Thing struct.
Everything works as expected and there is nothing wrong with it. But! It looks
like there is a better way to do this:


  type Item struct {
    thing.Thing
    weight units.Weight
  }


A simple change - Thing is now embedded directly into Item without a pointer
and we only have a single struct.

This may not seem that important. However we now have just one struct instead
of two tied together via a pointer. This lowers memory usage AND seems to make
the garbage collector much happier. All of the debugging using finalizers and
explicit setting of pointers to nil etc has all just gone away.

So I've modified all of the structs and am currently running tests on the
modified code.

However I think I can still do better. Each 'thing' is created using a New()
function. For example Thing and Item have:


  func New(name string, aliases []string, description string) *Thing {

    t := &Thing{
      name:        name,
      aliases:     make([]string, len(aliases)),
      description: description,
      uniqueId:    <-Next,
      mutex:       make(chan bool, 1),
    }

    for i, a := range aliases {
      t.aliases[i] = strings.ToUpper(strings.TrimSpace(a))
    }

    log.Printf("Thing %d created: %s\n", t.uniqueId, t.name)

    return t
  }


  New(name string, aliases []string, description string,
                                        weight units.Weight) *Item {
    return &Item{
      Thing:  *thing.New(name, aliases, description),
      weight: weight,
    }
  }


What happens here is that Thing is Embedded into Item. To do so Item calls
thing.New() to create a new *Thing the embedding then seems to create a
copy[2] of the Thing referenced and the Thing is then finalised because it's
no longer referenced! So instead of returning a reference to the new Thing I
could possibly allocate the data directly into the Item and save another
object creation - which also saves on allocation and garbage collection. Is
this was made the garbage collector happier?

So a little more investigating to do but it all looks good to me ;)

--
Diddymus

  [1] Go users mailing list: https://groups.google.com/group/golang-nuts
  [2] I think the copy is done for the allocation into the Item struct?


  Up to Main Index                              Up to Journal for July, 2012