La chiave per "accedere ai membri annidati su livelli di astrazione più elevati" è usare "livelli di astrazione più alti". Non lo stai facendo qui: B
a F
sono referenziati direttamente all'interno di A
. Sono tutti strettamente accoppiati e non vi è alcuna astrazione in corso.
La soluzione è usare l'astrazione, quindi B
diventa:
class B
{
public int Value => ...
}
Come B
consegna Value
diventa un dettaglio di implementazione; cioè non è legato all'API ed è libero di cambiare senza influenzare il codice che chiama b.Value
. È astratto.
Quindi se B
a G
risiede in un assembly e A
risiede in un altro, puoi implementarlo come:
public class B
{
...
public int Value => c.d.e.f.g.Value;
}
o potresti eseguire ripetutamente la stessa astrazione, in modo che B
non abbia idea di dove C
ottiene Value
da ecc:
public class B
{
...
public int Value => c.Value;
}
Ogni livello di astrazione riduce l'accoppiamento, ma introduce ripetizione e complessità. Così come per tutto il resto della programmazione, devi raggiungere il giusto equilibrio ogni volta che usi questa tecnica e quel punto di equilibrio cambierà ogni volta.