Manuel Skrevet 14. oktober 2005 Del Skrevet 14. oktober 2005 (endret) Jeg har en struktur med mange medlemmer. Mange av disse medlemmene er forskjellige variabler (ikke arrays) som jeg ønsker å tildele verdier. Siden jeg fyller opp mange variabler om gangen, så synes jeg at det er litt overflødig å måtte referere til strukturen *hver* gang jeg ønsker å bruke en medlemsvariabel eller medlemsfunksjon. Se f.eks på: struct ting{ int ting_nummer; char navn[50]; // inkl. "padding" char beskrivelse[200]; struct tang{ int tang_nummer; char navn_tang[50]; char beskrivelse[200]; }andre_egenskaper; }egenskaper; Hver gang jeg skal bruke et medlem i strukturen tang er jeg nødt til å innlede med egenskaper. Finnes det ikke en måte som forteller kompilatoren at samtlige variabler innenfor disse klammeparantesene finnes i struktur egenskaper? Endret 14. oktober 2005 av Manuel Lenke til kommentar
GeirGrusom Skrevet 19. oktober 2005 Del Skrevet 19. oktober 2005 Hvis du kutter ut tang, for hvis du vil ha tak i det, skjønner jeg ikke hva du skal med tang i det hele tatt. Hvis du vil ha en peker til tang, uten å deklarere tang, kan du peke til &ting.tang_nummer Lenke til kommentar
dayslepr Skrevet 19. oktober 2005 Del Skrevet 19. oktober 2005 (endret) Hver gang jeg skal bruke et medlem i strukturen tang er jeg nødt til å innlede med egenskaper. tang_nummer er et medlem av tang, og jeg trenger ikke bruke scope-operatoren her: ting::tang i_tang; i_tang.tang_nummer = 321; jeg refererer kun til den ytre strukturen når jeg skal ha tak i den indre strukturen for å lage en instans .. etterpå refererer jeg ikke til strukturen, men til instansen - og dens medlemmer, direkte uten bruk av scope-operator.. ..så du må forklare bedre - bruk et kjørbart eksempel, med kommentarer som viser hva du vil (hvilke detaljer du lurer på om er mulig å abstrahere vekk, om de ikke allerede er de som kommer frem i ex. mitt over da ... ) om du mener noe slikt, så vet jeg ikke om det er mulig i C++, kanskje med noe template-trickery (dette er Common Lisp): (defclass Test () ((navn :accessor navn :initarg :navn) (alder :accessor alder :initarg :alder))) (let ((person-1 (make-instance 'Test :navn "Lars" :alder 25)) (person-2 (make-instance 'Test :navn "Elisabeth" :alder 20))) (with-accessors ((navn-1 navn) (alder-1 alder)) person-1 (with-accessors ((navn-2 navn) (alder-2 alder)) person-2 (print navn-1) (print alder-1) (print navn-2) (print alder-2)))) "Lars" 25 "Elisabeth" 20 Edit: det er mulig ting er annerledes mellom C og C++ her også ... jeg antok at du bruker C++ jeg da men .... Endret 19. oktober 2005 av dayslepr Lenke til kommentar
A_N_K Skrevet 19. oktober 2005 Del Skrevet 19. oktober 2005 (endret) Virker som du vil operere på medlemmet andre_egenskaper av objektet egenskaper? Da er det ikke verre enn å opprette en referanse direkte til andre_egenskaper. F.eks: ting::tang &andre = egenskaper.andre_egenskaper; strncpy(andre.navn_tang, "hihi", 50); Mulig at jeg misforstår hva du vil fram til, men med tanke på at du faktisk har definert objektene egenskaper og andre_egenskaper går jeg ut i fra at det er dette du vil. Edit: Forresten har språket D et nøkkelord with som gjør at du kan operere med et visst skop i en blokk. Mistenker at det er noe slikt du spør etter, men jeg vet ikke hva helt hva jeg skal synes om det. Endret 19. oktober 2005 av A_N_K Lenke til kommentar
Manuel Skrevet 19. oktober 2005 Forfatter Del Skrevet 19. oktober 2005 (endret) #include <cstdio> #include <iostream> #include "require.h" using namespace std; struct Stack{ struct Link{ void* data; Link* next; void initialize(void* dat, Link* nxt) { data = dat; next = nxt; } }* head; void initialize() { head = 0; } void push(void* dat) { Link* newLink = new Link; newLink->initialize(dat, head); head = newLink; } void* peek() { require(head != 0, "Stack empty"); return head->data; } void* pop() { if(head == 0) return 0; void* result = head->data; Link* oldHead = head; head = head->next; delete oldHead; return result; } void cleanup() { require(head == 0, "Stack not empty"); } }; void setstring(char szTarget[], char szIn[]){ int i = 0; do { szTarget[i] = szIn[i]; } while(szIn[i++] != '\0'); } struct Video_Management{ int serial; //unikt tall for hver film char rental_date[6]; //Utleie- og innleveringsdato i formatet DD/MM char return_date[6]; //Siste tegn fungerer som terminering, så hvis denne settes til noe // annet enn '/0' blir det et problem! int nCount; // antall ganger utleid char name[50]; // filmens navn int released; // utgivelsesdato, år char notes[200]; // andre notater void PrintInfo(void){ printf("Tittel: %s\n", name); printf("Serienummer: %d\n", serial); printf(" Utgivelsesaar: %d\n", released); printf(" Sist utleid: %s\n", rental_date); printf(" Sist tilbakelevert: %s\n", return_date); printf(" Antall ganger utleid: %d\n", nCount); printf("NOTATER: %s\n", notes); } int Rent(char* sz, char (*operation)){ int i = 4; while(i > 0){ if((sz[i] < 47) || (sz[i] > 57)) return -1; i = i - 1; } setstring(operation,sz); nCount = nCount + 1; return 0; } }; int main(){ Stack videos; Video_Management v1, v2, v3; v1.Rent("31/05", v1.rental_date),v1.Rent("01/06", v1.return_date); v1.serial = 5594; v1.nCount = 1; setstring(v1.name, "The Rock"); v1.released = 1998; setstring(v1.notes, "Finnes både på VHS og DVD som tosidig plate"); v2.Rent("06/07", v2.rental_date), v2.Rent("07/07", v2.return_date); v2.serial = 5492; v2.nCount = 4; setstring(v2.name, "Crimson Tide"); v2.released = 1995; setstring(v2.notes, "Denne har jeg bare på VHS"); v3.Rent("08/08", v3.rental_date),v3.Rent("09/08", v3.return_date); v3.serial = 5444; v3.nCount = 6; setstring(v3.name, "Mission: Impossible"); v3.released = 1997; setstring(v3.notes, "Denne finnes både på VHS og DVD"); videos.initialize(); videos.push(static_cast<void*>(&v1)); videos.push(static_cast<void*>(&v2)); videos.push(static_cast<void*>(&v3)); Video_Management* vp; vp = static_cast<Video_Management*>(videos.pop()); ((*vp).PrintInfo()); (*((Video_Management*)(videos.pop()))).PrintInfo(); //En skikkelig stygg peker-i-peker-i-masse-paranteser-variant (*((Video_Management*)(videos.pop()))).PrintInfo(); videos.cleanup(); return 0; } require.h inneholder bare noen enkle funksjoner som tar i bruk cassert. Stack-strukturen fungerer som stack-segmenter i assembly, med push, pop osv. Dette er skrevet som en del av en oppgave. Min oppgave var å lage en struktur som representerer en videofilm til en utleiebutikk, med alle egenskaper jeg finner passende. Jeg lager altså tre objekter av typen "Video_Management", og tildeler disse egenskaper som serienummer, utleiedata, innleveringsdato osv. Stack-objektet, "videos", er i grunn overflødig, men dette er altså oppgaven. Programmet avsluttes ved å "poppe" stacket, og kaste void-pekere tilbake til Video_Management-pekere. Spørsmålet dreier seg om denne delen: v1.Rent("31/05", v1.rental_date),v1.Rent("01/06", v1.return_date); v1.serial = 5594; v1.nCount = 1; setstring(v1.name, "The Rock"); v1.released = 1998; setstring(v1.notes, "Finnes både på VHS og DVD som tosidig plate"); v2.Rent("06/07", v2.rental_date), v2.Rent("07/07", v2.return_date); v2.serial = 5492; v2.nCount = 4; setstring(v2.name, "Crimson Tide"); v2.released = 1995; setstring(v2.notes, "Denne har jeg bare på VHS"); v3.Rent("08/08", v3.rental_date),v3.Rent("09/08", v3.return_date); v3.serial = 5444; v3.nCount = 6; setstring(v3.name, "Mission: Impossible"); v3.released = 1997; setstring(v3.notes, "Denne finnes både på VHS og DVD"); Her referer jeg til v1, v2 og v3 flere ganger på rad. Det hadde vært fint om det var mulig å begrense det til èn gang ved å si at "mellom disse klammeparantesene så refererer jeg bare til instanser ( ? ) i objektet v1". edit: Virker som om forumet ikke liker tabulator... Endret 19. oktober 2005 av Manuel Lenke til kommentar
dayslepr Skrevet 19. oktober 2005 Del Skrevet 19. oktober 2005 okei, nei det går nok ikke -- da må du over til et annet språk (f.eks. D som A_N_K nevner, eller Common Lisp som jeg nevner i kode-ex. over) mulig jeg tar feil her - noen får bekrefte/avkrefte Lenke til kommentar
A_N_K Skrevet 19. oktober 2005 Del Skrevet 19. oktober 2005 Eksempel på hvordan det kan gjøres i D: class Blah { public: int x; } int main() { Blah b = new Blah(); b.x = 20; with (b) { printf("Tjohei: %d\n", x); } return 0; } Moro. Lenke til kommentar
Anbefalte innlegg
Opprett en konto eller logg inn for å kommentere
Du må være et medlem for å kunne skrive en kommentar
Opprett konto
Det er enkelt å melde seg inn for å starte en ny konto!
Start en kontoLogg inn
Har du allerede en konto? Logg inn her.
Logg inn nå