Reading a text file


The assignment is to download a file called words.txt. Read all the words from the file and store them in a vector. Calculate the number of words, total number of letters, the average length of words in the list and output the data to a file named "output.txt"




[#include <iostream>
#include <string>
#include <fstream>
#include <vector>
using namespace std;

string numberOfWords();
string totalNumberOfLetters();
string averageLengthOfWords();
int main()
{
ifstream fin;
ofstream fout;


fout.open("output.txt");
if (fout.is_open())
{
fout << "output.txt";
fout.close();
}
while (!fin.eof())
{
fin >> text;
cout << text;
getline(fin, text);
}
fin.close;
return 0;

string numberOfWords();
vector <string> numberOfWords;
words.size;
getline_pushback

string totalNumberOfLetters();
vector <string> totalNumberOfLetters;

string averageLengthOfWords();
vector <string> AverageLengthOfWords();



}
]
Code formatting is done like this: [code] { your code here } [/code]
You can edit your post and add it.

What problem are you having? Be specific.
Last edited on
First problem is that the code was not compiled before it was posted and all the errors are not fixed. It also looks like there are missing functions.

In case I have not posted this before:

PLEASE ALWAYS USE CODE TAGS (the <> formatting button), to the right of this box, when posting code.

Along with the proper indenting it makes it easier to read your code and also easier to respond to your post.

http://www.cplusplus.com/articles/jEywvCM9/
http://www.cplusplus.com/articles/z13hAqkS/

Hint: You can edit your post, highlight your code and press the <> formatting button.
You can use the preview button at the bottom to see how it looks.

I found the second link to be the most help.



Andy
Hello bethmayweather,

Is there any chance of the input file can be downloaded? It helps when everyone is using the same information.

The first part I would work on is opening and reading the input file and creating the vector of all the words. Once you get this far you will have something to work with.

When I tried to compile the code it was full of errors. It makes it look like you tried to code your ideas, but in no particular order.

I made some changes and the first part of the program woul work better like this:
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
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
#include <iostream>
#include <iomanip>
#include <string>
#include <vector>

#include <fstream>
#include <chrono>
#include <thread>

//using namespace std;  // <--- Best not to use.
// A recent post that is worth reading. http://www.cplusplus.com/forum/beginner/258335/

std::string numberOfWords();
std::string totalNumberOfLetters();
std::string averageLengthOfWords();

int main()
{
	std::string text;
	std::vector<std::string> words;

	std::string inFileName{ "Random Text 1.txt" };  // <--- A file I have with about 600 random words.

	std::ifstream inFile(inFileName);

	if (!inFile)
	{
		std::cout << "\n File " << std::quoted(inFileName) << " did not open" << std::endl;
		std::this_thread::sleep_for(std::chrono::seconds(3));  // <--- Needs header files chrono" and "thread". Optional as is the header files.
		return 1;  //exit(1);  // If not in "main".
	}

	while (inFile >> text)
	{
		std::cout << text << '\n';
		words.emplace_back(text);

		//std::getline(inFile, text);
	}

	inFile.close();

	// The next line may not be needed. If you have to press enter to see the prompt it is not needed.
	//std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');  // <--- Requires header file <limits>.
	std::cout << "\n\n Press Enter to continue: ";
	std::cin.get();

	return 0;
}

I have no idea what your intention for using the "getline" in the while is for, but it will not work.

The while loop will read the file properly, but will also include any punctuation on the last word of the sentence. I would add some code in the while loop to eliminate the punctuation.

If you get this far now you have something to work with for your other functions.

Hope that helps,

Andy
Thank you! I'm having trouble opening the file on my computer..even though I have it saved it says the system can't find the file. Also, I need to count the number of words and average length..how would I go about that??
Hello bethmayweather,

Unfortunately I can not see your computer, so this is mostly a guess for now. Also if you have mentioned in the past what IDE and operating system you are using I have lost track of that information.

I use VS with Windows and when the IDE is set for debug compile it tends to consider the current working directory as the one that contains the ".cpp" files. Compiling under release mode that becomes a different working directory,

I have also found that if you have to use a path to the file it is quite easy to get something wrong in the path that can cause a problem.

