Click here to Skip to main content
15,896,269 members
Please Sign up or sign in to vote.
1.00/5 (1 vote)
See more:
Why won't my program continue after I ask for the text file? Once I run the program, for some reason I doesn't seem as if it looks for the file, nor does it output the contents of the file.
what can be done to fix this.

I'm trying to input a text file with a string of paths. And then from there I parse through this string and put it to a link list. and then create a search function afterwards.




output:

enter text file
warning: this program uses gets(), which is unsafe.
a1.txt


text file: path.txt

a/a1.txt
a/a2.txt
a/b/b3.txt
a/b/b4.txt
a/c/c4.txt
a/c/c5.txt
a/c/d/d6.txt
a/c/d/g
a/c/d/h
a/c/e/i/i7.txt
a/c/f/j/k/k8.txt




code:

C++
#include <string.h>
#include <stdio.h>
#include <stdlib.h>

typedef struct sMyPath{
        char *element;
        struct sMyPath *next;
} tMyPath;


int main(void)
{
        FILE *pFile;
        pFile = fopen("path.txt", "r");
        char inputstr[1024];
        tMyPath *curr, *first = NULL, *last = NULL;

//get the text file, and put it into a string inputstr

        if (pFile != NULL)
        {
                while(!feof(pFile))
                {
                        fgets(inputstr, sizeof(inputstr), pFile);
                }
        fclose(pFile);
        }
        else
        {
                printf("Could not open the file.\n");
        }

//using tokens to get each piece of the string
//seperate directories and text files, put it into a link list

        char *token = strtok(inputstr, "\\");
        while (token != NULL)
        {
        if(last == NULL){
                //creating node for directory
                first = last = malloc (sizeof (*first));
                first -> element = strdup (token);
                first -> next = NULL;
        } else {
                last -> next = malloc (sizeof (*last));
                last = last -> next;
                last -> element = strdup (token);
                last -> next = NULL;
        }
        token = strtok(NULL, "\\");
        }




//ask user for txt file
        char pathU[20];
        printf("enter text file\n");
        gets(pathU);


//check if text file exist, if yes output entires in text file, else say no
        while(first != NULL)
        {
                if(strcmp (first -> element,pathU)==0)
                {
                        FILE *nFile;
                        char texxt[300];
                        nFile = fopen(pathU, "r");
                        while (!feof(nFile))
                        {
                                fgets(texxt, 300, nFile);
                                printf("Theses are the contents\n");
                                printf("%s", texxt);
                        }

                }

                else if(first == NULL)
                {
                        printf("invalid file name\n");
                }

                else
                {
                first = first -> next;
                }




        }

return 0;
}
Posted
Comments
[no name] 5-May-13 18:45pm    
"doesn't seem as if it looks for the file", why don't you debug your code and find out what it is actually doing?
joedoeuse 5-May-13 18:51pm    
debugger is not installed in the computer
[no name] 5-May-13 19:56pm    
Well the obvious solution is to install the debugger.

1 solution

There is a surprisingly large number of issues with this short piece of code (without even mentioning having very strange naming standards).

1) I'm not sure it should even compile. A decent compiler won't let you do "first = last = malloc (sizeof (*first));" because you're trying to implicitly convert from void* to sMyPath*.
Replace it with this: "first = last = (sMyPath*)malloc (sizeof (*first));"
or, better still, this: "first = last = new sMyPath;"
(although perhaps the later is a C++ thing? I'm a bit sketchy on some of the differences with C)

2) Noted that "curr" is never used. Remove it.

3) You are using several unsafe functions. If this is for Windows at least (VC++), make sure to replace them with the secure versions: fopen_s, gets_s, and strtok_s instead of fopen, gets, and strtok respectively. Ideally avoid strtok_s completely. I'm not even sure what you're trying to do with it since you're not passing it a delimiter that is even in your file.

4) You are looping until end of file calling fgets, and putting it into the same buffer each time.
"fgets reads characters from the current stream position to and including the first newline character, to the end of the stream, or until the number of characters read is equal to n – 1, whichever comes first."
Thus when you reach the end of file, inputstr contains only the last line of the file. (In your example "a/c/f/j/k/k8.txt\n" - the newline is included!)

5) You should be checking for NULL returned by fgets anyway, and then check if it means there was an error (using ferror) or the end of file was reached (using feof)

6) This means that you end up with only one "sMyPath" object. first = last, where next is NULL and element contains "a/c/f/j/k/k8.txt\n". (again the newline is included).

7) As a result, you can never enter a path which exists in your linked list, because even if you enter "a/c/f/j/k/k8.txt" it won't match the only entry you have because you cannot enter the newline character.
Hence you can never find the file in your linked list, and so the program simply exists as it has nothing to do.

8) Not sure why your testing if "first == NULL" after having checked it isn't (in the while loop), and using the pointer to access the element member!

9) You are never freeing all the memory you have allocated.

In summary:
a) Your main (logical) issue is that you should be removing the newline character and creating the linked list entries as you read each line in.
b) You need to do some serious rework.

Regards,
Ian.
 
Share this answer
 

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900