Reputation: 25
Write a program that takes an arbitrary number of file names as command line arguments and counts the frequency of each letter in the English alphabet (A through Z) appearing among all the files. Ignore all characters that are not part of the basic English alphabet. You should regard upper and lower case of the same letter as the same. Report the count of each letter, along with its overall frequency (as a percentage of total letters) to the user. You do not have to worry about letters with diacritical marks (e.g. umlauts) or other variants from the standard alphabet. (Rather than using many conditionals or switch, I suggest using a vector or map to store counts.)
I have most of the idea down, but once I am iterating through each individual character of the file, how do I add a count to the corresponding vector element? Here is my attempt at it but it is riddled with errors.
#include <iostream>
#include <cmath>
#include <vector>
#include <fstream>
#include <iomanip>
#include <string>
using namespace std;
int main(int argc, char* argv[]){
double total_letters = 0.0;
vector<double> counts[26]={};
if (argc == 1) {
cout << "You did not enter any command line arguments!" << endl;
return 0;
}
for(int i = 1; i <= argc - 1; i++){
ifstream ifs(argv[i]);
if (!ifs.is_open()){
cout << "Error: file could not be opened." << endl;
return 0;
}
string words = "";
ifs >> words;
for(int i = 0; i < words.size()-1; i++){
if((tolower(words[i]) >= 97) && (tolower(words[i]) <= 122)){
counts[(int)tolower(words[i]) - 97] = counts[(int)tolower(words[i]) - 97]+1;
}
}
for(int i = 0; i < counts.size()-1; i++){
total_letters = total_letters + counts[i];
}
ifs.close();
ifs.clear();
}
for(int i = 0; i < counts.size()-1; i++){
cout << endl << (char)i + 65 <<": " << counts[i] << ", " << ((double)counts[i]/total_letters)*100 << "%";
}
return 0;
}
Upvotes: 0
Views: 59
Reputation: 726479
You've made an array of vectors, rather than a simple vector. You should make the vector like this:
vector<double> counts('z'-'a'+1, 0);
'z'-'a'+1
is another way of writing 26. This way of writing the length of your vector leaves no doubts in reader's mind as to the purpose of the array (counting letters).
Now all you need to do is writing counts[index]++
.
Note that hard-coding 97
and 122
should be avoided.
You need to read words
in a loop. This line
ifs >> words;
reads a single word, not all words. The main loop should be as follows:
string word;
while (ifs >> word) {
for (int i = 0 ; i != word.size() ; i++) {
ch = word[i];
if (!isalpha(ch)) {
continue;
}
counts[tolower(ch)-'a']++;
}
}
Upvotes: 1