Jeg har et program som er opbygget af flere forskellige klasser. En hovedklasse som arver fra JFrame, og viser selve programmet, og to biklasser som hvert arver fra JPanel. I hovedklassen bliver begge biklasser så indsat i contentPane.
Er det her dårlig opbygning? Kan man ligesågodt have det hele i én klasse?
Mit problem er at jeg skal have kørt en metode i hovedklassen fra en af biklasserne efter programstart... hvordan gør man det?
Denne side indeholder artikler med forskellige perspektiver på Identity & Access Management i private og offentlige organisationer. Artiklerne behandler aktuelle IAM-emner og leveres af producenter, rådgivere og implementeringspartnere.
1) Det lyder som en god opbygning, specielt hvis dine to biklasser kunne tænkes at blive brugt andetsteds. Hvis de er totalt specifikke er det hip som hap. 2) For at køre en metode fra en biklasse, må den have kendskab til hovedklassen, og det gøres nemmest ved at lade konstruktoren for biklassen modtage en reference til hovedklassen, så har den adgang til at udføre metoder på denne. Du kan gøre noget som det her. public Biklasse { private Hovedklasse h; public Biklasse(Hovedklasse h) { this.h = h; } }
carstenknudsen >> Hvis der, som her, bliver snakket om god/dårlig opbygning af koden, var det så ikke mest korrekt at benytte et observer-pattern, f.eks Java's eget, istedet for at sende hele klassen med.
Dette er ikke en kritik af svaret, men mere et spørgsmål om ikke det er mest korrekt.
ng-km: det der er beskrevet i spørgsmålet har intet med observer pattern at gøre. Det er et spørgsmål om at et par komponenter skal bruge i en anden komponent. Ang at en klasse skal kunne kalde en anden har heller ikke noget direkte med observer pattern at gøre. Man kunne lave løsningen som en observer pattern, men det vil være overkill at gøre det sådan, det er netop derfor man som regel bruger metodekald. Du er velkommen til at specificere hvad du mener så vi kan snakke videre om det, det er jo det vi er her for alle sammen.
Min kommentar var et åbent spørgsmål til alle hajerne, for jeg mener selv at jeg jeg har meget at lære endnu i Java, og det er dejligt at kunne udveksle erfaringer og meninger på denne måde. Det er rigtigt at det er overkill hvis der kun skal benyttes én metode, og jeg har ingen indsigelser imod det, jeg gør det en sjælden gang selv hvis jeg lige hurtigt skal "have ordnet et lille problem". En del af brinkomans spørgsmål går imidlertid på god programmeringsskik, og der mener jeg at man godt må se lidt anderledes på det, for hvor går grænsen?. Her er en udlægning som jeg tror på er sund at få lagt ind på rygraden.
-------------
En af de objekt-orienterede filosofier bygger på at hvert objekt tager ansvaret for egne handlinger, hvilket er indlysende nok, ellers kan man jo bare skrive al koden i en klasse. Ved at sende din hoved-klasse med til din biklasse, lader du din biklasse få fuld adgang og fuld kendskab til din hoved-klasse, hvilket pludselig giver din biklasse ansvaret for hoved-klassens handlinger, og hvad hvis biklassen pludselig får brug for at sende hoved-klassen videre til andre biklasser, så er hoved-klassen kendt og åben i hele dit program.
Her kan du efter min mening så gøre tre ting i omvendt prioriteret rækkefølge:
1: Hvis du sender hoved-klassen til biklassen, så sørg som minimum for at hoved-klassens metoder og variabler er private, undtagen dem som biklassen skal kende til.
2: Du kan også skrive et Interface med kun den/de metoder der skal være kendte i din hoved-klasse, og så lade din hoved-klasse implementere dette interface. I stedet for at sende din hoved-klasse til din biklasse kan du så sende interfacet, der jo kun lader biklassen få adgang til den/de metoder der er i interface'et. Dette er en god metode til eksplicit at begrænse kendskabet til hoved-klassen, hvor interfacet bremser et evt. misbrug af hoved-klassens metoder.
3: Den sidste og mest omfattende(og MÅSKE mest korrekt) er at benytte et observer-designmønster, der adskiller de to klasser fuldstændig fra hinanden, så biklassen intet kender til hoved-klasse, men kommunikerer via en observer. Denne implementerings-metode bygger på at biklassen via en Observable-klasse sender forespørgsler/kald videre til hoved-klasse, som er observer, uden at vide hvor og hvordan det modtages. Disse informationer tager hoved-klasse sig selv af via sin observer, og dermed beholder hoved-klassen ansvaret for sine egne handlinger. Denne implementerings-metode benytter jeg selv, og har selv lavet min egen Observer-package fordi Java's observer til tider var utilstrækkelig.
Hvis du mener at du kan bruge observer-metoden, lægger jeg gerne den kode(Java's observer) jeg selv lavede da jeg skulle lære at forstå mønstret i al sin enkelhed og genialitet.
Hvis i er uenige i min fremlæggelse, tager jeg selvfølgelig gerne mod konstruktiv kritik, for som sagt mener jeg selv at der er meget at lære endnu.
1) Det kan vi næppe blive uenige om, men da der er tale om JFrame og JPanel er der ingen grund til at være nervøs her. Anden halvdel af kommentaren kan man ikke altid leve op til (se kommentar 2). Bemærk at klasserne i forvejen kender til hinanden (JFrame og JPanel altså).
2) Det ville være en god ide, men igen det kan ikke altid lade sig gøre. Selvom du lader hovedklassen implementere et interface, er der intet til hinder for at biklassen undersøger om objektet tilfældigvis implementerer andre interfacet og i så fald laver en eller flere class casts og kalder metoder det ikke var meningen den skulle gøre. I stedet kan man lave sit hovedklasse (ikke i dette tilfælde dog) være "tom" og istedet bare har en masse instanser af forskellige klasser der står for den konkrete funktionalitet. Disse kan så smides ud som parametre og de kan ikke gøre andet end det de nu engang gør. Dette vil være lidt omstændigt i mange eksempler, men kan til dels bruges praktisk i mange sammenhænge.
3) Det kan heller ikke skille os ad,at det er en god ide at anvende observer pattern som du har beskrevet. Der er tale om en gui og der kan du ikke undgå at bruge observer pattern'et, hele AWT og Swing er gennemsyret af brug at dette vigtige pattern, dog sjældent (om nogensinde) i den rene form, der er som regel tale om forskellige varianter af mønstret. Man skal bare altid huske at anvende sit pattern på det rette niveau og så implementere det på sædvanligvis, ikke med rekursiv anvendelse af samme pattern, som f.eks. så skal biklassen og observable klassen også være uafhængige og til det anvender vi observer pattern, og så fremdeles (ad infinitum). Ang kritikken af Observer/Observable som de eksisterer i Java, har du delvis ret. Det er også normalt således at man selv laver sine listener klasser hvis man vil bruge observer pattern, det som der leveres gennem nævnte klasser er for generelt til de fleste tilfælde (når alle objekter er af type Object bliver det nogle gange lidt fjollet til sidst).
Endelig et par generelle kommentarer til dine unummererede kommentarer. Ang objekter der tager ansvar for sig selv, så overdriver :) du nok lidt her; at en instans leveres som parameter til en anden klasse for at den skal kunne kalde en enkelt metode på denne er ikke at overdrage ansvaret fra hovedklassen til biklassen. Ang punkt 1 så synes jeg vel egentlig at det var det der skal have højeste prioritet idet du ikke kan bygge noget fornuftigt med mindre de mere basale niveauer er lavet ordentligt, og hvis man ikke laver en ordentlig sondring mht til f.eks. synlighed af data og funktionalitet er det vanskeligt at forestille sig at der kan komme noget godt ud af det. Alt i alt er vi vel ret enige, selvom der er detaljer hvor vi måske har lettere divergerende holdninger. Jeg kan godt forstå at du er glad for observer pattern, det er også et af de mest bruge i selve Java, så det kan ikke anbefales nok, men i det tilfælde der blev skitseret i spørgsmålet her, der tror jeg ikke det vil egne sig.
Min egen (og jeg er noob) generelle erfaring er at man benytter specielt indre klasser i langt højere grad i java2/swing end man gjorde i java1/awt. Til eksempel class HTML { class Tag { static { HTML.Tag.LI = this("LI"); HTML.Tag.P = this("P"); // et cetera } } } Så vidt jeg kan se er det en god ide at inkludere indre klasser hvis: 1) Funktionaliten repræsenterer et objekt 2) Hver instans af den ydre klasse kan tænkes at have flere instanser af dette objekt tiknyttet eller at oprette nye som resultat af sin egen funktion. I henhold til dette spørgsmål drejer det sig om du skal MODEL 1: public class MyFrame extends Frame { // konstruktor må i tænke jer til public Panel makeMyMenu(argumenter) { } public Panel makeMyContent(argumenter) { } } eller MODEL 2: public class MyFrame extends JFrame { // konstruktor må i tænke jer til class MenuPanel extends JPanel{ } class ContentPanel extends JPanel { } } eller MODEL 3: public class MyFrame extends Frame { } class MenuPanel extends JPanel { } class ContentPanel extends JPanel { } Sådan som jeg ser det har du fordel af model 1 hvis du ikke vil knytte unikke funktioner til dine paneler. Model 2 er bedst hvis du ikke påtænker at lave andre underklasser af JFrame, som kan bruge disse objekter og slutteligt er model 3 bedst hvis og kun hvis disse objekter finder anvendelse uden en instans af MyFrame i scope. Det er sådan jeg ser på det, men jeg er ikke desideret ekspert (hvad laver jeg her??) så andre er velkomne til sagligt at forkaste det jeg har skrevet.
jeg havde først skrevet Frame og Panel, men besluttede at ændre det til JFrame og JPanel. Jeg fik det hvis ikke gjort konsistent. Tilgiv mig.
Synes godt om
Ny brugerNybegynder
Din løsning...
Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.