-1

This is one of my homework and I keep running into seg fault after the cin while loop, can anybody tell what did I do wrong? I have not learn map yet so I can't do that. One of my thought is that it went into seg fault because I was comparing the two string elements inside the vector, what is the way to do that properly?

#include <chrono>
#include <climits>
#include <cfloat>
#include <limits>
#include <cassert>
#include <exception>
#include <cctype>
#include <string>
#include <cmath>
#include <iostream>
#include <fstream>
#include <sstream>
#include <iomanip>
#include <regex>
#include <vector>
using namespace std;
int main()
{
        vector<string> word_input;
        vector<int> word_count;
        string word;
        string fileName;
        ifstream inputFile;
        cout << "Enter file name: ";
        getline(cin,fileName);

        inputFile.open(fileName);

        while (inputFile.fail())
        {
                cout << "Can't open the file" << endl;
                exit(1);
        }

        cout << "File opened successfully \n";

        while (inputFile >> word)
        {
                if (word != word_input.back())
                {
                        word_input.push_back(word);
                        word_count.push_back(1);
                }
                else
                {
                        word_count.push_back( word_count.back() + 1);
                }
        }
        int count =word_count.back();
        // Compare the input words
        // and output the times of every word compared only with all the words
        for (int i = 0; i != count; ++i)
        {
            int time = 0;
            for (int j = 0; j != count; ++j)
                {
                    if (word_input[i] == word_input[j])
                        ++time;
                }

            std::cout << "The time of "
                 << word_input[i]
                 << " is: "
                 << time
                 << endl;
        }
        inputFile.close();
        return 0;
}
  • Please post the input to your program. – R Sahu Jan 25 '19 at 22:56
  • @RSahu The input file is a text file only contains 1 sentence: Big fish eat small fish ( I made this up just for testing) – Devaskar Jan 25 '19 at 23:00
  • Basic debugging. Step through it. At the second "fish" see if the condition detects the previous "fish" and it will be pretty obvious why it does not. – Kenny Ostrom Jan 25 '19 at 23:01
  • 1
    Let Devaskar work for it a little, geez. :) – Kenny Ostrom Jan 25 '19 at 23:02
  • That's a lot of header files you don't use. Don't include any more than the bare minimum you need. – Some programmer dude Jan 25 '19 at 23:05
  • 3
    Additionally, "Calling back on an empty container is undefined." https://en.cppreference.com/w/cpp/container/vector/back – Kenny Ostrom Jan 25 '19 at 23:05
  • The thing is I can not really reach to the output it gives me yet so I can't really tell whether it detects the other words or not – Devaskar Jan 25 '19 at 23:06
  • @KennyOstrom it's a requirement from my instructor so I have to put it in ( but thanks for the advice anyways) – Devaskar Jan 25 '19 at 23:06
  • You can't really test if something works if you can't see the results. Easiest way to handle this is add a small print function that dumps the contents of your `vector`s to the console. You can remove the function before you submit the assignment if you want. Call the print function after every operation on the `vector`s and watch what happens. Fix the code accordingly. – user4581301 Jan 25 '19 at 23:18
  • I'm not the one who commented on your excessive headers. I thought about it ... I just didn't say it. However, your instructor did not make you post them here. You should trim things down to the actual problem here, and include the input. [mcve] You don't need std::cin to create the test case -- I like to initialize the data in code as literals. – Kenny Ostrom Jan 25 '19 at 23:31
  • Step through the code with a debugger and you will see what is wrong. – eesiraed Jan 26 '19 at 04:47

1 Answers1

0

The strategy you are using is fraught with problems. A simpler approach would be to use a std::map<std::string, int>.

int main()
{
   std::map<std::string, int> wordCount;
   string word;
   string fileName;
   ifstream inputFile;

   cout << "Enter file name: ";
   getline(cin,fileName);

   inputFile.open(fileName);

   if (inputFile.fail())
   {
      cout << "Can't open the file" << endl;
      exit(1);
   }

   cout << "File opened successfully \n";

   while (inputFile >> word)
   {
      // --------------------------------------------------------------
      // This is all you need to keep track of the count of the words
      // --------------------------------------------------------------
      wordCount[word]++;
   }

   for ( auto const& item : wordCount )
   {
      std::cout << "The time of "
         << item.first
         << " is: "
         << item.second
         << std::endl;
   }
   inputFile.close();
   return 0;
}
R Sahu
  • 204,454
  • 14
  • 159
  • 270
  • Any reason for `while (inputFile.fail())` instead of a simple `if(inputFile.fail())`? Plus, why manually close `std::ifstream`? That seems to contradict with advices posted [here](https://stackoverflow.com/a/748059/7151494). – Fureeish Jan 25 '19 at 23:15
  • 1
    @Fureeish, the first point is one of oversight - copy and paste error from the OP's code. The second point -- it's the OP's code and it doesn't hurt. – R Sahu Jan 25 '19 at 23:17