Saya punya masalah dengan penyembunyian nama yang sangat sulit dipecahkan. Berikut adalah versi sederhana yang menjelaskan masalahnya:
Ada kelas: org.A
package org;
public class A{
public class X{...}
...
protected int net;
}
Lalu ada kelas net.foo.X
package net.foo;
public class X{
public static void doSomething();
}
Dan sekarang, inilah kelas bermasalah yang mewarisi dari A
dan ingin dipanggilnet.foo.X.doSomething()
package com.bar;
class B extends A {
public void doSomething(){
net.foo.X.doSomething(); // doesn't work; package net is hidden by inherited field
X.doSomething(); // doesn't work; type net.foo.X is hidden by inherited X
}
}
Seperti yang Anda lihat, ini tidak mungkin. Saya tidak dapat menggunakan nama sederhana X
karena disembunyikan oleh tipe yang diwariskan. Saya tidak dapat menggunakan nama yang sepenuhnya memenuhi syarat net.foo.X
, karena net
disembunyikan oleh bidang warisan.
Hanya kelas yang B
ada di basis kode saya; kelas net.foo.X
dan kelas org.A
perpustakaan, jadi saya tidak bisa mengubahnya!
Solusi saya satu-satunya terlihat seperti ini: Saya dapat memanggil kelas lain yang pada gilirannya memanggil X.doSomething()
; tapi kelas ini hanya akan ada karena nama bentrok, yang nampaknya sangat berantakan! Apakah tidak ada solusi di mana saya bisa langsung menghubungi X.doSomething()
dari B.doSomething()
?
Dalam bahasa yang memungkinkan untuk menentukan namespace global, misalnya, global::
di C # atau ::
di C ++, saya bisa mengawali net
dengan awalan global ini, tetapi Java tidak mengizinkannya.
net.foo.X
punya metode, tidak org.A.X
!
A
? Warisan bisa menjadi sangat jahat, seperti yang Anda temukan…
I could call another class that in turn calls X.doSomething(); but this class would only exist because of the name clash, which seems very messy
1 untuk sikap kode bersih. Tapi bagi saya sepertinya ini adalah situasi yang harus Anda lakukan pengorbanan. Cukup lakukan ini, dan berikan komentar panjang yang bagus tentang mengapa Anda harus melakukannya (mungkin dengan tautan ke pertanyaan ini).
public void help(net.foo.X x) { x.doSomething(); }
dan panggil denganhelp(null);