Форум программистов, компьютерный форум CyberForum.ru

С++ для начинающих

Войти
Регистрация
Восстановить пароль
 
Рейтинг: Рейтинг темы: голосов - 11, средняя оценка - 4.91
Gepar
1175 / 531 / 20
Регистрация: 01.07.2009
Сообщений: 3,516
#1

Вывод в файл и последующее чтение из файла объектов класса - C++

04.05.2012, 01:43. Просмотров 1438. Ответов 5
Метки нет (Все метки)

Как наиболее правильно и канонично выводить (так чтобы потом ещё и прочитать) объекты классов в файл?
Представим ситуацию:
Есть класс A, от него унаследован класс B и класс C.
Есть функция, которая принимает список объектов А, В и С (вперемешку).
Есть функция, задача которой считать из файла объекты А, В и С (и не перепутать что где) и вернуть список этих объектов.

Как это лучше всего реализовать?
Классы A, B и C пускай будут простенькие. Хоть бы вот такие:
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
class A
{
public:
    A(int _x)
    :x(_x){}
 
    virtual void fun()
    {
        cout<<x<<"\t";
    }
 
private:
    int x;
};
 
class B: public A
{
public:
    B(int _x, int _y)
    :A(_x), y(_y){}
 
    virtual void fun()
    {
        cout<<"B"<<"\t";
        A::fun();
        cout<<y<<endl;
    }
 
private:
    int y;
};
 
class C: public A
{
public:
    C(int _x, char _c)
    :A(_x), c(_c){}
 
    virtual void fun()
    {
        cout<<"C"<<"\t";
        A::fun();
        cout<<c<<endl;
    }
 
private:
    char c;
};
Приведите пример как ЛУЧШЕ ВСЕГО организовать вывод в файл и чтение из файла объектов моих А, В и С.

Добавлено через 31 минуту
Тоесть вся сложность в том что мы заранее не знаем что записано в файл, посему не знаем сколько байт читать и когда у нас один объект закончился, а начался другой ...
Дописал ещё прототипы функций, а также main если кто захочет поэкспериментировать чтобы помочь:
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
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
class A
{
public:
    A(int _x)
    :x(_x){}
 
    virtual void fun()
    {
        cout<<x<<"\t";
    }
 
private:
    int x;
};
 
class B: public A
{
public:
    B(int _x, int _y)
    :A(_x), y(_y){}
 
    virtual void fun()
    {
        cout<<"B"<<"\t";
        A::fun();
        cout<<y<<endl;
    }
 
private:
    int y;
};
 
class C: public A
{
public:
    C(int _x, char _c)
    :A(_x), c(_c){}
 
    virtual void fun()
    {
        cout<<"C"<<"\t";
        A::fun();
        cout<<c<<endl;
    }
 
private:
    char c;
};
 
struct Block
{
    Block(A* what)
    :obj(what), next(NULL){}
 
    A* obj;
    Block* next;
};
 
void outToFile(Block* list)
{
    while(list)
    {
        
    }
}
 
Block* readFromFile(ofstream& file)
{
 
}
 
 
int main()
{
    A a(1);
    B b(2,2);
    C c(3,'c');
 
    Block* simpleList= new Block(&c);
    simpleList->next= new Block(&b);
    Block* tail= simpleList->next;
    tail->next= new Block(&a);
    outToFile(simpleList);
}
Добавлено через 17 минут
Допустимо дописывать что угодно и делать как угодно, лишь бы выполнить задачу ...
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
04.05.2012, 01:43     Вывод в файл и последующее чтение из файла объектов класса
Посмотрите здесь:

C++ Чтение массива объектов и регистрация расширения файла
запись и чтение динамических объектов в файл C++
Запись объектов в файл и чтение C++
Запись, чтение объектов в файл через указатели. C++
Сохранение и чтение объекта класса в файл/из файла C++
Запись и чтение объектов разных классов в один файл C++
Вывод текста из файла в консоль и его последующее редактирование C++
Запись в файл и последующее чтение массива типа char C++
Чтение объектов из файла C++
C++ Запись и чтение объектов класса в файл С ++
Добавить вывод в файл и чтение из файла объектов класса C++
C++ Вывод значений объектов класса

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

