Field | Value |
---|---|
DIP: | (number/id -- assigned by DIP Manager) |
Author: | Richard (Rikki) Andrew Cattermole [email protected] |
Implementation: | (links to implementation PR if any) |
Status: | Draft |
Some people feel that D's visibility is too coarse, this proposal introduces an additional visibility modifier that provides finer protection against unexpected mutation and access based upon sharing of the this
pointer in a declaration.
- Rationale
- Prior Work
- Description
- Breaking Changes and Deprecations
- Reference
- Copyright & License
- Reviews
Some D programmers feel that having D's private
to the module is far too loose, it prevents them from feeling like they have control over the granuality over the visibility of their symbols.
class Class {
void callable() {}
private void sideEffectsHere() {}
}
Class c = new Class;
c.callable(); // Okay
c.sideEffectsHere(); // Not okay
Having the ability to control visibility to finer grained and limit it to just that one type's methods would give confidence that they are not going to step on code that was not intended to be touched.
Many heated threads on adding private to the this
pointer exists on the D's News Group. These in the past have not lead to any language additions of this nature. Including the recent DIP ideas[0] thread for the introduction of this feature.
An example of a langauge that supports private to a class, struct or union is Java[1]. It includes a visibility modifier which acts as the default that prevents all accesses outside of the current above to the symbol, declaration.
An exception exists to this requirement is the permit clause in a class declaration. It allows the parent to specify children that may implement it and therefore have access to its private symbols.
The primary change this DIP introduces is the private to the this
pointer visibility modifier.
VisibilityAttribute:
private
+ private ( this )
This allows symbols that share a this
pointer within a declaration to access each other.
Nested classes, nested structs, nested unions, static methods, module constructors and unit tests do not support this, and therefore are not capable of having access to their parent types symbols with it.
struct Encapsulation {
private(this) int field;
unittest {
Encapsulation encapsulation;
assert(encapsulation); // Error: Cannot access Encapsulation's symbol `field` as it is private to the this pointer.
}
}
Nested classes, structs and unions can be declared as being private(this)
but their methods will not have access to the parent's private(this)
symbols.
class Parent {
private(this) int field;
private(this) class Nested {
void accessIt() {
field++; // Error: Parent classes symbols that are private to the this pointer cannot be accessed from nested children symbol's.
}
}
}
Class inheritance does not introduce access, use protected
instead.
class Parent {
private(this) int field;
}
class Child : Parent {
void accessIt() {
field++; // Error: symbol `field`` is private to this scope, and cannot be accessed in child class.
}
}
Like private
, private to the this pointer will also act as final
upon a class method.
There are no expected behavioral changes will be introduced by this proposal.
- [0] DIP ideas thread: Extending D's support for object-oriented design with private(this)
- [1] Java Specification 22
Copyright (c) 2024 by the D Language Foundation
Licensed under Creative Commons Zero 1.0
The DIP Manager will supplement this section with links to forum discsusionss and a summary of the formal assessment.