Program, który liczy ilość liter i wyrazów zawartych w pliku tekstowym

0

Witam,

Potrzebuję pomocy drodzy internauci. Mam do napisania program, który liczy ilość liter oraz wyrazów zawartych w pliku tekstowym.

Problem dotyczy tego iż, nie wiem jak ominąć zliczanie przecinków kropek oraz spacji. Program liczy wszystko okej jeżeleli w pliku tekstowym jest napisa "Ala ma kota i psa", ale jeżeli w pliku pojawi się napis:
"Ala ma kota i psa ", lub "Ala ma kota i psa , " to sytuacja się od razu zmienia.

Mój kod źródłowy:

#include<fstream>
#include<iostream>
#include<string>

using namespace std;

int main()
{
    ifstream dane;
    string plik;
    string slowo;
    
    int i = 0;
    int j = 0;
    int k = 0;
    char litera[ 101 ];
    
    
    cout << "Podaj nazwe pliku \n";
    getline( cin, plik );
    
    dane.open( plik.c_str() );
    
    while( !dane.eof() )
    {
        
        dane >> slowo;
        i++;
        
    }
    dane.close();
    dane.open( plik.c_str() );
    while( !dane.eof() )
    {
        
        dane >> litera[ j ];
        k++;
        j++;
        
    }
    dane.close();
    system( "cls" );
    
    
    cout << "Liczba liter w pliku to: " << k - 1 << endl;
    cout << "Liczba slow w pliku to: " << i << endl;
    
    
    cin.get();
    return 0;
}
1

Cały kod bym poprawił, niepotrzebnie wczytujesz wielokrotnie cały plik i marnujesz miejsce na tablicę znaków, których nie używasz.

Zapewne chcesz użyć <cctype> i isalpha() aby sprawdzić czy wczytany znak faktycznie był literą.

0
#include<fstream>
#include<iostream>
#include<string>
#include <algorithm>

using namespace std;

vector <char> forbidden_chars = {',','.', '!'}; // characters you DONT want to count
bool is_char(vector <char> chars, char KEY, char litery[], int iter)
{
    KEY = litery[iter];
    if (count(chars.begin(), chars.end(), KEY))
        return true;
    else
        return false;
}

vector <string> forbidden_words = {",",".","!"}; // words you DONT want to count, to be done
bool is_word(vector <string> words, string word)
{
    if (count(words.begin(), words.end(), word))
        return true;
    else
        return false;
}
int main()
{

    ifstream dane;
    string plik;
    string slowo;

    int i = 0;
    int j = 0;
    int k = 0;
    char litera[ 101 ];

    cout << "Podaj nazwe pliku \n";
    getline( cin, plik );

    dane.open( plik.c_str() );

    while( !dane.eof() )
    {

        dane >> slowo;
        if (!is_word(forbidden_words, slowo))
            i++;

    }
    dane.close();
    dane.open( plik.c_str() );
    while( !dane.eof() )
    {

        dane >> litera[ j ];

        if (!is_char(forbidden_chars, litera[j], litera, j))
            k++;
        j++;

    }
    dane.close();
    system( "cls" );

    cout << "Liczba liter w pliku to: " << k - 1 << endl;
    cout << "Liczba slow w pliku to: " << i << endl;

    cin.get();
    return 0;
}

Zliczanie liter działa dobrze. Zliczanie wyrazów trzeba poprawić.
Tutaj zliczy dobrze wszystko:
Ala,,! ma... . ! . ! , kota
Ale tutaj zliczy źle wyrazy:
Ala,,! ma... .. !! .. !! ,, kota (policzy wszystkie podwójne znaki przed którymi wcześniej była spacja)

1

Myślałbym bardziej o czymś takim (pisane z palca):

#include <cctype>
#include <fstream>
#include <iostream>
#include <sstream>

int main()
{
    size_t words = 0, characters = 0;
    std::string file_name;
    std::cin >> file_name;
    std::ifstream file(file_name);

    std::string temp;
    while(std::getline(file, temp)) {
        std::stringstream ss{temp};
        while(ss >> temp) {

            // if(word_ok(word))
            words++;

            for(char c : temp) {
                if(isalpha(c)) characters++;
            }
        }
    }
}


0

To nie wychowawcze, ale raz na jakiś czas mogę wrzucić gotowca.

#include <regex>
#include <iostream>

int main() {
  const std::string subject("Ala ma kota i psa , ");
  std::regex re("\\w+");
  std::sregex_iterator next(subject.begin(), subject.end(), re);
  std::sregex_iterator end;
  std::cout << "Wyrazy: " <<std::distance(next, end) << '\n';
    
  unsigned charsNum = 0;
  while (next != end) {
    charsNum += (*next).str().size();
    next++;
  }
  std::cout << "Znaki: " << charsNum;
}
1

Regex? Serio? :)

Wystarczy for_each i count_if.

#include <iostream>
#include <fstream>
#include <iterator>
#include <string>
#include <cctype>
#include <algorithm>

using namespace std;

int main(int argc, char* argv[])
{
   ifstream file{"plik.txt"};
   if (file) {
      size_t words = 0, chars = 0;
      for_each(istream_iterator<string>(file), istream_iterator<string>(), [&](const string& str) {
         chars += count_if(str.begin(), str.end(), [](char chr) {
            return isalpha(chr);
         });
         ++words;
      });
      cout << "Words: " << words << "\n";
      cout << "Characters: " << chars << "\n";
   }
}
0
tajny_agent napisał(a):

Regex? Serio? :)

@tajny_agent: a co jest złego w regexach? Kod jak każdy inny, a w przeciwieństwie do Twojego działa zgodnie z założeniami. Dla napisu Ala ma kota i psa , wynikiem powinno być pięć wyrazów, Twój przykład zaraportuje sześć z tego co widzę.

Ayway, mimo błędnego rozwiązania dałem Ci +1 bo mam nieuzasadnioną słąbość do istream/outstream::iterator

0

Nie ma nic złego w regexach, ale tutaj to trochę armata na muchy :P
Autor wspominał tylko o białych znakach i interpunkcji, nie widzę, żeby chciał się pozbywać również spójników. To też są wyrazy ;)

1

Tak, spójniki to też wyrazy, dlatego w zdaniu Ala ma kota i psa , jest pięć wyrazów, a nie sześć jak wylicza Twój kod. Dla porównania, wyniki działani mojego kodu.

tajny_agent napisał(a):

Nie ma nic złego w regexach, ale tutaj to trochę armata na muchy :P

Tutaj zgoda. Aczkolwiek nie wymagają one linkowania zewnętrznych bibliotek i są proste do napisania, dlatego na potrzeby ogólnego wątku na forum jest to rozwiązania jak każde inne ;)

0

No racja! Coś ciężko myślę. bo dopiero zajarzyłem, że chodzi o przecinek :D

Swoją drogą to robienie odstępów przed przecinkiem/kropką/dwukropkiem/etc. jest błędem. Czyli input jest zły, a nie kod.
To nie bug - to feature! ;)

1 użytkowników online, w tym zalogowanych: 0, gości: 1