26 / 26 / 15
Регистрация: 30.12.2015
Сообщений: 95
1

Различия ifstream::get() и ifstream::get(ch)

03.03.2016, 01:26. Показов 7552. Ответов 7
Метки нет (Все метки)

Доброго времени суток. Была тут тема, в которой я не разобрался до конца. Код ниже проверяет баланс скобок в текстовом файле
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
#include "StdAfx.h"
 
using namespace std;
 
int main(void)
{
    setlocale(LC_ALL, "Russian");
 
    ifstream in("cppcode.txt");
    ofstream out("scanresult.txt");
 
    if (in.is_open() && out.is_open())
    {
        int symbols[] = { 0, 0, 0, 0 }; // '(', ')', '{', '}'
 
        while (!in.eof())
        {
            char symbol = static_cast<char>(in.get());
 
            switch (symbol)
            {
                case '(':
                {
                    symbols[0]++;
                    break;
                }
 
                case ')':
                {
                    symbols[1]++;
                    break;
                }
 
                case '{':
                {
                    symbols[2]++;
                    break;
                }
 
                case '}':
                {
                    symbols[3]++;
                    break;
                }
            }
        }
 
        out << "( = " << symbols[0] << endl
            << ") = " << symbols[1] << endl
            << "{ = " << symbols[2] << endl
            << "} = " << symbols[3] << endl;
 
        in.close();
        out.close();
 
        if (symbols[0] == symbols[1])
            cout << "OK1" << endl;
        else cout << "ERROR1" << endl;
 
        if (symbols[2] == symbols[3])
            cout << "OK2" << endl;
        else cout << "ERROR2" << endl;
    }
    else cout << "Error opening files." << endl;
 
    cin.get();
 
    return 0;
}
В таком виде все работает нормально, при входном файле
{{}}
()
выдаст
( :1
) :1
{ :2
} :2

Но если заменить строку 18 на
C++
1
2
char symbol;
in.get(symbol);
то в выводе будет добавлен один лишний символ, который последний в файле, в данном случае
( :1
) :2
{ :2
} :2

При этом, если в конец файла добавить пустую строку, второй вариант тоже нормально отработает. Объясните в чем разница... Заранее благодарю.
__________________
Помощь в написании контрольных, курсовых и дипломных работ здесь
0
Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
03.03.2016, 01:26
Ответы с готовыми решениями:

ifstream
Привет всем такая проблема ввода Student* s;// студенты s = new Student; ifstream...

fstream ifstream
подключил библиотеку fstream создал объект ifstream file открыл файл, поработал(считывал до конца...

Ifstream ошибка
int main(int argc, char* argv) { setlocale(LC_ALL,&quot;Russian&quot;); // корректное отображение...

Объект ifstream!!!
Скажите пожалуйста, почему при создании объекта ifstream(например fin) и привязке его к...

7
1355 / 501 / 69
Регистрация: 21.07.2015
Сообщений: 1,277
03.03.2016, 02:04 2
Цитата Сообщение от elephants Посмотреть сообщение
Код ниже проверяет баланс скобок
Неправильный. Не отловит ситуацию )(
1
Эксперт С++
2361 / 1649 / 275
Регистрация: 29.05.2011
Сообщений: 3,378
03.03.2016, 02:06 3
Лучший ответ Сообщение было отмечено elephants как решение

Решение

Разница в том, что если пытаться читать из файла после достижения конца файла, то вариант get() вернёт EOF, а вариант get(symbol) значение переменной не изменит, а там предыдущий считанный символ.
Проблема в том, что признак конца файла устанавливается не после считывания последнего символа, а при попытке считать следующий. То есть проверять надо после чтения, а не до.
То есть, например
C++
1
2
3
4
5
        while (!in.eof())
        {
            int symbol  = in.get();
            if (symbol == EOF)
                break();
или
C++
1
2
3
4
5
        while (!in.eof())
        {
            char symbol;
            if (!in.get(symbol))
                break();
или даже так
C++
1
2
3
        char symbol;
        while (in.get(symbol))
        {
2
26 / 26 / 15
Регистрация: 30.12.2015
Сообщений: 95
03.03.2016, 02:14  [ТС] 4
Цитата Сообщение от shmkv Посмотреть сообщение
Неправильный. Не отловит ситуацию )(
Код не мной написан, особо не вникал. Интересовал именно описанный мной момент.
grizlik78, Благодарю.
0
1355 / 501 / 69
Регистрация: 21.07.2015
Сообщений: 1,277
03.03.2016, 02:19 5
Касаемо второго варианта, то можно вкорячить проверку eof сразу после get. С такой работай я его тоже сталкивался, но в причинах не разбирался.

Добавлено через 3 минуты
Цитата Сообщение от grizlik78 Посмотреть сообщение
устанавливается не после считывания последнего символа, а при попытке считать следующий
Ну примерно так и думал.
0
26 / 26 / 15
Регистрация: 30.12.2015
Сообщений: 95
03.03.2016, 02:21  [ТС] 6
Цитата Сообщение от shmkv Посмотреть сообщение
то можно вкорячить проверку eof сразу после get.
Я так и делал, просто непонятно было, почему symbol не изменяется после чтения отсутствующих данных через get(symbol).
0
1355 / 501 / 69
Регистрация: 21.07.2015
Сообщений: 1,277
03.03.2016, 02:22 7
Ну вот разработчики как-то так решили. Видимо, из соображений, что в char не запихать EOF.
0
26 / 26 / 15
Регистрация: 30.12.2015
Сообщений: 95
03.03.2016, 02:23  [ТС] 8
Цитата Сообщение от grizlik78 Посмотреть сообщение
что признак конца файла устанавливается не после считывания последнего символа, а при попытке считать следующий.
Это понятно, а вот про
Цитата Сообщение от grizlik78 Посмотреть сообщение
Разница в том, что если пытаться читать из файла после достижения конца файла, то вариант get() вернёт EOF, а вариант get(symbol) значение переменной не изменит
я не знал.
0
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
03.03.2016, 02:23

ifstream ofstream
как работают данные файловые операции, объясните пожалуйста куда происходит запись ена жёстком...

не работает в ifstream
Сам очень плохо разбираюсь в &lt;fstream&gt; Вот код, который должен &quot;записывать и выводить&quot; данные из...

ifstream считывает 0
Здравствуйте. Есть 2 текстовых файла с названиями n.in n.out .Содержимое входящего файла 1 5 2...

Unget and ifstream
Я правильно понимаю, что если ifstream in; string str1; in &gt;&gt; str1, то unget обратно эту...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
8
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2021, vBulletin Solutions, Inc.