Reading a in file

Hello, for a class project I need to write a code that spell checks a book from a file against a dictionary from another file. My code will check the first word in the book but won't continue to check the next word. I thought using "book >> word;" would make it read the next word but it just leaves the loop. Also, how do I read from the beginning of the file for the dictionary every time I get a new word from the book?

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
  int main() {
    string word, dictWord, current;                 
    ifstream dict ("dict.txt");     //dictionary     
    ifstream book ("book.txt");     //book

        while (book >> word)        //read book word by word
        {
            if (word.empty() == 0)
            {
                current = cleanword(word);                      //remove all upercase and ascii characters
                while (dict >> dictWord)
                {
                    if (!current.compare(dictWord) == 0)        //if word doesnt match 
                    {
                        dict >> dictWord;                        //get next dictionary word
                    }else if (!current.compare(dictWord) == 1)  //if word does match
                    { 
                        //cout << "right";                        
                        book >> word;                           //get next word in book
                    }else                                       // if no more words in dictionary
                    {
                        book >> word;                           //get next word in book
                    }
                }
            }
            
        }
        book.close();
}
Make sure that the file actually opened:

1
2
3
4
if(!book.is_open())
{
     cout << "File not Found!\n";
}



book >> word should work, giving you every word in book.txt until it runs out.


Your logic, however, is flawed. You have a loop for a reason, yet you use book >> word twice in the inner while loop.

Also, since you want to check the whole dictionary file for every word in the book, you want to close and reopen the file every iteration of the first loop.
Are you permitted to use a std::unordered_set<std::string> ?
This would be the container best suited to storing a list of words.

If not, you should expect the dictionary to be properly sorted from file, so all you need to do is read it in to a std::vector<std::string>, or an array[] (exactly as you think: just use dict >> dictWord). Once you have that then you you can use a binary search to find whether a word is in the vector/array/whatever or not.

(A binary search is really easy, and you can write a function to do it yourself, or use the std::binary_search() (#include <algorithm>.)

The list of valid words (the dictionary) should be loaded first, before you even bother to mess with the user input file.


Once you have your dictionary (list of valid words) loaded and a way to determine whether or not a word is in the list, then you can start dinking with the user input file. This implies another loop.

Again, you can load it word-by-word, with book >> bookWord. Once you get the word, you will need to preprocess it a little bit. Convert it to lowercase, remove periods and question marks and other punctuation, and use the function you prepared above to see if the word is found in the dictionary or not.

If it is found in the dictionary, the word is good.
If it is not found, then you need to tell the user that the word needs to have its spelling fixed.

(If I understand your assignment correctly, you do not actually have to suggest a correct spelling. Your assignment is already pretty involved for the level that this homework matches, and finding suggested spellings is significantly more involved than it appears at first blush.)

Hope this helps.
Unfortunately, the end goal of the project is to load the dictionary into a linked list and check the book against that. Use of any other list is not allowed. The dictionary file only has one word per line, making it quite easy to read. However, the creation of the linked list is what is stumping me. I can't seem to find any good information on how to make a linked list, then add the dictionary, which is several thousand words long.

I think I understand how to compare the words from the book to the words in the dictionary. Aswell as loop through the linked list to continually read new words in.

You are correct in that I just need to find out if the word exists in the dictionary, I do not need to suggest a correct spelling.
all a linked list is, is a multi-variable type (struct, class, or even a tuple) where one of the fields is a pointer to the same type.

struct lyst
{
string word;
lyst* next; //this makes it a linked list.
}
and then a bunch of methods to insert, remove, etc and do the raw memory management are needed to finish it up. a simple insert at the top for example,

temp = new lyst; //get a new link in the chain
temp->word = "blah"; //fill in the data
temp-> next = oldlist; //the chain is now temp -> oldliststart -> oldlistsecond->.. oldlistend
oldlist = temp; //smoke and mirrors the old list now has the new node at its beginning and is chained on out to the end. This is very fast way to insert, poking the next one on top each time.

there should be billions of these things out there from people doing homework. Its a popular task...
you may want to make it sorted for performance, or not. thousands is nothing to a modern computer, so looking through the whole list every time (stop if you found it) isnt much more expensive than sorting it unless the user is constantly asking to look up words that don't exist.
if you want to make it sorted, and are feeling really gung ho about it, you can do a skip list off the first letter of the words; this is a second pointer that just leaps to the next letter change, eg if you are at "minnow" the skip pointer may take you to the first N word, "nab" perhaps...
Last edited on
Thank you all for the help. I think I've got it all up and going now.
Your assignment is to use a linked list as a membership predicate structure?
That's some pretty poor course design for you.

Anyway, whenever dinking with linked lists, make sure to draw stuff (using a pencil). Use squares for nodes, and arrows for links to nodes. Whenever you do something, make sure that you do it in the right order so that no node ever loses at least one arrow pointing to it. After that writing code to do it is easy.

Glad you've got it sorted. :O)
Last edited on
Topic archived. No new replies allowed.