Как я могу подсчитать строки, используя стандартные классы fstream
и ifstream
?
Как подсчитать строки файла в C ++?
Ответы (7)
Как насчет этого :-
std::ifstream inFile("file");
std::count(std::istreambuf_iterator<char>(inFile),
std::istreambuf_iterator<char>(), '\n');
person
Abhay
schedule
18.06.2010
Я бы так сказал, если бы ты не сказал этого до меня. Тем не менее, ваш путь немного лучше ... +1
- person fingerprint211b; 19.06.2010
Только что вспомнил, что, если в последней строке нет \ n?
- person fingerprint211b; 19.06.2010
@ fingerprint211b: Добавьте один к результату :-) Всегда есть компромисс, есть ли у вас новая строка в конце файла.
- person Abhay; 19.06.2010
@ fingerprint211b: Тогда на одну строчку меньше. То, что последняя строка пуста, не означает, что она отличается от любой другой строки.
- person Billy ONeal; 19.06.2010
Красиво и элегантно. Люблю этот STL.
- person wheaties; 19.06.2010
@wheaties: Я также думаю, что это более быстрый способ подсчета строк в файле, если не самый быстрый. Если вы читаете строки, системная библиотека (будь то fgets или std :: readline) скопирует данные в ваш буфер; но оптимальное решение будет обращаться к данным в буфере, откуда они считываются из системы, например, при отображении памяти. Таким образом, действительно оптимальным решением для библиотеки могло бы быть создание mmap_streambuf для mmap файла. Тогда метод count_lines просто перебирает его, и вообще никогда не будет необходимости копировать данные.
- person Abhay; 19.06.2010
Я не могу найти std: count. Я только что включил ‹iostream›, ‹string› и ‹fstream›.
- person malhobayyeb; 19.06.2010
@MIH: Быстрый поиск в Google сказал бы вам, что
std::count()
находится в <algorithm>
.
- person James McNellis; 19.06.2010
@ MIH1406:
#include <algorithm>
- person Abhay; 19.06.2010
+1 за
istream
buf _iterator
, о чем свидетельствует пункт 29 действующего стандарта STL!
- person Cubbi; 19.06.2010
Когда я пытаюсь использовать это решение, я получаю сообщение об ошибке
error: const struct std::basic_string<char, std::char_traits<char>, std::allocator<char> >' has no member named 'str'
. Кто-нибудь знает, как это исправить?
- person synaptik; 01.12.2012
Похоже, что с
std:ifstream
вам не нужно закрывать файл?
- person qed; 04.11.2013
@qed: см. stackoverflow.com/questions/748014/
- person Abhay; 04.11.2013
Совершенно уверен, что это решение работает только в том случае, если вы предполагаете, что кодировка имеет низкий ASCII, поскольку вы параметризуете тип с помощью
char
, поэтому вы сравниваете по одному октету за раз, а не по одному фактическому символу за раз. Тем не менее, это работает для моего варианта использования, поэтому +1 к вам. :)
- person Parthian Shot; 04.11.2015
@ParthianShot: он будет работать с любой из кодировок ISO-8859, многих кодовых страниц Windows / DOS, а также UTF-8 (при условии, что компилятор кодирует
'\n'
как 0x0a
). Ни в коем случае не идеально, но достаточно, если вы можете утверждать, что файл находится в одной из этих кодировок.
- person DevSolar; 21.04.2016
Этот метод выдаст недопустимое количество строк (на 1 слишком мало строк), если в файле отсутствует POSIX
eol
(например, '\n'
в конце последней строки текста). И поскольку нет буфера для проверки, содержит ли он действительный текст, там это не способ поймать это состояние.
- person David C. Rankin; 15.03.2019
@ DavidC.Rankin Я бы сказал, что результат всегда один два маленьких. POSIX - это красный слух. Если последний символ - это новая строка, то в конце остается еще одна пустая строка. Чем пустая строка в конце отличается от пустой строки где-либо еще в файле?
- person Martin York; 15.03.2019
Дело в том, что этот
size_t n = 0; while (getline (stream, string)) n++;
точно сообщит количество строк независимо от того, имеет ли файл POSIX eof
. Подход std::count
, как показано в этом ответе, не сможет подсчитать последнюю строку - даже если текст присутствует для чтения. В любом случае количество строк должно быть точным. Изюминкой всего вопроса является то, почему значительное меньшинство текстовых редакторов продолжают писать файлы с окончанием, отличным от POSIX. :)
- person David C. Rankin; 15.03.2019
супер решение!
- person Shudipta Sharma; 08.01.2020
Вы читаете файл построчно. Подсчитайте количество прочитанных строк.
person
Martin York
schedule
18.06.2010
Звучит как огромное чрезмерное усложнение! ;-)
- person James McNellis; 19.06.2010
Что правильно. Чтение с буфером - единственный способ поймать не-POSIX eof.
- person David C. Rankin; 15.03.2019
Это правильная версия ответа Крейга В. Райта:
int numLines = 0;
ifstream in("file.txt");
std::string unused;
while ( std::getline(in, unused) )
++numLines;
person
Billy ONeal
schedule
18.06.2010
std :: getline (in, std :: string ()) - Привязка неконстантной ссылки к временному объекту недопустима в C ++.
- person Pietro; 08.04.2013
методы ядра после @Abhay
Полный код, который я сделал:
size_t count_line(istream &is)
{
// skip when bad
if( is.bad() ) return 0;
// save state
std::istream::iostate state_backup = is.rdstate();
// clear state
is.clear();
std::istream::streampos 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
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» для последней строки.
person
小文件
schedule
08.06.2016
вернуть 1 для пустого файла или без файла.
- person masoomyf; 30.01.2018
Думаю, 0 может быть лучше?
- person 小文件; 30.01.2018
да 0 требуется, если в файле ничего нет или файл не существует. Но эта функция возвращает ноль для пустого файла.
- person masoomyf; 31.01.2018
если
blank file
- это файл только с пробелами, функция может вернуть 1, как и ожидалось ~
- person 小文件; 01.02.2018
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/
person
Craig Wright
schedule
18.06.2010
while ( ! in.eof() )
‹--- НЕЕЕТ! Это приведет к появлению мусора, если при чтении файла произойдет какой-либо сбой. Положите std::getline
как условие на время.
- person Billy ONeal; 19.06.2010
Он по-прежнему недействителен после вашего редактирования, потому что, если
std::getline
не удается, вы увеличиваете счетчик строк и не проверяете, удалось ли это, до тех пор, пока не будет. Переведите std::getline
в состояние пока.
- person Billy ONeal; 19.06.2010
Разделите размер файла на среднее количество символов в строке!
person
John
schedule
18.06.2010
Как определить среднее количество символов в строке, не читая файл? Если вы подсчитываете символы, вы можете вместо этого просто подсчитать символы новой строки; что делает ваш ответ недействительным.
- person Thomas Matthews; 19.06.2010
Потрясающий! Именно так написано 99,99% кода, который я получил от своих предшественников!
- person Herwig; 07.04.2021
person
schedule
Пустая строка по-прежнему остается строкой, поэтому проверку
empty()
следует удалить.
- person Remy Lebeau; 15.03.2019
@RemyLebeau зависит от того, как вы определяете строки, которые OP не указал.
- person Rick; 10.06.2021
line
- учитывается ли содержимое между последним разрывом строки и концом файла? что, если бы сразу после перехода на строку следовало eof. - person Greg Domjan   schedule 19.06.2010