Getting Word Frequency From Vector

Hi,
Hopefully you can help:)
I am trying to figure out how I would be able to count how many times each element of a vector of strings was entered; Googled it. I don't know how to use maps. Found this code:


struct wordFreq
{
string word;
int count;
wordFreq(string str, int c):word(str),count(c){}


//I don't understand this line what is it for?Is it initializing struct?What is this of symbol ":" for?

};
vector<wordFreq> words;

int ffind(vector<wordFreq>::iterator i, vector<wordFreq>::iterator j, string s)

//this line is also a total mystery. is it a function or what is it?
{
for(;i<j;i++){
if((*i).word == s)
return 1;
}
return 0;
}
Code for finding the no of occurrences in a textfile vector is then:

for(int i=0; i< textfile.size();i++){
if(ffind(words.begin(),words.end(),textfile[i])) // Check whether word already checked for, if so move to the next one, i.e. avoid repetitions
continue;
words.push_back(wordFreq(textfile[i],1)); // Add the word to vector as it was not checked before and set its count to 1
for(int j = i+1;j<textfile.size();j++){ // find possible duplicates of textfile[i]
if(file[j] == (*(words.end()-1)).word)
(*(words.end()-1)).count++;
}
}
closed account (o3hC5Di1)
Hi there,

Please wrap your code in code tags next time, it makes it much more readable.
As to your questions:

wordFreq(string str, int c):word(str),count(c){}

This is the constructor for the wordFreq struct. It will be called automatically when an object of the type of wordFreq is created. The part after the : is called the initialiser list, which allows you to set initial values for the member data of the struct or class. in this case you could do:

wordFreq wf(w, c); where word is a string and count an int, and it will create a new object of type wordFreq with its member data set to word=w and count=c.

1
2
3
int ffind(vector<wordFreq>::iterator i, vector<wordFreq>::iterator j, string s)
//...
iffind(words.begin(),words.end(),textfile[i])


ffind() receives the starting index of the vector and the ending index of it, so it knows how many items to check. it also gets the search string so it knows what to look for.

It then uses a for-loop to loop over every item of the vector, starting at the beginning index and stopping at the last, checking every element for the search string along the way.

Let us know if you have any further questions.

All the best,
NwN
Thank you for answering NwN.
I am not sure if I should use this code because even after your explanation it is still a little too complicated for my level. I have read that the best solution is probably a map but we have not covered it yet.

Right now I am at the point in my program when I got user input (multiple names), stored it in vector.

Trying to count how many times each word appeared; Found slightly easier code;Tried it but I am getting compiler error. Cannot find it. So I am back here:)

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
58
59
60
void GetUserInput(vector<string>&names);
void LoopThroughVector(vector<string>&names, vector<int>&ocurrence);

vector<string>candidates;
vector<int>frequency_count;
string user_choice;
int count=0;

int main ()
{

    GetUserInput(candidates);
    LoopThroughVector(candidates, frequency_count);

}

void GetUserInput(vector<string>&names)
{

    while (1)
    {   cout<<"Please enter a name: ";
        user_choice=GetLine();

        if (user_choice=="DONE")
        break;

        else
        {
            candidates.push_back(user_choice);
            //saving entered names in vector named candidates
            count = candidates.size();

        }
    }
    cout << "Number of enetered names:" << count << endl;
}

void LoopThroughVector(vector<string>&names, vector<int>&ocurrence)

{

string target;
int num=0;
    for (int i=0; i<names.size(); i++)
    //Outter loop is for looping through whole vector
    {
        for (int j = 0; j <= i; j++)
        target =names[i];

        //inner loop is to compare values
			if (target==names[i])
			{
				names[i] = names[j];
				ocurrence[j]++;
                frequency_count.push_back(ocurrence[j]);

			}
    }

}


1 error messages: 1. error name lookup of "j" changed for ISO "for" scoping



Last edited on
The block scope of variable j is the statement following for-statement.

1
2
        for (int j = 0; j <= i; j++)
        target =names[i]; // <== here is end of for 


But you are trying to access j outside the for loop.


1
2
3
4
5
if (target==names[i])
			{
				names[i] = names[j]; // here you are trying to access j
				ocurrence[j]++;
                frequency_count.push_back(ocurrence[j]);

}
Last edited on
Thanks for answering Vlad. I still have some questions I thought the inner loop should include if statement as well:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
 for (int i=0; i<names.size(); i++)
    //Outter loop is for looping through whole vector
    {
        for (int  j = 0; j <= i; j++)

        { target =names[i];


        //inner loop is to compare values
			if (target==names[i])

				{  names[i] = names[j];
				   ocurrence[j]++;
                   frequency_count.push_back(ocurrence[j]);
				}
        }



    }


I tried to run it and it runs but it actually crashes my compiler.
Last edited on
I have not understood what do you mean saying "crashes my compiler"?
It runs and then it just says "Plain Projects has stopped working"
It seems that your program has undefined behavior.
I changed the code again and now got a little further I hope:)

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
void CheckMajority(vector<string>&names, vector<int>&ocurrence)

{
    int times;
    string winner;
    //have to use new variable coz names[i] can be used only inside of the loop
    times=(names.size()/2);


     for (int i=0;i<ocurrence.size();i++)
       {
          if (ocurrence[i]>times)

          {
            winner=names[i];
            cout<<"The candidate who got majority is "<<winner<<endl;

          }
          else
          {
              cout<<"No majority winner."<<endl;
          }
          break;
       }
}

void CheckPlurality(vector<string>&names, vector<int>&ocurrence)
{
    int plurality=0;

    string winner_plurality;

      for (int i=0;i<ocurrence.size();i++)
       {
          plurality=ocurrence[i];
          if (ocurrence[i]>ocurrence[i+1])
          {
              plurality=ocurrence[i];
              winner_plurality=names[i];

          }



       }

cout<<"The candidate who got plurality is "<<winner_plurality<<endl;


there is a logical error. I tested it and for majority it reports no winners if there is a winner. For plurality it does not run correctly if there are more than 2 names.
Last edited on
Topic archived. No new replies allowed.