Или воспользуйтесь поиском по форуму:
После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
ggmann
20 / 20 / 1
Регистрация: 06.10.2008
Сообщений: 173
04.05.2012, 09:52     Вывод в файл и последующее чтение из файла объектов класса #2
почитай об сериализации и xml, очень хороший способ сохранения объектов класса и последующее использование. думаю есть готовые классы в нете для ++.
ForEveR
Модератор
Эксперт С++
7958 / 4720 / 319
Регистрация: 24.06.2010
Сообщений: 10,525
Завершенные тесты: 3
04.05.2012, 10:31     Вывод в файл и последующее чтение из файла объектов класса #3
boost::serialization.
Gepar
1175 / 531 / 20
Регистрация: 01.07.2009
Сообщений: 3,516
04.05.2012, 12:16  [ТС]     Вывод в файл и последующее чтение из файла объектов класса #4
ForEveR, не-не-не. Задача на построение алгоритма вручную, а не на получение результата через реализованую сериализацию бустом или MS в их библиотеках или ещё кем. Приведите пожалуйста "самописный" пример, ато мне вероятно придётся решать такую задачку в очень скором будущем, вот и думаю как правильнее всего это сделать.
ForEveR
Модератор
Эксперт С++
7958 / 4720 / 319
Регистрация: 24.06.2010
Сообщений: 10,525
Завершенные тесты: 3
04.05.2012, 12:25     Вывод в файл и последующее чтение из файла объектов класса #5
Gepar, Не столь просто реализовать грамотную сериализацию.
Gepar
1175 / 531 / 20
Регистрация: 01.07.2009
Сообщений: 3,516
05.05.2012, 11:56  [ТС]     Вывод в файл и последующее чтение из файла объектов класса #6
ForEveR, ну я понял что вот в xml так не напишешь. Ну а вообще как написать вывод в файл чтобы это не получилось быдлокодом. Вот это плохой вариант:

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
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
#include <iostream>
#include <fstream>
#include <cstdlib>
#include <list>
using namespace std;
 
class A
{
public:
    A(int _x)
    :x(_x){}
 
    virtual void fun()
    {
        cout<<x<<"\t";
    }
 
    virtual void serialize (ofstream& file)
    {
        file<<x<<' ';
    }
 
private:
    int x;
};
 
class B: public A
{
public:
    B(int _x, int _y)
    :A(_x), y(_y){}
 
    virtual void fun()
    {
        cout<<"B"<<"\t";
        A::fun();
        cout<<y<<endl;
    }
 
    virtual void serialize(ofstream& file)
    {
        A::serialize(file);
        file<<y<<' ';
    }
 
private:
    int y;
};
 
class C: public A
{
public:
    C(int _x, char _c)
    :A(_x), c(_c){}
 
    virtual void fun()
    {
        cout<<"C"<<"\t";
        A::fun();
        cout<<c<<endl;
    }
 
    virtual void serialize(ofstream& file)
    {
        A::serialize(file);
        file<<c<<' ';
    }
 
private:
    char c;
};
 
 
bool writeToFile(list<A*>& x, ofstream& file)
{
    file.clear();
 
    list<A*>::iterator it= x.begin();
    while(it!= x.end() && file.good())
    {
        if(dynamic_cast<C*> (*it))
         file<<"C";
        else if(dynamic_cast<B*> (*it))
         file<<"B";
        else
         file<<"A";
 
        file<<" ";
        (*it++)->serialize(file);
    }
 
    return (file.good() ? true: false);
}
 
 
int main()
{
    A a(1);
    B b(2,2);
    C c(3,'c');
 
    ofstream outFile("file.xml");
 
    list<A*> simpleList;
    list<A*>::iterator it;
    simpleList.push_back(&b);
    simpleList.push_back(&c);
    simpleList.push_back(&a);
 
    writeToFile(simpleList,outFile);
}
?
Скажте если что некрасиво или если вообще идея плохая. Предположительно будет задание написать что-то на наследование и на вывод в файл за часок (на листке), думаю полноценная сериализация как это в MFC или у буста на это время не рассчитывается, рассчитывать будут на что попроще (если вообще такое задание дадут конечно).

