Bonjour,
Je travaille sur la création d'un logiciel de modéilisation moléculaire appliqué à la théorie de Huckel en JAVA.Je
résume mon affaire
Actuellement un objet de classe Molecule est un un conteneur d'objtets d'Atomes Huckel et de Liaisons Huckel .
En gros :
public class Molecule {
private ArrayList lstAtom // liste d'atomes
private ArrayList lstBond // liste de liaisons
private int charge // charge de la molécule
/*** créer un atom d'un type Enum atomType à un poin donné ****/
public Atom createAtom (AtomType type, Point2D p) {...}
/** lier deux atomes . type de liaison = 1 ou 2 ou 3 (simple, double triple)
public void link (Atom a1, Atom a2, int type) {...}
public void rotate () {................}
public List getAtoms () {............}
public List getBonds () {............}
...........
}
Ma classe Atom et ma Class Bond contiennent des parametres (membres de classe) inhérents au squelette de la
molécule : comme par exemple charge atomique, nombre d'électrons, pour l'atome
la classe Bond possède uen référence sur les deux atomes qui contiennent la liaison et un type de laiison "int" : 1
2 ou 3 suivant si c'est une liaison triple ou double.
Ces deux classes ne sont pas "interne" à la molécule pour plus de lisibilité, donc elles contiennent une référence
à la molécule qui les incluent : je ne sais pas si cela est efficace, j'aurai peut etre dû mettre ces classes à
l'intérieur de la lcase molécule.
mais les classes Atom et Bond ont actuellement aussi des paramètres inhérents à la théorie de huckel : double hX
pour l'atome et double hxy pour la liaison (bond) . quand on modifie le type d'atome (Carbone, Azote, etc....
propriété inhérente au squelette) le paramètre hx est modifié sur l'atome, mais cela va aussi modifier le
paramètre Hxy dans toutes les liaisons de la molécule qui possèdent l'atome. pour cela qd on fait un "set" sur
l'atome, l'objet appelle ensuite une fonction "handle...." dans la molécule qui va faire les modifs sur les
liaisons. Apres chaque modif apportée sur la molécule ou une liaison ou un atome l'objet molécule envoie des
évenements aux vues par des listeners que j'ai créé (classe MoleculeEvent, interface MoleculeListener) .
Bref voilà ma question .
comment puis-je séparer ce qui est inhérent au squelete et et ce qui est inhérent à huckel ???
En effet j'aimerai bien que mon suqelette de base soit réutilisable pour des logiciels qui n'ont rien à voir avec
huckel.
j'avias pensé au départ faire une classe Skeleton qui contient des listes d'AtomSekel et de BondSekel ayant
simplement eux meme des propriété inhétentes aux squelette, et dérivée AtomSkel et BondSkel en AtomHuckel et
BondHuckel., puis dérivée Skeleton et MoleculeHuckel.
Cela n'est pas possible parce que par dérivation les arraylist de MoleculeHuckel n'auront pas AtomSkel et des
BondSkel mais simlplement des AtomHuckel et des BondHuckel.
Comment faire ? j'ai 'impression que je dois tout mettre dans la même classe et qu'il est impossible de dériver un
conteneur d'objet contenant un contenu lui-même dérivé
En vous remerciant par avance
Cordialement
# Interface
Posté par Bozo_le_clown . Évalué à 3.
Par exemple, tu peux créer un interface AtomHuckelInt qui déclare toutes les opérations liée aux spécificités Huckel des atomes (setHx, ....). Tu crées une classe d'implémentation AtomHuckelImpl qui implémente cette interface.
Tes classe de base (Atom, ..)ne déclarent et n'implémentent que les méthodes de bases.
Tu crées une classe AtomHuckel qui hérite de Atom et qui implemente l'interface AtomHuckelInt.
A l'intérieur, tu encapsules une référence à la classe AtomHuckelImpl (composition=> attribut privé par exemple private AtomHuckelImpl ah) dans l'implémentation des méthodes de l'interface tu délegues le comportement à ta réference privée par simple appel de méthode ( ah.setHx() )
Voici 2 liens qui explique le fonctionnement
http://www.artima.com/designtechniques/compoinh.html
En espérant ne pas avoir tapé à coté du sujet.
[^] # Re: Interface
Posté par Bozo_le_clown . Évalué à 3.
Pardonnes moi si je t'enonce des concepts que tu maîtrises déjà, je n'ai peut-être pas bien compris ta problématique?
.
En POO si tu déclares une méthode dans une classe qui attend des objets d'une certaine classe et leur applique un traitement. Le code de cette méthode pourra parfaitement fonctionner si les objets référencés sont en fait des instances d'une classe dérivée de celle déclarée. Dans le traitement de la méthode, ils seront considérés comme des objets de la classe mère attendue et les méthodes correspondantes seront invoquées. En java, si ces méthodes ont été redéfinies dans les sous classe c'est l'implémentation de la sous classe qui sera appelée. On parle alors de polymorphisme.
http://en.wikipedia.org/wiki/Polymorphism_in_object-oriented(...)
Dans ton cas donc si AtomHuckel est dérivé de AtomSkel et que tu traites un ArrayList de AtomSkel dans ta classe Molecule. Le code fonctionnera à l'identique si l'ArrayList contient en fait des références à des AtomHuckel.
Autre chose, je ta'ai donnné unline qui explique l'intêret de la composition.
Voici un article qui traite plus précisément de la délégation
http://en.wikipedia.org/wiki/Delegation_%28programming%29
[^] # Re: Interface
Posté par nicolas . Évalué à 1.
en fait ds l'exemple ci dessous
A = Atom de base
AA : atom huckel
contA : squelette de la molécule . j'ai besoin d'un constucteur par copie
dans mon main quand je fais une iteration sur la copie du conteneur ca plante sur le cast , forcément, pcq je caste en AA et que mon constructeur par copie ne copie que des objets de classe A foaut -il donc que je fasse un nouveau conteneur contAA ? et que donc pour gérer des objets AA je ne me serve plus du tout de contA ?
public class A {
public int a;
public A(int a) {
this.a = a;
}
public A(A other) {
this.a = other.a;
}
}
public class AA extends A {
public int aa;
public AA (int a, int aa) {
super (a);
this.aa = aa;
}
public AA (AA other) {
super (other);
this.aa = other.aa;
}
}
import java.util.ArrayList;
import java.util.Iterator;
public class ContA {
public ArrayList contA;
public ContA() {
contA = new ArrayList ();
}
public ContA(ContA other) {
contA = new ArrayList ();
Iterator it = other.contA.iterator();
A a;
while (it.hasNext()) {
a = (A) it.next();
this.contA.add(new A (a));
}
}
}
import java.util.Iterator;
public class Main {
/**
* @param args
*/
public static void main(String[] args) {
ContA myContA = new ContA();
AA a1 = new AA(11, 20);
AA a2 = new AA(12, 25);
myContA.contA.add(a1);
myContA.contA.add(a2);
Iterator it = myContA.contA.iterator();
AA a;
while (it.hasNext()) {
a = (AA) it.next();
System.out.println(a.a + " " + a.aa);
}
ContA copyContA = new ContA(myContA);
it = copyContA.contA.iterator();
while (it.hasNext()) {
a = (AA) it.next();
System.out.println(a.a + " " + a.aa);
}
}
}
[^] # Re: Interface
Posté par Bozo_le_clown . Évalué à 2.
La solution est peut être de recourir aux types paramétrés (genérics pour java, templates pour C++,...)
public class ContA {
....
http://java.sun.com/j2se/1.5/pdf/generics-tutorial.pdf
Par contre tu ne pourras pas mélanger des objets de type différents
dans un même conteneur. Dans ton exemple ca n'est pas le cas doncca devrait marcher.
Ca nécessite aussi au minimum un JDK 1.5
[^] # Re: Interface
Posté par Bozo_le_clown . Évalué à 2.
public class ContA {
public ArrayList contA;
....
}
....
public class Main {
/**
* @param args
*/
public static void main(String[] args) {
ContA myContA = new ContA();
AA a1 = new AA(11, 20);
AA a2 = new AA(12, 25);
myContA.contA.add(a1);
myContA.contA.add(a2);
Iterator it = myContA.contA.iterator();
AA a;
while (it.hasNext()) {
a = (AA) it.next();
System.out.println(a.a + " " + a.aa);
}
ContA copyContA = new ContA(myContA);
it = copyContA.contA.iterator();
while (it.hasNext()) {
a = (AA) it.next();
System.out.println(a.a + " " + a.aa);
}
}
L'idée est là mais ya sûrement des erreurs de syntaxe
Tiens nous au courant de tes aventures
[^] # Re: Interface
Posté par Bozo_le_clown . Évalué à 2.
je la refais
public class ContA<E> {
public ArrayList<E> contA;
....
}
....
public class Main {
/**
* @param args
*/
public static void main(String[] args) {
ContA<AA> myContA = new ContA<AA>();
AA a1 = new AA(11, 20);
AA a2 = new AA(12, 25);
myContA.contA.add(a1);
myContA.contA.add(a2);
Iterator it = myContA.contA.iterator();
AA a;
while (it.hasNext()) {
a = (AA) it.next();
System.out.println(a.a + " " + a.aa);
}
ContA<AA> copyContA = new ContA<AA>(myContA);
it = copyContA.contA.iterator();
while (it.hasNext()) {
a = it.next();
System.out.println(a.a + " " + a.aa);
}
}
Sinon en passant ce n'est en général pas une bonne idée de déclarer les attributs d'une classe public. Ca casse l'encapsulation et si tu décides de changer l'implémentation de ta classe (remplacer des ArrayList par atre chose par exemple) tu seras obligé de modifier tout ton code dans toutes les methodes appelantes.
Suivre le flux des commentaires
Note : les commentaires appartiennent à celles et ceux qui les ont postés. Nous n’en sommes pas responsables.