Ma classe devrait s'étendre sur deux classes en même temps:
public class Preferences extends AbstractBillingActivity {
public class Preferences extends PreferenceActivity {
Comment le faire
Upd. Puisque ce n’est pas possible, comment puis-je utiliser AbstractBillingActivity with Preferences alors?
Upd2. Si je vais avec des interfaces, dois-je créer:
BillingInterface
public interface BillingInterface extends PreferenceActivity, AbstractBillingActivity {
}
PréférenceActivité
public interface PreferenceActivity {
}
AbstractBillingActivity
public interface AbstractBillingActivity {
void onCreate(Bundle savedInstanceState);
}
et alors
public class Preferences implements BillingInterface {
Java ne prend pas en charge l'héritage multiple.
Il existe quelques solutions de contournement auxquelles je peux penser:
La première est l'agrégation: créez une classe qui prend ces deux activités sous forme de champs.
La seconde consiste à utiliser des interfaces.
La troisième consiste à repenser votre conception: est-il logique pour une classe Preferences
d'être à la fois une PreferenceActivity
et une AbstractBillingActivity
?
Java ne supporte pas l'héritage multiple. Vous pouvez implémenter plusieurs interfaces, mais pas étendre plusieurs classes.
Une autre solution consiste à créer une classe interne privée qui étend la seconde classe. Par exemple, une classe qui étend JMenuItem
et AbstractAction
:
public class MyClass extends JMenuItem {
private class MyAction extends AbstractAction {
// This class can access everything from its parent...
}
}
Java 1.8 (ainsi que Groovy et Scala) a un objet appelé " Interface Defender Methods ", qui sont des interfaces avec des corps de méthodes par défaut prédéfinis. En implémentant plusieurs interfaces utilisant des méthodes defender, vous pouvez effectivement étendre le comportement de deux objets d'interface.
De plus, dans Groovy, en utilisant l'annotation @Delegate, vous pouvez étendre le comportement de deux classes ou plus (avec des avertissements lorsque ces classes contiennent des méthodes du même nom). Ce code le prouve:
class Photo {
int width
int height
}
class Selection {
@Delegate Photo photo
String title
String caption
}
def photo = new Photo(width: 640, height: 480)
def selection = new Selection(title: "Groovy", caption: "Groovy", photo: photo)
assert selection.title == "Groovy"
assert selection.caption == "Groovy"
assert selection.width == 640
assert selection.height == 480
Non, vous ne pouvez pas étendre une classe à deux classes.
Une solution possible consiste à le faire s'étendre d'une autre classe et à rendre cette classe à l'autre.
Java ne prend pas en charge l'héritage multiple. Cependant, votre problème peut être résolu en utilisant des interfaces.
La solution la plus simple serait de créer une interface pour AbstractBillingActivity
et PreferenceActivity
et de les implémenter.
Ce que vous demandez, c'est l'héritage multiple, et c'est très problématique pour plusieurs raisons. L'héritage multiple a été spécifiquement évité en Java; le choix a été fait de prendre en charge la mise en œuvre de plusieurs interfaces, solution de contournement appropriée.
Java ne supporte pas l'héritage multiple, c'est pourquoi vous ne pouvez pas étendre une classe à partir de deux classes différentes en même temps.
Utilisez plutôt une classe unique à partir de, et utilisez interfaces
pour inclure des fonctionnalités supplémentaires.
Dans Groovy, vous pouvez utiliser trait au lieu de classe. Comme elles agissent de la même manière que les classes abstraites (vous pouvez spécifier des méthodes abstraites tout en pouvant en implémenter d'autres), vous pouvez faire quelque chose comme:
trait EmployeeTrait {
int getId() {
return 1000 //Default value
}
abstract String getName() //Required
}
trait CustomerTrait {
String getCompany() {
return "Internal" // Default value
}
abstract String getAddress()
}
class InternalCustomer implements EmployeeTrait, CustomerTrait {
String getName() { ... }
String getAddress() { ... }
}
def internalCustomer = new InternalCustomer()
println internalCustomer.id // 1000
println internalCustomer.company //Internal
Signalons simplement que ce n'est pas exactement la même chose que d'étendre deux classes, mais dans certains cas (comme dans l'exemple ci-dessus), cela peut résoudre le problème. Je suggère fortement d'analyser votre conception avant de vous lancer dans l'utilisation de traits, car ils ne sont généralement pas nécessaires et vous ne pourrez pas implémenter correctement l'héritage (par exemple, vous ne pouvez pas utiliser de méthodes protégées dans les traits). Suivez la recommandation de la réponse acceptée si possible.
De plus, au lieu de classes internes, vous pouvez utiliser vos 2 classes ou plus comme champs.
Par exemple:
Class Man{
private Phone ownPhone;
private DeviceInfo info;
//sets; gets
}
Class Phone{
private String phoneType;
private Long phoneNumber;
//sets; gets
}
Class DeviceInfo{
String phoneModel;
String cellPhoneOs;
String osVersion;
String phoneRam;
//sets; gets
}
Donc, ici vous avez un homme qui peut avoir un téléphone avec son numéro et son type, vous avez également DeviceInfo pour ce téléphone.
En outre, il est préférable d’utiliser DeviceInfo comme champ dans la classe Phone, comme
class Phone {
DeviceInfo info;
String phoneNumber;
Stryng phoneType;
//sets; gets
}
Je peux penser à une solution de contournement qui peut aider si les classes que vous souhaitez étendre incluent uniquement des méthodes.
Écrivez ces classes en tant qu'interfaces. En Java, vous pouvez implémenter un nombre illimité d'interfaces et implémenter les méthodes en tant que méthodes par défaut dans les interfaces.
Si vous souhaitez utiliser des méthodes de plusieurs classes, la meilleure méthode consiste à utiliser Composition au lieu de Héritage.
Familier avec la hiérarchie multiniveau?
Vous pouvez utiliser la sous-classe comme super-classe de votre autre classe.
Vous pouvez essayer ça.
public class PreferenceActivity extends AbstractBillingActivity {}
puis
public class Preferences extends PreferenceActivity {}
Dans ce cas, la classe Preferences hérite à la fois de PreferencesActivity et de AbstractBillingActivity.