1

I'm attempting to do basic file reading in C with fgets. It should read one line, pass it to the tokeniser function which should split it at every ' ' and add it to a linked list. At the moment it is entering into a never ending while loop and I'm not sure why. Any help is appreciated. I am really struggling with this C language

#define INPUTSIZE 11 void tokeniseString(LinkedList *list, char *str) { char *token = strtok(str, " "); while (token != NULL) { insertLast(list, *token); } } void readInputFile(char *fileName, LinkedList *list) { FILE* inputFile = fopen(fileName, "r"); char str[INPUTSIZE]; printf("1"); if (inputFile == NULL) { perror("Could not open file"); } else { while (fgets(str, INPUTSIZE, inputFile) != NULL) { tokeniseString(list, str); } if (ferror(inputFile)) { perror("Error while reading from file"); } } } 
1
  • 3
    while (token != NULL) { insertLast (list, token); token = strtok (NULL, " "); } to insert all tokens in to list. Share a Minimal, Reproducible Example. Commented Apr 18, 2022 at 8:21

1 Answer 1

1

You have an endless loop because you do not scan for the next token in the loop body. You should write:

void tokeniseString(LinkedList *list, char *str) { char *token = strtok(str, " "); while (token != NULL) { insertLast(list, *token); token = strtok(NULL, " "); } } 

Not however that you insert the value of the first byte of the token into the list. You should probably convert the token as a number using strtol() instead:

#include <errno.h> #include <limits.h> #include <string.h> #include <stdlib.h> void tokeniseString(LinkedList *list, char *str) { char *token = strtok(str, " \t\r\n"); while (token != NULL) { char *p; long value; errno = 0; value = strtol(token, &p, 10); if (p == token || *p != '\0') { fprintf(stderr, "token is not a number: %s\n", token); } else if (errno != 0 || value > INT_MAX || value < INT_MIN) { fprintf(stderr, "number is out of range: %s\n", token); } else { insertLast(list, (int)value); } token = strtok(NULL, " \t\r\n"); } } 

Note that modifying the string argument is considered bad practice, especially using a function with side effects on a static state such as strtok(). Here is another version that does not modify the argument:

#include <errno.h> #include <limits.h> #include <stdio.h> #include <stdlib.h> #include <string.h> void tokeniseString(LinkedList *list, const char *str) { for (;;) { char *p; long value; int len; /* skip whitespace */ str += strspn(str, " \t\r\n"); if (*str == '\0') break; /* get the length of the token */ len = strcspn(str, " \t\r\n"); errno = 0; value = strtol(token, &p, 10); if (p == str) { fprintf(stderr, "token is not a number: %.*s\n", len, str); } else if (p != str + len) { fprintf(stderr, "token has extra characters: %.*s\n", len, str); } else if (errno != 0 || value > INT_MAX || value < INT_MIN) { fprintf(stderr, "number is out of range: %.*s\n", len, str); } else { insertLast(list, (int)value); } str += len; } } 

Also note that you must close the file in readInputFile().

Sign up to request clarification or add additional context in comments.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.