Как узнать, является ли следующий символ EOF в C++
мне нужно знать, если следующий символ в ifstream
является концом файла. Я пытаюсь сделать это с помощью .peek()
:
if (file.peek() == -1)
и
if (file.peek() == file.eof())
но не работает. Есть способ сделать это?
Edit: что я пытаюсь сделать, это добавить букву в конец каждого слова в файле. Чтобы сделать это, я спрашиваю, является ли следующий символ знаком препинания, но таким образом последнее слово остается без дополнительной буквы. Я работаю только с char
, не string
.
7 ответов
istream::peek()
возвращает константу EOF
(т. е. не гарантированно будет равно -1), когда он обнаруживает конец файла или ошибка. Чтобы проверить надежность конца файла, сделайте следующее:
int c = file.peek();
if (c == EOF) {
if (file.eof())
// end of file
else
// error
} else {
// do something with 'c'
}
вы должны знать, что базовый примитив ОС,read(2)
, только сигналы EOF, когда вы пытаетесь прочитать мимо конец файла. Следовательно,file.eof()
не будет правдой, когда вы просто прочитали до последний символ в файле. Другими словами,file.eof()
быть false не означает, что следующая операция чтения будет успешной.
Это должно работать:
if (file.peek(), file.eof())
но почему бы просто не проверить наличие ошибок после попытки чтения полезных данных?
для потока, подключенного к клавиатуре, условие eof заключается в том, что я намерен ввести Ctrl+D/Ctrl+Z во время следующего ввода.
peek()
совершенно не вижу. :-)
file.eof()
возвращает значение флага. Он имеет значение TRUE, если вы больше не можете читать из файла. EOF не является фактическим символом, это маркер для ОС. Так что, когда ты там ... --0--> должно быть true
.
Итак, вместо if (file.peek() == file.eof())
вы должны есть!--4--> после чтения (или peek), чтобы проверить, достигли ли вы конца файла (что вы пытаетесь сделать, если я правильно понимаю).
невозможно сказать, является ли следующий символ концом файла, и попытка сделать это является одной из самых распространенных ошибок, которые делают новые программисты на C и C++, потому что в большинстве операционных систем нет символа конца файла. Вы можете сказать, что чтение мимо текущей позиции в потоке будет читать мимо конца файла, но это в целом довольно бесполезная информация. Вместо этого вы должны проверить все операции чтения на успех или неудачу и действовать в этом состоянии.
обычно для проверки конца файла я использовал:
if(cin.fail())
{
// Do whatever here
}
еще один такой способ реализовать это было бы..
while(!cin.fail())
{
// Do whatever here
}
дополнительная информация была бы полезна поэтому мы знаем чего вы хотите делать.
вы не показали никакого кода, с которым работаете, поэтому есть некоторые догадки с моей стороны. Обычно вам не нужны низкоуровневые объекты (например,peek()
) при работе с потоками. То, что вас, вероятно, интересует, это istream_iterator
. Вот пример,
cout << "enter value";
for(istream_iterator<double> it(cin), end;
it != end; ++it)
{
cout << "\nyou entered value " << *it;
cout << "\nTry again ...";
}
вы также можете использовать istreambuf_iterator для работы с буфером напрямую:
cout << "Please, enter your name: ";
string name;
for(istreambuf_iterator<char> it(cin.rdbuf()), end;
it != end && *it != '\n'; ++it)
{
name += *it;
}
cout << "\nyour name is " << name;