user2841098
user2841098

Reputation: 323

C++ vector and string, count vowels

This program supposed to read a text and count the number of vowels and consonants. it should ignore any non alphabetic characters. the result should me something like this:

Enter your text: I have to TURN this..in before midnight!!
 a,  e,  i,  o,  u,  y
 1,  3,  5,  2,  1,  0
There are 19 consonants.

but the result from my code is :

Enter your text: I have to TURN this..in before midnight!!
 a,  e,  i,  o,  u,  y
 1,  3,  4,  2,  0,  0
There are 31 consonants.

I dont know what is happening!! Also this is an assignment and I have to use all these functions and I cannot add or remove them! I read couple of other ways to count and display the numbers but unfortunately the template was given...

#include <iostream>
#include <iomanip>
#include <string>
#include <vector>

using namespace std;

// FUNCTION PROTOTYPES GO HERE:
void init_vectors(vector<char> & vowels, vector<int> & frequencies);
string read_text(const string & prompt);
bool is_alphabetic(const char character);
void create_list(const string & str_text, vector<char> & vec_text);
bool is_member(const vector<char> & list, char character);
int find_index(const vector<char> & list, char character);
int compute_vowel_freqs(const vector<char> & text, const vector<char> & vowels, vector<int> & freqs);
void display_characters(const vector<char> & characters, const int colwidth);
void display_freqs(const vector<int> & freqs, const int colwidth);

int main()
{
    vector<char> vowels;
    vector<int> freqs;
    string input;
    vector<char> text;
    int consonants(0);

    const int COLUMNWIDTH = 2;
    init_vectors(vowels, freqs);
    input=read_text("Enter your text: ");

    create_list(input, text);
    compute_vowel_freqs(text, vowels, freqs);

    display_characters(vowels, COLUMNWIDTH);
    display_freqs(freqs, COLUMNWIDTH);

    consonants = compute_vowel_freqs(text, vowels, freqs);
    cout<<"There are "<< consonants<< " consonants."<<endl;
    return 0;
}

void init_vectors(vector<char> & vowels, vector<int> & frequencies)
{

    for (int i(0); i<6; i++) //i is loop variable
    {
        frequencies.push_back(0);
    }
    vowels.push_back('a');
    vowels.push_back('e');
    vowels.push_back('i');
    vowels.push_back('o');
    vowels.push_back('u');
    vowels.push_back('y');
}

string read_text(const string & prompt)
{
    string phrase;
    cout<<prompt;
    getline(cin,phrase);
    return phrase;
}


bool is_alphabetic(const char character)
{
    bool alphabet;
    if ((character > 'a' && character < 'z')||(character > 'A' && character < 'Z'))
    {
        alphabet = true;
    }
    return alphabet;
}

void create_list(const string & str_text, vector<char> & vec_text)
{
    for( int i = 0 ; i < str_text.length() ; i++)
    {
        if(is_alphabetic(str_text[i]))
            vec_text.push_back(str_text[i]);
    }
}

bool is_member(const vector<char> & list, char character)
{
    bool vowel;
    for (int i(0); i<list.size(); i++)
    {
        if (character == list[i])
        {
            vowel=true;
        }
    }
    return vowel;
}

int find_index(const vector<char> & list, char character)
{
    int index = -1;
    for(int i=0; i<list.size(); i++)
    {
        if(character == list[i])
        {
            index = i;
            break;
        }
    }
    return index;
}

int compute_vowel_freqs(const vector<char> & text, const vector<char> & vowels, vector<int> & freqs)
{
    int num_cons(0);
    for(int i = 0 ; i < text.size() ; i++)
    {
        int index;
        if(is_member(vowels, text[i]))
        {
            index = find_index(vowels , tolower(text[i]));
            freqs[index]++;
        }
        else
            num_cons++;
    }

    return num_cons;
}

void display_characters(const vector<char> & characters, const int colwidth)
{
    for(int i=0; i<characters.size(); i++)
    {
        cout<<setw(colwidth)<<characters[i];
        if((i+1)<characters.size())
        {
            cout<<",";
        }
    }
    cout<<endl;
    return;
}

void display_freqs(const vector<int> & freqs, const int colwidth)
{
    for(int i=0; i<freqs.size(); i++)
    {
        cout<<setw(colwidth)<<freqs[i];

        if((i+1)<freqs.size())
            cout<<",";
    }
    cout<<endl;
    return;
}

Upvotes: 3

Views: 3447

Answers (2)

Beta
Beta

Reputation: 99124

If you write hundreds of lines of code before you test any of it, you're bound to fail. Start small and simple, add complexity a little at a time, test at every step, and never add to code that doesn't work.

You should have tested these functions one by one as you wrote them. Here's the first problem:

bool is_alphabetic(const char character)
{
  bool alphabet;
  if ((character > 'a' && character < 'z')||(character > 'A' && character < 'Z'))
    {
      alphabet = true;
    }
  return false;
}

This always returns false, so nothing is recognized as text.

EDIT:

Second problem: is_member has exactly the same bug, with the same solution.

EDIT:

Third problem: I failed to notice that in this line in is_alphabetic:

if ((character > 'a' && character < 'z')||(character > 'A' && character < 'Z'))

You're using '>' and '<' when you should use ">=" and "<=". According to this function, 'a' and 'z' are not letters.

Look, you're still trying to test and fix this program as a whole. You must test it piecemeal. Pick a place in main and print out every variable that should have been assigned a value by then. This function may be useful:

void printVector(const vector<char> &V)
{
  for(vector<char>::const_iterator citr=V.begin(); citr!=V.end(); ++citr)
    cout << *citr;
  cout << endl;
}

Then inspect the results. If a variable doesn't contain what it should, then something above that point is misbehaving. Trace the problem back to a function where good things go in but something bad comes out. Fix that, then look at the output again. I can't emphasize this enough: don't try to fix everything at once.

Upvotes: 3

VladimirM
VladimirM

Reputation: 817

Your is_member is always false, so no char is vowel. And it results in 0 count.

bool is_member(const vector<char> & list, char character)
{
    bool vowel = false;   # this fix is not obligatory, I just made code look clearer
    for (int i(0); i<list.size(); i++)
    {
        if (character == list[i])
        {
            vowel=true;
        }
    }
    return vowel;  # this should be fixed
}

By the way, the same issue is in the function 'is_alphabetic'. It is always false.

Upvotes: 1

Related Questions