| | |
| Stránka: 1 z 1
| [ Príspevkov: 14 ] | |
Autor | Správa |
---|
Registrovaný: 18.03.07 Prihlásený: 02.06.13 Príspevky: 264 Témy: 82 | Napísal svejk: 04.01.2012 22:33 | |
|
zdravim
mam tento program: Kód: int main(void){ struct osoba{ char meno[20],priezvisko[20]; int vek; };
int n; puts("zadaj maximalny pocet poloziek"); scanf("%d", &n);
struct osoba pole[n]; int poradie=1,i=0; while (i<n){ printf("zadaj meno %d osoby\n", poradie); fgets(pole[i].meno, 19, stdin); printf("zadaj priezvisko %d osoby\n", poradie); fgets(pole[i].priezvisko, 19, stdin); printf("zadaj vek %d osoby", poradie); scanf("%d", &pole[i].vek); i++; poradie++; }
printf("%s%s%d", pole[1].meno, pole[1].priezvisko, pole[1].vek);
return 0; }
nefunguje nacitanie do typu struktura cezprikaz fgets, akoby to na zadany udaj necakalo, help pls.
diki
|
|
Registrovaný: 11.01.09 Prihlásený: 28.03.24 Príspevky: 1385 Témy: 9 Bydlisko: Hrinova | Napísal Fico: 05.01.2012 11:29 | |
|
Problem je v tom, ze na riadku:
Kód: scanf("%d", &n); Nacitavas len jeden udaj - cislo zo standardneho vstupu. Ty vsak napises cislo a stlacis enter. Ten enter ti ostava v bufferi na dalsie spracovanie. Ked sa dostanes na riadok: Kód: fgets(pole[i].meno, 19, stdin); skontroloje sa buffer, ci tam uz nieco nie je. Ak ano, precita data z neho. To znamena, do pole[i].meno sa v tomto pripade ulozi spominany enter ( presnejsie povedane, znak noveho riadku ). To iste sa stane pri dalsom scanf, pri nacitani veku, opat v bufferi ostane novy riadok. Mozno sa pytas, preco sa nieco taketo nestane aj po volani funkcie fgets. Jednoducho preto, pretoze ta skopiruje vsetko az po nulovy znak ( koniec retazca ), pripadne maximalne 19 znakov a nulovy znak automaticky prida nakoniec sama. Cize precita sa aj spominany novy riadok - staci si vsimnut, ze ak napises napr meno "svejk", tak vyzva na napisanie priezviska je uz na dalsom riadku, pretoze sa precita "svejk[ENTER]". Aby si tomu predisiel, staci po volani funkcie scanf vyprazdnit vstupny buffer. Napis si nasledujucu funkciu: Kód: void flush_stdin() {
int c; while ( ( c = getchar() ) != '\n' && c != EOF );
} ktoru jednoducho volaj po kazdom volani funkcie scanf: Kód: scanf( "%d", &n); flush_stdin();
|
|
Registrovaný: 18.03.07 Prihlásený: 02.06.13 Príspevky: 264 Témy: 82 | Napísal autor témy svejk: 05.01.2012 12:14 | |
|
nakoniec som to robil trochu pochopitelnejsie pre mna a sice touto funkciou: Kód: void deleteEnter(char *string) { char *znak = strrchr(string, '\n'); *znak = '\0'; no a zo scanf som to odstranoval pomocou Kód: scanf("%*c");
tomu s tym scanf nerozumiem (nasiel som to iba v jednom programe) ale vobec netusim jak to ze to robi to co chceme. co je to %*c??
diki
|
|
Registrovaný: 11.01.09 Prihlásený: 28.03.24 Príspevky: 1385 Témy: 9 Bydlisko: Hrinova | Napísal Fico: 05.01.2012 12:45 | |
|
Ale ako chces pomocou tvojej funkcie deleteEnter zmazat vstup zo vstupneho buffra, ked ako argument davas retazec? Myslim, ze ti ta funkcia velmi nepomoze.
svejk píše: co je to %*c? "An optional starting asterisk indicates that the data is to be retrieved from stdin but ignored, i.e. it is not stored in the corresponding argument." - znamena to, ze sa precita dalsi znak ( iba jeden ) z buffra, ale neulozi sa do dalsej premennej, bude ignorovany. Ak bude v buffri len znak noveho riadku, fajn, tento postup ti pomoze, ale co v pripade, ze tam bude este nieco? Opat dostanes chybny vstup. Teraz napisem dve verzie tvojho programu, len ho trocha skratim, aby tam nebol zbytocn cyklus. Spust si najprv prvy, potom druhy s tym, ze po vyzve "zadaj maximalny pocet poloziek", zadaj toto: Citácia: 3 totojedlhypreklep
Tvoja verzia s pouzitim scanf( "%*c" ) :
Kód: #include <stdio.h>
int main(void){
struct osoba{ char meno[20],priezvisko[20]; int vek; };
int n; puts("zadaj maximalny pocet poloziek"); scanf( "%d%*c", &n );
struct osoba pole[n];
printf( "zadaj meno prvej osoby\n" ); fgets( pole[0].meno, 19, stdin ); printf( "zadaj priezvisko prvej osoby\n" ); fgets( pole[0].priezvisko, 19, stdin) ; printf( "zadaj vek prvej osoby\n" ); scanf( "%d%*c", &pole[0].vek );
printf( "\n\nMeno = %s Priezvisko = %s Vek = %d\n", pole[0].meno, pole[0].priezvisko, pole[0].vek ); return 0;
} Moja verzia s vyprazdnenim celeho buffra :Kód: #include <stdio.h>
void flush_stdin() {
int c; while ( ( c = getchar() ) != '\n' && c != EOF );
}
int main(void){
struct osoba{ char meno[20],priezvisko[20]; int vek; };
int n; puts("zadaj maximalny pocet poloziek"); scanf( "%d", &n ); flush_stdin();
struct osoba pole[n];
printf( "zadaj meno prvej osoby\n" ); fgets( pole[0].meno, 19, stdin ); printf( "zadaj priezvisko prvej osoby\n" ); fgets( pole[0].priezvisko, 19, stdin) ; printf( "zadaj vek prvej osoby\n" ); scanf( "%d", &pole[0].vek ); flush_stdin();
printf( "\n\nMeno = %s Priezvisko = %s Vek = %d\n", pole[0].meno, pole[0].priezvisko, pole[0].vek ); return 0;
} Vsimol si si rozdiel? V druhom pripade moze byt cokolvek v buffri, zmaze sa to vsetko. Ak vravis, ze to je pre teba tazkopadne pochopit, pokusim sa ti to vysvetlit, pretoze to ozaj nie je nic komplikovane. Je to iba jedna jednoducha slucka: Kód: while ( ( c = getchar() ) != '\n' && c != EOF );
getchar() je funkcia, ktora nacita znak z buffra stdin. Znak sa ulozi do premennej c a nasledne sa kontroluje, ci sa nerovna '\n', co je znak noveho riadku, pripadne ci sa nerovna znaku EOF, co je signal, ze uz nie je co citat - to znamena buffer je prazdny. A kedze je to cele v podmienke while, bude sa citat cely buffer, pokial nenarazi na novy riadok, pripadne kym nedojde po koniec. To je cela veda.
|
|
Registrovaný: 18.03.07 Prihlásený: 02.06.13 Príspevky: 264 Témy: 82 | Napísal autor témy svejk: 05.01.2012 13:10 | |
|
a funkcia getchar automaticky aj vymaze ten hladany znak \n?
tu moju funkciu som pouzival po prikaze fgets...
|
|
Registrovaný: 11.01.09 Prihlásený: 28.03.24 Príspevky: 1385 Témy: 9 Bydlisko: Hrinova | Napísal Fico: 05.01.2012 13:26 | |
|
Ano, vymaze, ale to spravi kazda funkcia, aj scanf napriklad. Ak sa nieco precita z buffra, automaticky to z neho aj odstrani. Ak si tu funkciu pouzival az potom, v poriadku. Sam sa rozhodni, aky postup budes pouzivat, ja som sa len snazil vysvtelit, co sa vlastne deje. Ak si tomu pochopil, uz si sam dokazes navrhnut riesenie.
_________________ Ak potrebujete pomoc s diagnostikou/opravou vasej elektroniky ( notebook, motherboard, GPU, a ine ), kontaktujte ma cez SS. |
|
Registrovaný: 18.03.07 Prihlásený: 02.06.13 Príspevky: 264 Témy: 82 | Napísal autor témy svejk: 05.01.2012 22:23 | |
|
diki moc
|
|
Registrovaný: 18.03.07 Prihlásený: 02.06.13 Príspevky: 264 Témy: 82 | Napísal autor témy svejk: 08.01.2012 16:12 | |
|
dobre, takze zapocet spraveny... teraz to potrebujem realnesie pochopit.
mali nasa uloha s casti spocivala v nacitani dat zo zuboru do strukturovanej premennej. Robil som to pomocou fgets. ten by mal kurzor vzdy aj premiestnit na dalsi riadok ci?
nacitaval som nasledovne:
Kód: typedef struct info { char dodavatel[20], mesto[20], produkt[20]; int cena, pocet; }info;
info pole[10];
int main()
{ FILE *subor;
subor=fopen("data.txt", "r");
int ukon; puts("1. pre info o dodavatelovi"); puts("2. pre info o produkte"); puts("3. pre najdenie najlacnejsieho skladu podla produktu"); puts("4. pre koniec");
scanf("%d", &ukon);
//nacita veci zo suboru do structury for(int i=0; i<=7; i++){ fgets(pole[i].dodavatel, 19, subor); fgets(pole[i].mesto, 19, subor); fgets(pole[i].produkt, 19, subor); fgets(pole[i].pocet, 19, subor); fgets(pole[i].cena, 19, subor); }
printf("%s", pole[0].cena);
nakonci len pre kontrolu vypis nejakeho prvku. nevypisuje to tu hodnotu ktoru by som chcel..
subol vyzeral nasledovne:
Elektrosopa Brno telka 100 18000 Elektrosopa Praha telka 300 17300 KplusK Brno telka 430 19000 KplusK Brno dvd 430 1000 KplusK Brno pekarna 130 1489.45 KplusK Ostrava pekarna 120 1889.90 Najlacnejsi Pardubice pekarna 130 1429.60
moja myslienka bola najskor to vsetko nacitat do tej struktury a potom uz iba previest pozadovane operacie.. haldanie najnizsej ceny, vyhladanie skladu atd...
len pre info: data v subore su v tom poradi ako idu zasebou fkcie fgets teda.. dodavatel, mesto, produkt, pocet na sklade, cena...
program bol len na demonstraciu toho ci to vieme, v reale by mal zvladat aj keby tam bolo tych poloziek 1000
preco nefunguje teda dobre to nacitavanie?? asi tam je nejaky problem s polohou kurzoru..
diki
|
|
Registrovaný: 11.01.09 Prihlásený: 28.03.24 Príspevky: 1385 Témy: 9 Bydlisko: Hrinova | Napísal Fico: 08.01.2012 16:41 | |
|
Ked ti poviem, kde je problem, tak sa zasmejes
Kód: int cena, pocet; Kód: fgets(pole[i].pocet, 19, subor); fgets(pole[i].cena, 19, subor); Kód: printf("%s", pole[0].cena); S premennymi cena a pocet v strukture info pracujes ako s retazcom, kdezto v strukture su definovane ako int. Staci iba zmenit ich definiciu a vsetko pojde spravne: Kód: typedef struct info { char dodavatel[20], mesto[20], produkt[20]; char cena[20], pocet[20]; } info;
|
|
Registrovaný: 18.03.07 Prihlásený: 02.06.13 Príspevky: 264 Témy: 82 | Napísal autor témy svejk: 08.01.2012 17:16 | |
|
jeziiis, no tak tomu ver, vobec som si to neuvedomil... , mohol som mat o 5 bodou viac..
|
|
Registrovaný: 18.03.07 Prihlásený: 02.06.13 Príspevky: 264 Témy: 82 | Napísal autor témy svejk: 13.01.2012 13:46 | |
|
este jednu vec potrebujem...
nebudem davat cely kod.. je dlhy, dam iba cast ktora nefunguje, pritom by podlamna mala...
Kód: case 3:
for(int d = 0; d<=7; d++){ pole[d].intcena = atoi(pole[d].cena); pole[d].intpocet = atoi(pole[d].pocet);
//strcpy(pole[d].intcena, pole[d].cena); //strcpy(pole[d].intpocet, pole[d].pocet); } puts("zadaj nazov produktu"); scanf("%s", &nazov1);
for (n=0; n<=7; n++){ if(strstr(pole[n].produkt, nazov1)!=NULL){ cena[indexc]=pole[n].intcena; indexc++; } }
najlacnejsi=cena[0];
for(n=0; n<=9; n++){ if (cena[n]>najlacnejsi){ cena[n]=najlacnejsi; } }
printf("\nzadany produkt: %s ma najnizsiu cenu %dkc,-\n", nazov1, najlacnejsi);
}
vypisuje to cenu, len nie najnizsiu, vypise to prvu co to najde..
poradte..
diki
|
|
Registrovaný: 27.12.08 Prihlásený: 13.12.22 Príspevky: 1874 Témy: 96 Bydlisko: Bratislava,... | Napísal nBXXL: 13.01.2012 15:03 | |
|
kontroluješ si vôbec čo píšeš?
úplne opačne máš ten if na konci..
keď už tak Kód: { if ( cena[n] < najlacnejsi ) najlacnejsi = cena[n]; }
_________________ ~Listen to your brain, not your heart~ NB1: Lenovo Y500: CPU: Intel Core i7-3630QM; GPU: nVidia GT650M 2GB SLi; RAM: 16GB DDR3; HDD: 1TB + 256GB SSD (m4); LCD: 15,6" 1920x1080; OS: Win8.1 64-bit + Arch Linux 64-bit (UEFI Powered DualBoot) NB2: Asus K53SJ-SX093: CPU: Intel Core i3-2310M; GPU: Intel HD3000 / nVidia GT520M 1GB Optimus; RAM: 8GB DDR3; SSD: 128GB 840Evo; LCD: 15,6" 1366x768; OS: Win 8.1 Pro 64-bit (UEFI) |
|
Registrovaný: 18.03.07 Prihlásený: 02.06.13 Príspevky: 264 Témy: 82 | Napísal autor témy svejk: 13.01.2012 15:21 | |
|
hej, to uz som si vsimol.. to som len zabudol zmenit ked som vselico s tym skusal..
naprava neriesi problem..
|
|
Registrovaný: 27.12.08 Prihlásený: 13.12.22 Príspevky: 1874 Témy: 96 Bydlisko: Bratislava,... | Napísal nBXXL: 13.01.2012 15:50 | |
|
neviem ako to kompiluješ, ale problém by mohlo robiť to, že neinicializuješ indexc, ďalej, že pole cena[] je zbytočne veľké (prehľadávaš 9 prvkov, hoci viac ako 7 tam aj tak nenatrepeš, lebo tam hádžeš prvky zo 7-prvkového poľa pole[])..
po tej náprave to fungovať musí.. hľadáš najmenší prvok v poli či nie?
zopár rád:
- keď tie ceny môžu byť aj reálne čísla (demonštroval si to v príspevku vyššie), prečo používaš atoi?
- písal si, že v reále by mal zvládať aj 1000 položiek, no nepíšeš to takým spôsobom.. odporúčam ti dať si nejakú premennú, do ktorej uložíš počet položiek a potom v cykloch používať tú.. v prípade, že sa ti zmení počet položiek potom nemusíš prepisovať X cyklov
_________________ ~Listen to your brain, not your heart~ NB1: Lenovo Y500: CPU: Intel Core i7-3630QM; GPU: nVidia GT650M 2GB SLi; RAM: 16GB DDR3; HDD: 1TB + 256GB SSD (m4); LCD: 15,6" 1920x1080; OS: Win8.1 64-bit + Arch Linux 64-bit (UEFI Powered DualBoot) NB2: Asus K53SJ-SX093: CPU: Intel Core i3-2310M; GPU: Intel HD3000 / nVidia GT520M 1GB Optimus; RAM: 8GB DDR3; SSD: 128GB 840Evo; LCD: 15,6" 1366x768; OS: Win 8.1 Pro 64-bit (UEFI) |
|
| Stránka: 1 z 1
| [ Príspevkov: 14 ] | |
| Nemôžete zakladať nové témy v tomto fóre Nemôžete odpovedať na témy v tomto fóre Nemôžete upravovať svoje príspevky v tomto fóre Nemôžete mazať svoje príspevky v tomto fóre
|
|