No need to make it work with object.value
syntax. It’s not very Julian anyway. Personally, I hide almost all object.value
calls behind a getter as it makes refactors easier later. Use a global and have a accessor function that gets/sets it. Here’s an example:
const Type1_goodness = Ref(3.0) # use Ref to make it mutable
struct Type1
bigness::Float64
end
struct Type2
bigness::Float64
coolness::Float64
goodness::Float64
end
bigness(x::Type1) = x.bigness
coolness(x::Type1) = 2.0 # hard-coded, but could also reference a global const if it makes sense
goodness(x::Type1) = Type1_goodness[] # access the global const Ref
setgoodness!(x::Type1, val) = Type1_goodness[] = val # set the global
bigness(x::Type2) = x.bigness
coolness(x::Type2) = x.coolness
goodness(x::Type2) = x.goodness
# cannot setgoodness!(::Type2, val) because it is not mutable
# but you could make it construct a new Type2 with the new goodness and *not* mutate the original, depending on your needs
coolness(Type1(4.0)) # 2.0 - not a field but we can still get the value
coolness(Type2(5.0, 6.0, 7.0)) # 6.0 - read the field
goodness(Type1(4.0)) # 3.0 - the original default value
setgoodness!(Type1(4.0), 9.0) # 9.0 - we've set the value for all Type1 now
goodness(Type1(8.0)) # 9.0 - read the shared value