Yleiset I/O-sudenkuopat
Puskuri- ja rivinvaihto-ongelmat.
Yleiset I/O-sudenkuopat on ilmainen C Academy-oppitunti CoddyKitissä. Tämä on oppitunti 4/4. Voit lukea koko oppitunnin alta ilmaiseksi ja harjoitella sen jälkeen käytännössä selaimessa sisäänrakennetulla koodieditorilla ja ympäri vuorokauden käytettävissä olevan tekoälytuutorin avulla. Oppitunti kuuluu C Academy-oppimispolkuun, ja edistymisesi synkronoituu verkon ja CoddyKit-sovelluksen välillä. C Academy-kurssilla on yhteensä 4 oppituntia.
Yleiset I/O-ongelmat
C-kielen syötteessä ja tulosteessa on muutamia klassisia kompastuskiviä. Niiden tunteminen säästää tuntikausia virheenkorjauksessa.
#include <stdio.h>
int main(void) {
printf("Let us study I/O pitfalls\n");
return 0;
}Puskuriin jäänyt rivinvaihto
scanf("%d", ...)-kutsun jälkeen Enter-näppäin jättää puskuriin merkin \n. Myöhempi %c lukee tämän rivinvaihdon oikean syötteen sijaan.
#include <stdio.h>
int main(void) {
char c = 'A';
printf("Use a space before %%c to skip the leftover newline\n");
printf("c = %c\n", c);
return 0;
}Korjaaminen välilyönnillä
Kun kirjoitatte scanf(" %c", &c), alussa oleva välilyönti käskee scanf-funktiota ohittamaan ensin tyhjemerkit.
#include <stdio.h>
int main(void) {
char c = 'Z';
printf("scanf(\" %%c\", &c) skips whitespace\n");
printf("c = %c\n", c);
return 0;
}Et-merkinnän unohtaminen
Muuttujan välittäminen scanf-funktiolle ilman &-merkkiä tallentaa tiedon väärään osoitteeseen ja aiheuttaa todennäköisesti ohjelman kaatumisen.
#include <stdio.h>
int main(void) {
int n = 9;
printf("Always pass &n, not n, to scanf for an int\n");
printf("n = %d\n", n);
return 0;
}Määritteiden yhteensopimattomuus
Doublen lukeminen määritteellä %f määritteen %lf sijaan scanf-funktiossa turmelee arvon. Tulostuksessa molemmille käytetään %f-määritettä, mutta syötteessä ne eroavat toisistaan.
#include <stdio.h>
int main(void) {
double d = 2.5;
printf("scanf needs %%lf for double; printf uses %%f\n");
printf("d = %.1f\n", d);
return 0;
}Tulosteen puskurointi
Tuloste voidaan puskuroida, jolloin se ei näy heti. Lopettaminen merkkiin \n tai kutsu fflush(stdout) tyhjentää puskurin.
#include <stdio.h>
int main(void) {
printf("Flushed by newline\n");
fflush(stdout);
return 0;
}gets on vaarallinen
Vanha gets-funktio ei tarkistanut rajoja, ja se on poistettu nykyaikaisesta C-kielestä. Käyttäkää sen sijaan fgets-funktiota.
#include <stdio.h>
int main(void) {
char buf[10];
/* fgets(buf, sizeof buf, stdin); */
buf[0] = 'H'; buf[1] = 'i'; buf[2] = 0;
printf("buf = %s\n", buf);
return 0;
}Puskuriylivuoto %s-määritteellä
Pelkkä %s scanf-funktiossa voi kirjoittaa pienen taulukon rajojen yli. Rajoittakaa pituutta leveydellä, kuten %19s.
#include <stdio.h>
int main(void) {
char name[20];
printf("Use %%19s to leave room for the null terminator\n");
name[0] = 0;
printf("name length cap protects buffer\n");
return 0;
}fgets säilyttää rivinvaihdon
fgets tallentaa lopussa olevan rivinvaihdon. Se on usein poistettava erikseen.
#include <stdio.h>
#include <string.h>
int main(void) {
char line[] = "hello\n";
line[strcspn(line, "\n")] = 0;
printf("[%s]\n", line);
return 0;
}Palautusarvojen huomiotta jättäminen
scanf-funktion palautusarvon tarkistamatta jättäminen päästää virheellisen syötteen läpi huomaamatta. Tarkistakaa se aina.
#include <stdio.h>
int main(void) {
int n = 3;
int items = 1;
if (items != 1)
printf("bad input\n");
else
printf("ok: %d\n", n);
return 0;
}Kokonaisuuden turvallinen yhdistäminen
Luotettava toimintamalli on seuraava: lukekaa fgets-funktiolla, jäsentäkää sscanf-funktiolla ja tarkistakaa tulos.
#include <stdio.h>
int main(void) {
char line[] = "123";
int n;
if (sscanf(line, "%d", &n) == 1)
printf("parsed %d\n", n);
return 0;
}Pikatarkistus
Testatkaa, miten hyvin ymmärrätte I/O:n kompastuskivet.
Kertaus: yleiset I/O-kompastuskivet
Opitte välttämään yleisiä virheitä.
- Puskuriin jääneet rivinvaihdot sekoittavat
%c-määritteen; käyttäkää alussa välilyöntiä - Välittäkää osoitteet aina
&-merkin kanssa - Käyttäkää
%lf-määritettä double-arvojen lukemiseen - Suosikaa
fgets-funktiotagets-funktion sijaan ja rajoittakaa%s-määritteen pituutta - Tarkistakaa palautusarvot ja tyhjentäkää tulostuspuskuri
Opi C tekoälytuutorin avulla — ilmaiseksi
Kirjoita ja suorita oikeaa koodia selaimessa, saa välitöntä apua tekoälytuutorilta ympäri vuorokauden ja jatka siitä, mihin jäit, verkossa tai sovelluksessa.
- Kurssit
- 39
- Oppitunnit
- 144
Usein kysytyt kysymykset
Onko oppitunti ”Yleiset I/O-sudenkuopat” ilmainen?
Kyllä – oppitunnin ”Yleiset I/O-sudenkuopat” koko tekstin voi lukea täällä verkossa ilmaiseksi. Jos haluat harjoitella interaktiivisesti sisäänrakennetulla koodieditorilla ja ympäri vuorokauden käytettävissä olevan tekoälytuutorin avulla sekä avata koko C Academy-kurssin, päivitä CoddyKit PROhon. C Academy-kurssilla on yhteensä 4 oppituntia.
Mitä opin oppitunnilla ”Yleiset I/O-sudenkuopat”?
Puskuri- ja rivinvaihto-ongelmat. Harjoittelet C Academy-aihetta koodilla, jonka suoritat suoraan selaimessa. Ympäri vuorokauden käytettävissä oleva tekoälytuutori vastaa kysymyksiisi oppitunnin aikana.
Tarvitsenko kokemusta aloittaakseni C Academy-opiskelun?
Aiempi kokemus ei ole tarpeen. CoddyKitin C Academy-oppimispolku sopii vasta-alkajista edistyneisiin, joten voit aloittaa tästä tai alusta ja edetä omaan tahtiisi. Tämä on oppitunti 4/4.
Kuinka kauan ”Yleiset I/O-sudenkuopat”-oppitunnin suorittaminen kestää?
Useimmat CoddyKitin oppitunnit kestävät noin 5–10 minuuttia. Jokainen oppitunti on lyhyt ja interaktiivinen, joten edistyt tasaisesti ja voit jatkaa siitä, mihin jäit – sekä verkossa että sovelluksessa.
Voinko kirjoittaa ja suorittaa koodia tällä C Academy-oppitunnilla?
Kyllä. Jokainen C Academy-oppitunti sisältää sisäänrakennetun koodieditorin, joten voit kirjoittaa ja suorittaa oikeaa koodia suoraan selaimessa ja saada välitöntä palautetta tekoälyltä – paikallista asennusta ei tarvita.
Kaikki tämän kurssin oppitunnit
- printf-muotoilumääritteet
- scanf ja syöte
- Leveys, tarkkuus ja liput
- Yleiset I/O-sudenkuopat