I previously talked about accessing the scope of an owning class from a class declared and instantiated within it. Latest post here: https://jack.dreamwidth.org/1017241.html
The possible approaches seem to be: the owned class has a pointer back to the owning class; or functions dealing with the owned class get an extra parameter to the owning class. Whether that's implemented manually, or automatically by the language, or somewhere between.
Thinking some more about this, various things occurred to me:
Java
I hadn't realised, but I learned Java and C# (and maybe other recent/managed languages) do this automatically, presumably implemented by the owned class automatically having a pointer to the owning class, and checked where its instantiated that it's only instantiated by an instance of the owning class.
I was naturally drawn to a "owning pointer is passed in alongside or as part of a this pointer" implementation as it seemed more conceptually correct. However, the actual benefit of this is a lot smaller in most languages other than rust. I first started thinking about these options in a rust example, where having a pointer to the owning class needed some fancy dancing, because rust prefers to keep tight limits on how many pointers to a class at once (ideally one only).
This hopefully makes memory management safer, and means you can usually move classes around in memory using a raw memcpy, because they don't usually have internal pointers to different parts of them. But most other languages don't even try to do that, just assume that a non-trivial class is fixed in place in memory (or moved only by a garbage collector that knows where all the pointers are).
Implementation
If you try to avoid having a permanent pointer back to the owning class, and if you ever need a pointer to the owned class (this is common if you use it as a callback), you need to accept your pointers would actually be a pair (or more) of pointers, to the owning class, and to the owned class. The owned pointers might be an offset rather than a complete pointer. That's clunky, but wouldn't necessarily take up that much space if the language supports it. You could do a similar thing for iterators, like pointers to members of a collection, rather than having a bare pointer that only makes sense if you already know what the collection is.
That seems a useful concept, but I'm not sure how useful it would be in practice.
The possible approaches seem to be: the owned class has a pointer back to the owning class; or functions dealing with the owned class get an extra parameter to the owning class. Whether that's implemented manually, or automatically by the language, or somewhere between.
Thinking some more about this, various things occurred to me:
Java
I hadn't realised, but I learned Java and C# (and maybe other recent/managed languages) do this automatically, presumably implemented by the owned class automatically having a pointer to the owning class, and checked where its instantiated that it's only instantiated by an instance of the owning class.
I was naturally drawn to a "owning pointer is passed in alongside or as part of a this pointer" implementation as it seemed more conceptually correct. However, the actual benefit of this is a lot smaller in most languages other than rust. I first started thinking about these options in a rust example, where having a pointer to the owning class needed some fancy dancing, because rust prefers to keep tight limits on how many pointers to a class at once (ideally one only).
This hopefully makes memory management safer, and means you can usually move classes around in memory using a raw memcpy, because they don't usually have internal pointers to different parts of them. But most other languages don't even try to do that, just assume that a non-trivial class is fixed in place in memory (or moved only by a garbage collector that knows where all the pointers are).
Implementation
If you try to avoid having a permanent pointer back to the owning class, and if you ever need a pointer to the owned class (this is common if you use it as a callback), you need to accept your pointers would actually be a pair (or more) of pointers, to the owning class, and to the owned class. The owned pointers might be an offset rather than a complete pointer. That's clunky, but wouldn't necessarily take up that much space if the language supports it. You could do a similar thing for iterators, like pointers to members of a collection, rather than having a bare pointer that only makes sense if you already know what the collection is.
That seems a useful concept, but I'm not sure how useful it would be in practice.