Lösningsförslag till datorövning 1 i Programmeringsmetodik ---------------------------------------------------------- Övning 1 A ---------- // Strang.c int strlangd(char *s) { int i = 0; while (s[i] != '\0') ++i; return i; } // Strangtest.c #include #include int strlangd(char *s); int main(void) { char indata[30 + 1]; printf("Skriv en rad: "); gets(indata); // Övning: Varför ska man egentligen inte använda gets? Hur ska man göra i stället? printf("Strängens längd = %d\n", strlangd(indata)); // För Visual Studio printf("Tryck på ENTER för att avsluta: "); _getch(); return 0; } Övning 1 C ---------- // Strang.h int strlangd(char *s); void strkopia(char *to, char *from); // Strang.cpp #include "Strang.h" int strlangd(char *s) { int i = 0; while (s[i] != '\0') ++i; return i; } void strkopia(char *to, char *from) { int i; for (i = 0; from[i] != '\0'; ++i) to[i] = from[i]; to[i] = '\0'; } // Strangtest.cpp #include #include #include "Strang.h" int main(void) { char indata[30 + 1]; char kopia[30 + 1]; printf("Skriv en rad: "); gets(indata); // Övning: Varför ska man egentligen inte använda gets? Hur ska man göra i stället? printf("Strängens längd = %d\n", strlangd(indata)); strkopia(kopia, indata); printf("Kopian = %s\n", kopia); // För Visual Studio printf("Tryck på ENTER för att avsluta: "); _getch(); return 0; } Övning 1 D ---------- // Medlem.h #define MAX_NAMN 30 #define MAX_TELEFON 20 struct Medlem { int medlemsnummer; char namn[MAX_NAMN + 1]; char telefon[MAX_TELEFON + 1]; }; typedef struct Medlem Medlem; void las_medlem(Medlem *mp); void skriv_medlem(Medlem *mp); // Medlem.cpp #include #include #include "Medlem.h" // Kanske en lite väl ambitiös lösning på strängläsningen, // men det blir lite krångligt om alla fall ska hanteras rätt. void las_rad_med_max_langd(char *plats, int maxlangd) { int antal = 0; int c; while ((c = getchar()) != '\n' && c != EOF && antal < maxlangd) { plats[antal++] = c; } plats[antal] = '\0'; if (c != '\n' && c != EOF) { while ((c = getchar()) != '\n' && c != EOF) ; } } void las_medlem(Medlem *mp) { printf("Ange medlemsnummer: "); scanf("%d", &mp->medlemsnummer); while (getchar() != '\n') ; printf("Ange namnet: "); las_rad_med_max_langd(mp->namn, MAX_NAMN); printf("Ange telefonnumret: "); las_rad_med_max_langd(mp->telefon, MAX_TELEFON); } void skriv_medlem(Medlem *mp) { printf("Medlemsnummer: %d\n", mp->medlemsnummer); printf("Namn: %s\n", mp->namn); printf("Telefon: %s\n", mp->telefon); } // Medlemstest.cpp #include #include "Medlem.h" int main(void) { Medlem m; las_medlem(&m); skriv_medlem(&m); return 0; } Övning 1 E ---------- // Medlem.h #define MAX_NAMN 30 #define MAX_TELEFON 20 struct Medlem { int medlemsnummer; char namn[MAX_NAMN + 1]; char telefon[MAX_TELEFON + 1]; }; typedef struct Medlem Medlem; void las_medlem(Medlem *mp); void skriv_medlem(Medlem *mp); int las_medlem_fil(FILE *tsin, Medlem *mp); void skriv_medlem_fil(FILE *tsut, Medlem *mp); // Medlem.cpp #include #include #include "Medlem.h" // Kanske en lite väl ambitiös lösning på strängläsningen, // men det blir lite krångligt om alla fall ska hanteras rätt. void las_rad_med_max_langd_fran_fil(FILE *tsin, char *plats, int maxlangd) { int antal = 0; int c; while ((c = getc(tsin)) != '\n' && c != EOF && antal < maxlangd) { plats[antal++] = c; } plats[antal] = '\0'; if (c != '\n' && c != EOF) { while ((c = getc(tsin)) != '\n' && c != EOF) ; } } void las_medlem(Medlem *mp) { printf("Ange medlemsnummer: "); scanf("%d", &mp->medlemsnummer); while (getchar() != '\n') ; printf("Ange namnet: "); las_rad_med_max_langd_fran_fil(stdin, mp->namn, MAX_NAMN); printf("Ange telefonnumret: "); las_rad_med_max_langd_fran_fil(stdin, mp->telefon, MAX_TELEFON); } void skriv_medlem(Medlem *mp) { printf("Medlemsnummer: %d\n", mp->medlemsnummer); printf("Namn: %s\n", mp->namn); printf("Telefon: %s\n", mp->telefon); } int las_medlem_fil(FILE *tsin, Medlem *mp) { if (fscanf(tsin, "%d", &mp->medlemsnummer) != 1) return 0; int c; while ((c = getc(tsin)) != '\n' && c != EOF) ; las_rad_med_max_langd_fran_fil(tsin, mp->namn, MAX_NAMN); las_rad_med_max_langd_fran_fil(tsin, mp->telefon, MAX_TELEFON); return 1; } void skriv_medlem_fil(FILE *tsut, Medlem *mp) { fprintf(tsut, "%d\n", mp->medlemsnummer); fprintf(tsut, "%s\n", mp->namn); fprintf(tsut, "%s\n", mp->telefon); } // Medlemstest.cpp #include #include #include #include "Medlem.h" #define MAX_MEDLEMMAR 100 int main(void) { Medlem medlemmar[MAX_MEDLEMMAR]; int antal_medlemmar = 0; FILE *tsin = fopen("10-medlemmar.txt", "r"); if (tsin == NULL) { fprintf(stderr, "Kunde inte läsa filen '10-medlemmar.txt'\n"); exit(EXIT_FAILURE); } Medlem m; while (las_medlem_fil(tsin, &m) == 1) { if (antal_medlemmar == MAX_MEDLEMMAR) { fprintf(stderr, "För många medlemmar\n"); exit(EXIT_FAILURE); } medlemmar[antal_medlemmar++] = m; } fclose(tsin); FILE *tsut = fopen("ny-fil.txt", "w"); if (tsut == NULL) { fprintf(stderr, "Kunde inte skriva filen 'ny-fil.txt'\n"); exit(EXIT_FAILURE); } for (int i = 0; i < antal_medlemmar; ++i) { if (strncmp(medlemmar[i].telefon, "0158-", 5) != 0) skriv_medlem_fil(tsut, &medlemmar[i]); } fclose(tsut); return 0; }