Добавлено через 1 минуту
*чтение дописываю просто, спешу показать как я вывожу в файл. Чтение реализовать планирую подобно:
читаю первый символ, switch (символ) case A - читаю как А, case B - читаю как B. Ну вы поняли идею.
Другое дело если скажут " а если у нас тут char* есть поле в классе и мы не знаем его длину и там могут быть переводы строки, а ещё там могут быть скобки (") что тогда, а? Съел, а , съел?"

Добавлено через 17 минут
Дописал чтение из файла, но почему то с тестовыми данными вижу через дебагер что А последнюю (или если последнее что-то другое то это другое) два раза читает, любопытно как это получается оно так...
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
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
#include <iostream>
#include <fstream>
#include <cstdlib>
#include <list>
using namespace std;
 
class A
{
public:
    A(int _x)
    :x(_x){}
 
    virtual void fun()
    {
        cout<<x<<"\t";
    }
 
    virtual void serialize (ofstream& file)
    {
        file<<x<<' ';
    }
 
private:
    int x;
};
 
class B: public A
{
public:
    B(int _x, int _y)
    :A(_x), y(_y){}
 
    virtual void fun()
    {
        cout<<"B"<<"\t";
        A::fun();
        cout<<y<<endl;
    }
 
    virtual void serialize(ofstream& file)
    {
        A::serialize(file);
        file<<y<<' ';
    }
 
private:
    int y;
};
 
class C: public A
{
public:
    C(int _x, char _c)
    :A(_x), c(_c){}
 
    virtual void fun()
    {
        cout<<"C"<<"\t";
        A::fun();
        cout<<c<<endl;
    }
 
    virtual void serialize(ofstream& file)
    {
        A::serialize(file);
        file<<c<<' ';
    }
 
private:
    char c;
};
 
 
bool writeToFile(list<A*>& x, ofstream& file)
{
    file.clear();
 
    list<A*>::iterator it= x.begin();
    while(it!= x.end() && file.good())
    {
        if(dynamic_cast<C*> (*it))
         file<<"C";
        else if(dynamic_cast<B*> (*it))
         file<<"B";
        else
         file<<"A";
 
        file<<" ";
        (*it++)->serialize(file);
    }
 
    return (file.good() ? true: false);
}
 
list<A*>* readFromFile(ifstream& file)
{
    file.clear();
    list<A*>* result=new list<A*>;
 
    char ch;
    int x,y;
 
    while(!file.eof() && file.good())
    {
        file>>ch;
        switch(ch)
        {
            case 'A':
            file>>x;
            result->push_back(new A(x));
            break;
 
            case 'B':
            file>>x>>y;
            result->push_back(new B(x,y));
            break;
 
            case 'C':
            file>>x>>ch;
            result->push_back(new C(x,ch));
            break;
 
            default:
            break;
        }
        file.ignore();
    }
    return result;
}
 
 
int main()
{
    A a(1);
    B b(2,2);
    C c(3,'c');
 
    ofstream outFile("file.xml");
 
    list<A*> simpleList;
    list<A*>::iterator it;
    simpleList.push_back(&b);
    simpleList.push_back(&c);
    simpleList.push_back(&a);
 
    writeToFile(simpleList,outFile);
 
    outFile.close();
 
    ifstream inFile("file.xml");
    list<A*>* resultOfReading= readFromFile(inFile);
 
 
    it= resultOfReading->begin();
    while(it!=resultOfReading->end())
    {
        (*it++)->fun();
    }
}
Комментарии не пишу, названия функций говорят сами за себя.

Добавлено через 21 час 29 минут
Ходил вчера на собеседование, задание и правда было такое что нужно написать класс, наследников, а потом вывести в файл и считать из файла. Написал реализацию подобную той что в этой теме, посмотрим что скажут.
Yandex
Объявления
05.05.2012, 11:56     Вывод в файл и последующее чтение из файла объектов класса
Ответ Создать тему
Опции темы

Текущее время: 14:31. Часовой пояс GMT +3.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2017, vBulletin Solutions, Inc.
Рейтинг@Mail.ru