-2

I'm trying to learn how to work with dynamic lists in C, but can't seem to wrap my head around it - so help would be appreaciated. I've got a struct that has some info that i'm reading from a txt file in the command line and would need to add the info to a dynamic list..

this is what i have so far. I'm at a loss with pointers and don't know if the arguments are correct and where to go from there.

Have spent the better part of the weekend looking for a way to get this done. It isn't hard as I get the concept, just that the nuts and bolts of it are just eluding me...

#include <stdio.h>
#include <stdlib.h>
#define SIZE_MAX  20
#define BUFFER_MAX 256
FILE *file;


/*struct*/
struct student {
char name[SIZE_MAX];
int grade;
struct student *next;
};

typedef struct student Student;



int addToList(Student **head, char *, int);
void printList(Student **head);
void releaseMem(Student **head);

/*functions*/
void addToList(Student **head, char *name, int grade ){

//???
}

/*Main*/

int main (int argc, char *argv[]){

Student *head=NULL,*tail=NULL;
int grade = 100 ;
char buffer [BUFFER_MAX];
char name[SIZE_MAX];


/*opening file*/
file = fopen(argv[1], "r");
if (file == NULL){
  printf("\n\tWARNING: No data found.\n");
  exit(1);
}
else{
    printf("Reading file %s \n",argv[1]);
}
/*creating first node*/

Student* new_student(Student*)malloc(sizeof(Student));


while(fgets(buffer, BUFFER_MAX,file)!= NULL){
  sscanf(buffer,"%s%d",name,&grade);
    //printf("%s %d\n",string, grade);
    addToList(&head,name,grade);
}

return 0;
}

Edit: So far I've managed to add the data from the file to a dynamic list (thank you for the help). Here is what I have:

#include <stdio.h>
#include <stdlib.h>
#define SIZE_MAX  20
#define BUFFER_MAX 256
FILE *file;


/*Struct*/
struct student {
char name[SIZE_MAX];
int grade;
struct student *next;
};

typedef struct student Student;



int addToList(Student **head, char *, int);
void printList(Student *head);
void releaseMem(Student *head);

/*functions*/
int addToList(Student **head, char *name, int grade ){

Student *new_student = malloc( sizeof( Student ) );
{
Student *new_student = malloc( sizeof( Student ) );
int success = new_student != NULL;


if ( success )
{
        strcpy( new_student->name, name );
        new_student->grade = grade;
        new_student->next = *head;
        *head = new_student;




}

return success;
}
}
void printList(Student *head){

Student * current = head;
int i = 1;

while (current != NULL) {
    printf("%d. Student: %s grade %d\n",i,current->name  ,current->grade);
            i++;
    current = current->next;
}

}


void releaseMem(Student *head){
Student * current = head;

    while (current != NULL) {
            free(current);
            current = current->next;
    }
printf("mem cleared.\n");


}

/*Main*/

int main (int argc, char *argv[]){

Student *head=NULL,*first=NULL, *temp = NULL;
int grade = 100 ;
char buffer [BUFFER_MAX];
char name[SIZE_MAX];


/*opening file*/
file = fopen(argv[1], "r");
if (file == NULL){
printf("\n\tWARNING: No data found.\n");
exit(1);
}
else{
printf("reading file %s. \n",argv[1]);
}
printf("data added to list.\n");
while(fgets(buffer, BUFFER_MAX,file)!= NULL){
sscanf(buffer,"%s%d",name,&grade);
addToList(&head,name,grade);

}

printList(head);
releaseMem(head);
return 0;
}

Works (almost) like i'd like it to work. For some reason the printList function prints the content of the file in reverse order and after fiddling with it for some time I don't know how to print it from the beginning to the end instead from the end to the beginning. I suppose it has to do with pointers but more than that i'm at a loss what to do... What am I missing here? How would I go about reversing the printing order with keeping the (formatting) as it currently is?

Aok_16
  • 35
  • 1
  • 3
  • `Student* new_student(Student*)malloc(sizeof(Student));` is not valid c. Missing "equals" sign somewhere... – Jean-François Fabre Feb 19 '17 at 20:28
  • 1
    don't need teh codez written for me, just point me in the write direction, honestly i'm lost with pointers at this point – Aok_16 Feb 19 '17 at 20:34
  • 1
    I've been trying to learn from fe. this http://www.learn-c.org/en/Linked_lists but just end up with a segmentation fault, and decided to start from scratch... – Aok_16 Feb 19 '17 at 20:36
  • Right here: https://stackoverflow.com/questions/562303/the-definitive-c-book-guide-and-list – 2501 Feb 19 '17 at 20:36

2 Answers2

0

you should allocate new students in the student list and place it to the last member's next like this :

//since we are adding new members after the last member in linked list 
//we are not going to change value of head so sending **head is not useful
void addToList(Student *head,char *name,int grade){
   Student *node;
   for(node = head; node->next != NULL; node = node->next );
   // now node points the last member of your linked list
   // now we are adding new student to the linked list with allocating memory  
  node->next = (Student *)malloc(sizeof(student));
  node->next->grade = grade;
  strcpy(node->next->name,name);
}
Khan9797
  • 600
  • 1
  • 4
  • 12
-1

The program will not compile at least because this statement

Student* new_student(Student*)malloc(sizeof(Student));

is invalid. And even if to write it like

Student* new_student = (Student*)malloc(sizeof(Student));

it does not make sense because new items should be added to the list by using the function addToList.

The declaration of the variable tail also does not make sense because it is impossible to pass it to the function (as it is declared) addToList along with the head.

As for the function itself then it is better to declare it the following way

int addToList( Student **head, const char *name, int grade );

The function can be defined like

int addToList( Student **head, const char *name, int grade )
{
    Student *new_student = malloc( sizeof( Student ) );
    int success = new_student != NULL;

    if ( success )
    {
        strcpy( new_student->name, name );
        // or
        // strncpy( new_student->name, name, SIZE_MAX );
        // new_student->name[SIZE_MAX - 1] = '\0';
        new_student->grade = grade;
        new_student->next = *head;
        *head = new_student;
    }

    return success;
}
Vlad from Moscow
  • 301,070
  • 26
  • 186
  • 335