Function that counts the number of integers in a text file?
I need to write just a function that counts the number of integers in an already opened and good text file.
a. Assume there is a text file with a large number of integers divided by spaces
b. Write a function开发者_如何学C called analyzeFile that accepts a previously opened ifstream file object as a parameter, and counts the number of integers in the file.
c. It does not need to do anything with the integers, but it must count exactly the correct number of integers in the file and return that number to the calling function.
d. It also does not need to manipulate the file operations themselves, so it does not need to close the file or conduct any other actions other than counting the integers and returning the number of them.
Thank you for any help on my problem!
Edit: Here is what I have as a function do far, is it right, I don't know:
int analizeFile (ifstream &inf, const string &fileName) {
int count = 1;
int num;
fin.open(fileName.c_str() );
fin >> num;
while (fin.good() ) {
fin>> num;
count ++;
}
return count;
}
Comments:
int analizeFile (ifstream &inf, const string &fileName) {
Since the count is always a non-negative quantity, I'd prefer to use size_t
rather than int. Nit: You may want to change the name of the function to analyzeFile
.
int count = 1;
Problem starts here: If your file does not have any integer then you return a wrong result.
int num;
fin.open(fileName.c_str() );
No need to call open
. This would typically be called by the ifstream
ctor.
fin >> num;
while (fin.good() ) {
Again, this is not required. You can extract from the stream and test in the while
condition -- something which is more frequently used.
fin>> num;
count ++;
}
return count;
}
You can use a functional approach too
// it was previously opened, so you don't need a filename.
int analyzeFile (istream &inf) {
std::istream_iterator<int> b(inf), e;
return std::distance(b, e);
}
If the iterator cannot read an integer, it will set the fail state on the stream and will compare equal to the end iterator. distance
then returns the number of iteration steps it took to reach the end iterator.
Many many years later, you could come up with a more modern solution.
You can simply use associative containers like std__map
or std::unordered:map
for counting. This is more ore less the standard approach.
Then there are many many new and powerful functions availbale.
Using those, you could come up with some like:
#include <iostream>
#include <fstream>
#include <string>
#include <iterator>
#include <map>
#include <cctype>
using Counter = std::map<char, std::size_t>;
const std::string fileName{"test.txt"};
int main() {
// Open file and check, if it could be opened
if (std::ifstream ifs{fileName}; ifs) {
// Read all data
std::string text{std::istream_iterator<char>(ifs),{}};
// Define the counters
Counter upperCaseLettterCount{},lowerCaseLettterCount{};
// Iterate over all characters in the string and count
for (const char c : text) {
if (std::isupper(c)) upperCaseLettterCount[c]++;
if (std::islower(c)) lowerCaseLettterCount[c]++;
}
// Show result
std::cout << "\nUppercase count:\n\n";
for (const auto& [letter,count] : upperCaseLettterCount) std::cout << letter << " -> " << count << '\n';
std::cout << "\nLowercase count:\n\n";
for (const auto& [letter,count] : lowerCaseLettterCount) std::cout << letter << " -> " << count << '\n';
}
else
// Error, file could not be opened
std::cerr << "\n\n*** Error: Text file '" << fileName << "' could not be opened\n\n";
}
精彩评论