If you declare or allocate a variable of type bar
, you reserve and initialize to zero memory for both rd uint8
and foo foo_
. There is always one variable of type foo_
embedded in a variable of type bar
.
var b bar // declare b
If you declare or allocate a variable of type barP
, you reserve and initialize to zero memory for both rd uint8
and foo *foo_
. A zero value pointer is a nil
pointer. No variable of type foo_
is allocated; you must do that separately. There is either zero (foo == nil
) or one variable of type foo_
pointed to by a variable of type barP
. A variable of type barP
may point to the same variable of type foo_
as other variables of type barP
, sharing the same copy of the variable of type foo_
. A change to a shared copy is seen by all variables that point to it.
var bp barP // declare bp
bp.foo = new(foo_) // allocate bp.foo
Which one to use depends on the properties of type bar
versus type barP
. Which type more closely reflects the problem that you are trying to solve?
For example, consider this invoice problem. We always have a billing address; we are always going to ask for our money. However, we often ship to the billing address, but not always. If the shipping address is nil
, use the billing address. Otherwise, use a separate shipping address. We have two warehouses, and we always ship from one or the other. We can share the two warehouse locations. Since we don't send an invoice until the order is shipped from the warehouse, the warehouse location will never be nil
.
type address struct {
street string
city string
}
type warehouse struct {
address string
}
type invoice struct {
name string
billing address
shipping *address
warehouse *warehouse
}