Как посчитать строки файла на C ?

#c

#c #file-io #io #fstream #ifstream

Вопрос:

Как я могу посчитать строки, используя стандартные классы, fstream и ifstream ?

Комментарии:

1. пахнет домашним заданием — что вы уже пробовали?

2. Начните с ‘1’ и продолжайте добавлять 1 для каждой строки в файле.

3. @Noah: В пустом файле одна строка?

4. @Martin — Ты прав. СБОЙ.

5. Это, должно быть, обман, потому что я написал сообщение в блоге, основанное на другом времени, когда кто-то задавал этот вопрос в Stack Overflow. adrianmccarthy.com/blog/?p=37

Ответ №1:

Как насчет этого :-

   std::ifstream inFile("file"); 
  std::count(std::istreambuf_iterator<char>(inFile), 
             std::istreambuf_iterator<char>(), 'n');
  

Комментарии:

1. @fingerprint211b: Добавьте единицу к результату 🙂 Всегда есть этот компромисс, есть ли у вас новая строка в конце файла.

2. Красивый и элегантный. Обожаю этот STL.

3. @MIH: Быстрый поиск в Google сказал бы вам, что std::count() находится в <algorithm> .

4. @MIH1406: #include <algorithm>

5. Суть в том, что это size_t n = 0; while (getline (stream, string)) n ; точно сообщит о количестве строк независимо от того, имеет ли файл POSIX eof . std::count Подход, как показано в этом ответе, не сможет подсчитать последнюю строку, даже если текст присутствует для чтения. Количество строк должно быть точным независимо. Изнанка всей проблемы в том, почему значительное меньшинство текстовых редакторов продолжают писать файлы с окончаниями, отличными от POSIX. :)

Ответ №2:

Вы читаете файл построчно. Подсчитайте количество прочитанных строк.

Комментарии:

1. Это звучит как огромное усложнение! 😉

2. Что правильно. Чтение с буфером — единственный способ перехватить значение eof, отличное от POSIX.

Ответ №3:

Это правильная версия ответа Крейга В. Райта:

 int numLines = 0;
ifstream in("file.txt");
std::string unused;
while ( std::getline(in, unused) )
     numLines;
  

Комментарии:

1. std::getline(в, std::string()) — Привязка неконстантной ссылки к временной не является законной в C .

Ответ №4:

методы ядра, следующие @Abhay

Полный код, который я сделал :

 #include <fstream>

std::size_t count_line(std::istream amp;is) {
    // skip when is not open or got bad
    if (!is || is.bad()) { return 0; }
    // save state
    auto state_backup = is.rdstate();
    // clear state
    is.clear();
    auto pos_backup = is.tellg();

    is.seekg(0);
    size_t line_cnt;
    size_t lf_cnt = std::count(std::istreambuf_iterator<char>(is), std::istreambuf_iterator<char>(), 'n');
    line_cnt = lf_cnt;
    // if the file is not end with 'n' , then line_cnt should plus 1
    // but we should check whether file empty firstly! or it will raise bug
    if (is.tellg() != 0) {
        is.unget();
        if (is.get() != 'n') {   line_cnt; }
    }

    // recover state
    is.clear() ; // previous reading may set eofbit
    is.seekg(pos_backup);
    is.setstate(state_backup);

    return line_cnt;
}
  

это не изменит состояние потока исходного файла и, включая обработку ‘ n’-пропустить обработку ситуации для последней строки.

Спасибо @masoomyf за указание на мою ошибку, и я был слишком глуп, чтобы понять это!

Комментарии:

1. верните 1 для пустого файла или без файла тоже.

2. Я думаю, что 0 может быть лучше?

3. да, 0 требуется, если в файле ничего нет или файл не существует. Но эта функция возвращает ноль для пустого файла.

4. если blank file это файл, содержащий только пробелы, функция может вернуть 1, как и ожидалось ~

5. @masoomyf привет, спустя почти 5 лет я наконец-то понял твои аргументы. Настолько глуп не только мой английский, но и моя логика. Спасибо

Ответ №5:

 int aNumOfLines = 0;
ifstream aInputFile(iFileName); 

string aLineStr;
while (getline(aInputFile, aLineStr))
{
    if (!aLineStr.empty())
        aNumOfLines  ;
}

return aNumOfLines;
  

Комментарии:

1. Пустая строка по-прежнему является строкой, поэтому empty() проверку следует снять.

2. @RemyLebeau зависит от того, как вы определяете строки, которые не указаны в OP.

Ответ №6:

Это работает для меня:

   std::ifstream fin{"source.txt"};
  std::count(std::istream_iterator<char>(fin >> std::noskipws), {}, 'n');
  

Ответ №7:

 
int numLines = 0;
ifstream in("file.txt");
//while ( ! in.eof() )
while ( in.good() )
{
   std::string line;
   std::getline(in, line);
     numLines;
}
  

Возникает вопрос о том, как вы обрабатываете самую последнюю строку файла, если она не заканчивается новой строкой. В зависимости от того, что вы делаете, вы можете захотеть посчитать это, а можете и нет. Этот код подсчитывает это.

Смотрите: http://www.cplusplus.com/reference/string/getline /

Комментарии:

1. while ( ! in.eof() ) <— НЕЕЕТ! Это приведет к мусору, если при чтении файла произойдет сбой любого типа. Поставьте std::getline в качестве условия while.

2. После редактирования он все еще недействителен, потому что в случае std::getline сбоя вы увеличиваете количество строк и не проверяете, удалось ли это до конца. Переместитесь std::getline в состояние while.

Ответ №8:

Разделите размер файла на среднее количество символов в строке!

Комментарии:

1. Как определить среднее количество символов в строке, не читая файл? Если вы считаете символы, вы могли бы также просто посчитать новые строки вместо этого; что делает ваш ответ недействительным.

2. Потрясающе! Именно так написано 99,99% кода, который я получаю от своих предшественников!

3. Вы заслуживаете Нобелевской премии за это решение.