I noticed this code in Pkg
, and the the utility of the copy
function inside the struct block eludes me even though it’s commented:
struct VersionSet
intervals::Vector{VersionInterval}
VersionSet(intervals::Vector{VersionInterval}) = new(normalize!(intervals))
# copy is defined inside the struct block to call `new` directly
# without going through `normalize!`
Base.copy(vset::VersionSet) = new(copy(vset.intervals))
end
How is copy
ever used? More generally, what is the scope of functions defined in the struct block?
It doesn’t define a new function so there isn’t really any scope to talk about (except the one of the original function).
To clarify Kristoffer’s comment, that line of code extends the same Base.copy
as if it were defined outside the struct
. The reason it is defined inside is that it calls new
, which is only accessible inside the scope of the struct
definition.
The “function” new
is ever only accessible from inside a struct
definition, and directly constructs an instance of VersionSet
, avoiding the constructor (which is defined here on the third line). That constructor does some work to preserve an invariant across all instances of VersionSet
, but since the purpose of copy
is to duplicate an existing pre-constructed VersionSet
, we know that work can be avoided.
With a struct like this, where the inner constructor always does some work, the only way forward is to call new
directly, which you can only do from inside the scope of a struct
definition, which is why the extension of Base.copy
ended up being put there – to have access to new
.
9 Likes
Ah I see now, thanks for the great explanation!
1 Like