Either post the code that you have so far or post the code that defines the file stream and opens the stream. An please do not leave anything out because you think it is not important.

If you are using Windows and a path I can work up some code that will help narrow down the problem.

One of the nice things, (advantages), about vectors that makes counting your words is the the vector will hold only what you tell it to. So using vectorName.size() or vectorName.length() will tell you how many words that are in the vector which is how many elements, or words, you have processed. The ".size()" and ".length()" functions both return the same number which is how many elements are in the vector.

Just for the future:

I'm having trouble opening the file on my computer..even though I have it saved it says the system can't find the file.



A nice message, but it does not tell me where the file is saved or what the code looks like the opens the file. A little more information would cut down the back and forth questions and save a lot of time.

Hope that helps,

Andy
Using std::string and std::vector makes computing the number of words, the number of letters in each word and the average number of letters very easy. No need for custom functions:

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
#include <iostream>
#include <string>
#include <vector>

int main()
{
   std::vector<std::string> vec_words { "The", "quick", "red", "fox", "jumped", "over",
                                        "the", "lazy", "brown", "dog" };

   // how many words in the vector?
   std::cout << "The number of words in the vector is: " << vec_words.size() << "\n\n";

   int total_letters { };

   // how many letters in each word?
   for (size_t loop { }; loop < vec_words.size(); loop++)
   {
      std::cout << vec_words[loop] << ":\t" << vec_words[loop].size() << '\n';

      total_letters += vec_words[loop].size();
   }
   std::cout << '\n';

   // casting to double to avoid the problem with integer division
   double average_size = static_cast<double>(total_letters) / static_cast<double>(vec_words.size());

   std::cout << "The average number of letters is: " << average_size << '\n';
}

The number of words in the vector is: 10

The:    3
quick:  5
red:    3
fox:    3
jumped: 6
over:   4
the:    3
lazy:   4
brown:  5
dog:    3

The average number of letters is: 3.9


Changing console input/output to file access is also easy, adding a couple of checks to ensure the input and output files have been opened properly:

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
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
#include <iostream>
#include <string>
#include <vector>
#include <fstream>

int main()
{
   std::ifstream fin("words.txt");

   //check to make sure the input file was opened
   if (!fin.is_open())
   {
      // std::cerr is similar to std::cout, for error reporting to the console
      std::cerr << "Unable to open input file, cya!\n";
      return 0;  // exit
   }

   std::ofstream fout("output.txt");

   //check to make sure the output file was opened
   if (!fout.is_open())
   {
      std::cerr << "Unable to open output file, cya!\n";
      return 0;  // exit
   }

   // create an empty vector
   std::vector<std::string> vec_words;

   std::string dummy;

   // read each word from the file, "fail" when there are no more words to be read
   while (fin >> dummy)
   {
      // push each word to the end of the vector
      vec_words.push_back(dummy);
   }

   // how many words in the vector?
   fout << "The number of words in the vector is: " << vec_words.size() << "\n\n";

   int total_letters { };

   // how many letters in each word?
   for (size_t loop { }; loop < vec_words.size(); loop++)
   {
      fout << vec_words[loop] << ":\t" << vec_words[loop].size() << '\n';

      total_letters += vec_words[loop].size();
   }
   fout << '\n';

   // casting to double to avoid the problem with integer division
   double average_size = static_cast<double>(total_letters) / static_cast<double>(vec_words.size());

   fout << "The average number of letters is: " << average_size << '\n';
}

How your output is structured is up to you.
For opening the file, keep in mind that if you are on a windows system, you need to escape the '\' characters in the path. Suppose your file is located at C:\My Documents\words.txt. So if your code contains:
string filename = "C:\My Documents\words.txt";
then the compiler strips out the '\' characters and what ends up in filename is C:My Documentswords.txt

To fix this, you must escape the backslashes:
string filename = "C:\\My Documents\\words.txt";
Also keep in mind that you don't *need* to use backslashes, C++ streams are perfectly compatible with [forward, normal] slashes.

To see where your program is executing from, try using
std::system("cd"); on windows and std::system("pwd"); on linux.

Then, place the file in that folder.
Topic archived. No new replies allowed.