Flash3 Δημοσ. 14 Μαρτίου 2014 Δημοσ. 14 Μαρτίου 2014 struct dvdtype{ int dvdcode; //kodikos tainias char title[50]; //titlos tainias int customerID; //peelaths poy thn exei enoikiasei int daysowned; //meres poy thn exei krathsei thn tainia o pelaths }; H δομή που θα χρησιμοποιήσουμε για να σώζουμε τις ταινίες είναι ένας δυναμικός πίνακας. struct dvdstruct{ //h domh poy sozoyme ola ta dvds (ena array kai //enas counter poy deixnei thn teleytaia eggrafh struct dvdtype *dvd; //to dynamiko array int numdvds; //o counter poy deixnei poses tainies yparxoyn }; Η μεταβλητή στην οποία θα σώζουμε όλες τις ταινίες θα δηλωθεί στη main. struct dvdstruct dvds; Θέλω να υλοποιήσω αυτη την συναρτηση initDvds() Λειτουργία: Αρχικοποιεί την dvds και δεσμεύει αρχικά μνήμη για 5 ταινίες. Για όλες τις ταινίες τα dvdcode, customerID, daysowned τίθωνται στην τιμή -1 και το title στο κενό string. Το dvds.numdvds παίρνει την τιμή 0 (πρώτη θέση του πίνακα που μπορούμε να γράψουμε). Μπορεί κάποιος να με βοηθήσει Εχω κάνει αυτο typedef struct dvdtype{ int dvdcode; char title[50]; int customerID; int daysowned;}dvdtype;typedef struct dvdstruct{ dvdtype *dvd; int numdvds;}dvdstruct;void initDvds(dvdstruct dvds); int main(int argc, const char * argv[]){ int i; dvdstruct dvds; initDvds(dvds);} void initDvds(dvdstruct dvds){ int i,j; dvds.dvd=(dvdtype*)malloc(5*(sizeof(dvdtype))); // for(i=0;i<5;i++) //{ dvds.dvd->customerID=-1; dvds.dvd->daysowned=-1; dvds.dvd->dvdcode=-1; dvds.dvd->title[50]=getchar(); //} } Το malloc που εκανα για τον δυναμικο πινακα πρεπει να πετυχε..Δεν ξερω ομως πως θα περασω 5 διαφορετικες ταινιες και πως θα περασω τα ονοματα τους.Δεν ξερω επισης αν αυτο με τον πινακα title και το getchar(); ειναι σωστα.
Moderators Kercyn Δημοσ. 14 Μαρτίου 2014 Moderators Δημοσ. 14 Μαρτίου 2014 Στην initDvds περνάς το argument by value, που σημαίνει ότι μέσα στην initDvds θα δημιουργηθεί ένα αντίγραφο του argument, και ό,τι αλλαγές κάνεις στη συνάρτηση θα είναι σε τοπικές μεταβλητές, οι οποίες θα εξαφανιστούν όταν τελειώσει η συνάρτηση. Πρέπει το dvds να το περάσεις ως pointer. Ας μπούμε τώρα μέσα στο for: Δε χρησιμοποιείς πουθενά το i. Πρέπει να είναι dvds.dvd->... Το dvds.dvd->title[50] = getchar() του λέει να πάει στη θέση 50 του title (η οποία δεν υπάρχει! Οι θέσεις του είναι από 0 έως 49) και να βάλει έναν χαρακτήρα που διαβάζει απ' το πληκτρολόγιο. Αυτό που πρέπει να κάνεις είναι gets(dvds.dvd->title), ούτως ώστε να διαβάσει ένα string και να το βάλει στο title. Το ίδιο που έκανες με το title μπορείς να κάνεις και με τις υπόλοιπες μεταβλητές, αν θες να τις δίνει ο χρήστης και όχι να αρχικοποιούνται σε -1.
Flash3 Δημοσ. 14 Μαρτίου 2014 Μέλος Δημοσ. 14 Μαρτίου 2014 Ευχαριστω πολυ..Ακολουθησα την συμβουλη σου και περασα το dvds σαν pointer..Πλεον περναω την διευθηνση στην συναρτηση και ειναι ετσι η συναρτηση μου. void initDvds(dvdstruct *dvds){ int i,j; dvds->dvd=(dvdtype*)malloc(5*(sizeof(dvdtype))); for(i=0;i<5;i++) { dvds->dvd->customerID=-1; dvds->dvd->daysowned=-1; dvds->dvd->dvdcode=-1; gets(dvds->dvd->title); } Αυτα που εχω με bold μου τα χτυπαει λαθος και δεν ξερω γιατι.Μου λεει οτι βασικα εκει που εχω βαλει το δευτερο τοξακι επρεπε να εχω τελεία αλλα δεν καταλαβω γιατι αφου το dvd einai pointer se typo dvdtype..Αν πάλι φύγω τα δεν μου χτυπαει λάθος το τοξακι..Και το gets(...) δεν ξερω αν το εγραψα σωστα.
Moderators Kercyn Δημοσ. 14 Μαρτίου 2014 Moderators Δημοσ. 14 Μαρτίου 2014 Το dvd είναι όντως pointer, το dvd όμως είναι ένα στοιχείο του dvd. Σκέψου το dvd σαν πίνακα. Στο gets βγάλε το από το title.
imitheos Δημοσ. 14 Μαρτίου 2014 Δημοσ. 14 Μαρτίου 2014 H δομή που θα χρησιμοποιήσουμε για να σώζουμε τις ταινίες είναι ένας δυναμικός πίνακας. struct dvdstruct{ //h domh poy sozoyme ola ta dvds (ena array kai //enas counter poy deixnei thn teleytaia eggrafh struct dvdtype *dvd; //to dynamiko array int numdvds; //o counter poy deixnei poses tainies yparxoyn }; Η μεταβλητή στην οποία θα σώζουμε όλες τις ταινίες θα δηλωθεί στη main. struct dvdstruct dvds; Θέλω να υλοποιήσω αυτη την συναρτηση initDvds() Λειτουργία: Αρχικοποιεί την dvds και δεσμεύει αρχικά μνήμη για 5 ταινίες. Για όλες τις ταινίες τα dvdcode, customerID, daysowned τίθωνται στην τιμή -1 και το title στο κενό string. Το dvds.numdvds παίρνει την τιμή 0 (πρώτη θέση του πίνακα που μπορούμε να γράψουμε). Μια πρώτη παρατήρηση που έχω να κάνω είναι στην επιλογή των ονομάτων. Υπάρχει πολύ dvd με αποτέλεσμα, όπως βλέπουμε παρακάτω, εκφράσεις τύπου dvds->dvd->dvdcode. Επίσης, στην αρχή λες ότι το numdvds δείχνει πόσες ταινίες υπάρχουν και μετά λες ότι η initDvds του θέτει την τιμή 0 ώστε να γράψεις στη πρώτη θέση. Δεν θα χρειαστείς ακόμη μία μεταβλητή-πεδίο που θα δηλώνει το μέγιστο αριθμό καταχωρήσεων που επιτρέπει η εκχωρημένη μνήμη (αρχικά 5) ώστε να ξέρεις πότε θα κάνεις realloc ? To initDvds σας το πρότεινε ο καθηγητής ? Ίσως είναι προσωπική μου παραξενιά αλλά το camelBack με ξενίζει λίγο. Λίγο πιο συνήθεις τρόποι γραφής είναι πχ initdvd, init_dvd, Init_Dvd. void initDvds(dvdstruct dvds); Όπως σου εξήγησε ο Kercyn και έκανες, έπρεπε να χρησιμοποιήσεις δείκτη ως όρισμα στην συνάρτηση. Ένας άλλος τρόπος που χρησιμοποιείται συχνά είναι να αναλαμβάνει όλη την εκχώρηση η init συνάρτηση και να επιστρέφει ένα δείκτη όπως φαίνεται παρακάτω: dvdstruct *initdvd(int n) { dvdstruct *tmp; tmp = malloc (tade); tmp->dvd = malloc( n * sizeof(dvdtype) ); ktl; return tmp; } Με αυτή τη μορφή, εκχωρείται μνήμη για το πεδίο dvds όπως έκανες και εσύ (απλά με μεταβλητό αριθμό αντί για 5 στοιχεία) αλλά εκχωρείται μνήμη και για τη δομή αυτή-καθεαυτή. Ανάλογα ποιος τρόπος σου αρέσει χρησιμοποιείς εκείνον. void initDvds(dvdstruct *dvds) { int i,j; dvds->dvd=(dvdtype*)malloc(5*(sizeof(dvdtype))); for(i=0;i<5;i++) { dvds->dvd->customerID=-1; dvds->dvd->daysowned=-1; dvds->dvd->dvdcode=-1; gets(dvds->dvd->title); } Αυτα που εχω με bold μου τα χτυπαει λαθος και δεν ξερω γιατι.Μου λεει οτι βασικα εκει που εχω βαλει το δευτερο τοξακι επρεπε να εχω τελεία αλλα δεν καταλαβω γιατι αφου το dvd einai pointer se typo dvdtype..Αν πάλι φύγω τα δεν μου χτυπαει λάθος το τοξακι..Και το gets(...) δεν ξερω αν το εγραψα σωστα. Το dvd είναι όντως pointer, το dvd όμως είναι ένα στοιχείο του dvd. Σκέψου το dvd σαν πίνακα. Στο gets βγάλε το από το title. Το dvds το έχεις δηλώσει ως δείκτη οπότε για να προσπελάσει την "τιμή" του πρέπει να χρησιμοποιήσεις τον τελεστή *. Άρα για να το δεις ως δομή πρέπει να το γράψεις ως (*dvds) και προσπελαύνεις τα πεδία του ως (*dvds).τάδε αλλά για να μη γράφεις όλο αυτό υπάρχει η συντόμευση του ->. Δηλαδή το (*dvds).τάδε ισοδυναμεί με το πιο απλό και όμορφο dvds->τάδε. Το dvds->dvd όμως είναι μια απλή δομή οπότε δεν μπορείς να χρησιμοποιήσεις το -> (αν το θέλεις διαφορετικά, η array notation με το έχει ήδη προσπελάσει την τιμή του δείκτη) αλλά χρειάζεσαι την απλή τελεία. Η σωστή λοιπόν έκφραση είναι dvds->dvd.daysowned.
Flash3 Δημοσ. 15 Μαρτίου 2014 Μέλος Δημοσ. 15 Μαρτίου 2014 Συμφωνα με αυτα που μου ζητάει η άσκηση δεν την έχω γράψει σωστα την δεσμευση μνημης και αυτα που είναι στη for...?Δεσμεύω μνημη αρχικα για πεντε εισχωρήσεις τύπου dvdtype στο δυναμικο πίνακα..Μετα αυτο που ζητάει δεν είναι να περασω απο το πληκτρολογιο 5 ονοματα τενιών και όλα τα άλλα τα στοιχεία τους να είναι -1..?? Συγνώμη που δεν καταλαμβαίνω και αν ρωταώ τα ίδια πραματα αλλα ενα μάθημα κάναμε ολο κι όλο στις δομες και μας έβαλε αυτή την άσκηση.
Moderators Kercyn Δημοσ. 15 Μαρτίου 2014 Moderators Δημοσ. 15 Μαρτίου 2014 Για βάλε τον ανανεωμένο κώδικα να δούμε (σε code tag!!)
Flash3 Δημοσ. 15 Μαρτίου 2014 Μέλος Δημοσ. 15 Μαρτίου 2014 Θα τον βάλω..Τι είναι το code tag ομως..??Και δεν καταλαβα ..Μου ζηταει με την αρχικοποίηση να περνάω και title απο το πληκτρολόγιο?Είναι λάθος που εωαλα την συνάρτηση σαν void?Επρεπε να την δηλώσω άλλο τύπο? void initDvds(dvdstruct *dvds){ int i,j; dvds->dvd=(dvdtype*)malloc(5*(sizeof(dvdtype))); dvds->numdvds=0; for(i=0;i<5;i++) { dvds->dvd.customerID=-1; dvds->dvd.daysowned=-1; dvds->dvd.dvdcode=-1; gets(&dvds->dvd->title); } }
Moderators Kercyn Δημοσ. 15 Μαρτίου 2014 Moderators Δημοσ. 15 Μαρτίου 2014 Code tag είναι το [ code ] κώδικας [ /code ] χωρίς τα κενά. void initDvds(dvdstruct *dvds) { int i,j; dvds->dvd=(dvdtype*)malloc(5*(sizeof(dvdtype))); dvds->numdvds=0; for(i=0;i<5;i++) { dvds->dvd[i].customerID=-1; dvds->dvd[i].daysowned=-1; dvds->dvd[i].dvdcode=-1; gets(&dvds->dvd->title[i]); } } Στο gets(&dvds->dvd->title); είναι που έχεις το λάθος. Άμα δεις την gets, θα δεις ότι δέχεται char*. Το title είναι ήδη char*, οπότε γιατί αλλάζεις τον τρόπο που διαβάζεις τα παραπάνω; Το σωστό είναι gets(dvds->dvd.title);
Flash3 Δημοσ. 15 Μαρτίου 2014 Μέλος Δημοσ. 15 Μαρτίου 2014 Ευχαριστο πολύ..Το διορθωσα..Την gets την εβαλα για να διαβαζει ονομα απο το πληκτρολογιο ετσι κατάλαβα ότι μας ζητάει η συνάρτηση...Κατάλαβα σωστά ή απλώς θέλει να αρχικοποιούμε τον πίνακα και όχι να περνάμε κάποιο όνομα μέσα?Αν ναι πως αρχικοποιώ τον πίνακα?
Moderators Kercyn Δημοσ. 15 Μαρτίου 2014 Moderators Δημοσ. 15 Μαρτίου 2014 και το title στο κενό string Δε χρειάζεται το gets, σου ζητάει να το αρχικοποιήσεις στο κενό string. Στη C, τα strings είναι null-terminated, δηλαδή ο τελευταίος χαρακτήρας είναι ο \0. Αφού θες το κενό string, αρκεί να βάλεις το \0 στον πρώτο χαρακτήρα. Δηλαδή: dvds->dvd.title[0] = '\0';
Flash3 Δημοσ. 15 Μαρτίου 2014 Μέλος Δημοσ. 15 Μαρτίου 2014 Ετσι?? dvds->dvd.title[0]='\0΄; Αυτο το dvd το βάζω επειδη θα τρέχει η for και θα αρχικοποιεί τους πίνακες και στις 5 θεσεις μνήμης που δεύσμευσα για αυτά τα δεδομένα..
Flash3 Δημοσ. 15 Μαρτίου 2014 Μέλος Δημοσ. 15 Μαρτίου 2014 int i,y; dvdstruct dvds; initDvds(&dvds); do{ y=displayMainMenu(); if(y==1) insertMovie(&dvds); if(y==2) printMovies(&dvds); }while(y!=0); }void initDvds(dvdstruct *dvds){ int i,j; dvds->dvd=(dvdtype*)malloc(5*(sizeof(dvdtype))); dvds->numdvds=0; for(i=0;i<5;i++) { dvds->dvd.customerID=-1; dvds->dvd.daysowned=-1; dvds->dvd.dvdcode=-1; dvds->dvd.title[0]='\0'; } }void insertMovie(dvdstruct *dvds){ //char s; //int counter; printf("Dwse tn kodiko tis tenias kai to onoma tis tenias \n"); scanf("%d ",&dvds->dvd[dvds->numdvds].dvdcode); //printf("Dwse to onoma tis tenias \n"); //while(s!='\n') // scanf("%c ",&s); gets(dvds->dvd[dvds->numdvds].title); dvds->numdvds++; if(dvds->numdvds ==5) ;}void printMovies(dvdstruct *dvds){ int i; if(dvds->numdvds==0) printf("Den exei tenies to katastima"); for(i=0;i<dvds->numdvds;i++) { printf("Dvdcode is :%d \n",dvds->dvd.dvdcode); printf("The name of the movie is: %s \n",dvds->dvd.title); }} Εχω αυτο το προγραμμα πλεον και εχω και ενα μενου το οποιο δεν ανεβασα...Με την insertMovie ουσιαστικα εισαγω τενιες στον πινακα μου και με την printMovie της τυπωνω..Αυτα μου δουλευον...Θελω όμως όταν εισάγω 5 τενιες ( dvds->numdvds++; if(dvds->numdvds ==5) ; ) και ο χρηστης ξαναδιαλέξει να εισαγει ταινια να κανω realloc και να αυξανω τον πίνακα μου κατα ενα και οταν ξαναδιαλεξει να εισαγει τενια να ξαναυξηθει..Απο ότι είδα αν έχω για παραδειγμα τον δυναμικο πινακα Α με Ν θεσεις μνημησ που δίνω απο το πληκτρολόγιο το realloc δημιουργει ενα νεο δυναμικο πινακα Β με Ν+1 ασ πουμε..καπως ετσι δηλαδη.. int *A=(int*)malloc ((N)*(sizeof(int))); το Β int *B=(int*)realloc(A,(N+1)*(sizeof(int))); Στη δικη μου περιπτωση που το Α είναι αυτο dvds->dvd=(dvdtype*)malloc(5*(sizeof(dvdtype))); ή Ν=5; dvds->dvd=(dvdtype*)malloc(N*(sizeof(dvdtype))); το Β μου που θελω να αυξάνεται καθε φορά που φτάνει το dvds->numdvds++ στο Ν...Πώς θα είναι..???
Προτεινόμενες αναρτήσεις
Δημιουργήστε ένα λογαριασμό ή συνδεθείτε για να σχολιάσετε
Πρέπει να είστε μέλος για να αφήσετε σχόλιο
Δημιουργία λογαριασμού
Εγγραφείτε με νέο λογαριασμό στην κοινότητα μας. Είναι πανεύκολο!
Δημιουργία νέου λογαριασμούΣύνδεση
Έχετε ήδη λογαριασμό; Συνδεθείτε εδώ.
Συνδεθείτε τώρα