Mathex319 Mathex319 - 4 years ago 86
C Question

I don't understand what's not working

So I have been coding for an assignment I have to turn in at school, and I came up to this point, whenever I try to launch this with the debugger, nothing happens, the program shows that he is proceeding with no errors what so ever, this still doesn't want to start.

I'm working in Microsoft Visual Studio 2015 (Provided by school, cannot use other programs as we need to work in this one).

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "Header.h"

typedef struct song {
int id;
char title[32];
char artist[32];
int yearOfRelease;
} Song;

int main() {
int capacity = 15;
int menuanswer = 0;
int numberOfSongs = 0;

Song *songs;
songs = (Song *)malloc(capacity * sizeof(Song));

songs[0].id = 0;
strcpy(songs[0].title, "Hear me now");
strcpy(songs[0].artist, "Alok");
songs[0].yearOfRelease = 2016;

while (menuanswer != 4) {
printf("Welcome to your favorite songs browser\n"
"What do you wanna do next?\n"
"1.Browse playlist\n"
"2.Add a song\n"
"3.Delete a song\n"
"4.Exit the program\n");
scanf("%d", &menuanswer);

switch (menuanswer) {
case 1:
printf("This is your playlist\n");
for (int i = 0; i < numberOfSongs; i++) {
printf("\nID of the song: %d", songs[i].id);
printf("\nName of the song: %s", songs[i].title);
printf("\nArtist of the song: %s", songs[i].artist);
printf("\nYear of the songs release: %d", songs[i].yearOfRelease);

getchar();
}
break;
case 2:
AddSong(songs);
numberOfSongs++;
break;
case 3:
break;
DeleteSong(songs);
case 4:
printf("\nThank you for using this program, Goodbye");
break;
default:
printf("Please choose one of the numbers provided in the Main Menu");
break;
}
}
getchar();
return 0;
}

void AddSong(Song songs) {
int amount = 0;

printf("Please enter in the song ID:\n");
scanf("%s", &songs.id);

printf("Please enter in your songs title;\n");
fflush(stdin);
fgets(songs.title, amount, stdin);

for (amount = 0; amount < 20; amount++) {
if (songs.title[amount] == '\n')
songs.title[amount] = '\0';
}

printf("What artist made this song?:\n");
scanf("%s", &songs.artist);
getchar();

printf("What year was your song released?:\n");
scanf("%s", &songs.yearOfRelease);
getchar();

printf("Song Sucessfully added to your playlist");
}

void DeleteSong(Song songs) {
printf("Here you can choose which song you want to delete:\n");
printf("Please choose the song ID you want to delete");
scranf("%d", songs.id);
getchar();
}


And this is my Header

#ifndef GUARD
#define ADDSONGS
#define DELETESONG
void AddSong(Song songs);
void DeleteSong(Song songs);
#endif


If someone could help me out I'd appreciate it,
Also I need to have that struct and void there as there are called as my teachers told me I need to be there and I cannot use other names or codes for them.

I'd also appreciate if you'd take it easy for me as I am new.

Answer Source

There are multiple problems in your program:

  • The case number 3 is incorrect: the break; statement should be moved after the call to DeleteSong(songs);

  • The function `DeleteSong`` should take the song array as an argument along with the number of songs present.

  • The function AddSong should potentially reallocate the song array if it is full and take a pointer to the first available entry.

  • fflush(stdin); has undefined behavior. To consume the pending newline, use this: int c; while ((c = getchar()) != EOF && c != '\n') { continue; }

  • when reading a string with scanf into an array, pass it directly as the array decays into a pointer to its first element, but provide scanf the maximum number of characters to store into the array before the null terminator to avoid potential buffer overflows, and check the return value:

    if (scanf("%31s", songs.artist) != 1) {
        // handle premature end of file
        ...
    }
    
  • in case 2, you should reallocate the array if numberOfSongs == capacity.

Your code should not compile as you call AddSong and DeleteSong with an incompatible argument type. The compiler should at least produce warnings. Try increasing the warning level. Also the typo on scranf should definitely cause a compilation error... There is something you are not telling us.

Here is a corrected version, still incomplete...

Header.h:

#ifndef GUARD
#define ADDSONGS
#define DELETESONG
int AddSong(Song *song);
int DeleteSong(Song *songs, int numberOfSongs);
#endif

main.c:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "Header.h"

typedef struct song {
    int id;
    char title[32];
    char artist[32];
    int yearOfRelease;
} Song;

int main(void) {
    int capacity = 15;
    int menuanswer = 0;
    int numberOfSongs = 0;

    Song *songs = malloc(capacity * sizeof(Song));
    if (songs == NULL) {
        printf("cannot allocate song array\n");
        return 1;
    }

    songs[0].id = 0;
    strcpy(songs[0].title, "Hear me now");
    strcpy(songs[0].artist, "Alok");
    songs[0].yearOfRelease = 2016;
    numberOfSongs = 1;

    printf("Welcome to your favorite songs browser\n");

    for (;;) {
        printf("What do you wanna do next?\n"
               "1.Browse playlist\n"
               "2.Add a song\n"
               "3.Delete a song\n"
               "4.Exit the program\n");

        if (scanf("%d", &menuanswer) != 1 || menuanswer == 4) {
            break;

        switch (menuanswer) {
          case 1:
            printf("This is your playlist\n");
            for (int i = 0; i < numberOfSongs; i++) {
                printf("ID of the song: %d\n", songs[i].id);
                printf("Name of the song: %s\n", songs[i].title);
                printf("Artist of the song: %s\n", songs[i].artist);
                printf("Year of the songs release: %d\n", songs[i].yearOfRelease);
                printf("\n");
                getchar();
            }
            break;
          case 2:
            if (numberOfSongs == capacity) {
                Song *new_songs;
                new_songs = realloc(songs, capacity * 2 * sizeof(*songs));
                if (new_songs == NULL) {
                    printf("cannot reallocate song array\n");
                    break;
                }
                songs = new_songs;
                capacity *= 2;
            }
            numberOfSongs += AddSong(&songs[numberOfSongs]);
            break;
          case 3:
            numberOfSongs = DeleteSong(songs, numberOfSongs);
            break;
          default:
            printf("Please choose one of the numbers provided in the Main Menu\n");
            break;
        }
    }
    printf("\nThank you for using this program, Goodbye");
    getchar();
    return 0;
}

int AddSong(Song *song) {
    int i, c;

    printf("Please enter in the song ID:\n");
    if (scanf("%d", &song->id) != 1)
        return 0;
    while ((c = getchar()) != EOF && c != '\n')
        continue;
    printf("Please enter in your songs title:\n");
    for (i = 0; ((c = getchar()) != EOF && c != '\n'; i++) {
        if (i < sizeof(song->title) - 1)
            song->title[i] = c;
    }
    song->title[i] = '\0';

    printf("What artist made this song?\n");
    for (i = 0; ((c = getchar()) != EOF && c != '\n'; i++) {
        if (i < sizeof(song->artist) - 1)
            song->artist[i] = c;
    }
    song->artist[i] = '\0';

    printf("What year was your song released?\n");
    if (scanf("%d", &songs.yearOfRelease) != 1)
        return 0;
    getchar();

    printf("Song Successfully added to your playlist\n");
    return 1;
}

int DeleteSong(Song *songs, int numberOfSongs) {
    int id;
    printf("Please choose the song ID you want to delete");
    scanf("%d", &id);
    /* write the code to remove the entry by shifting the
       next elements to lower index values
       and return the new number of songs
    */
    getchar();
    return numberOfSongs;
}
Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download