forked from grantrostig/file_maintenance_clipped
-
Notifications
You must be signed in to change notification settings - Fork 1
Expand file tree
/
Copy pathio_row.h
More file actions
191 lines (171 loc) · 8.26 KB
/
io_row.h
File metadata and controls
191 lines (171 loc) · 8.26 KB
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
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
#ifndef IO_ROW_H
#define IO_ROW_H
#include <string>
#include <vector>
#include <variant>
#include <optional>
#include <chrono>
#include <ctime>
#include <any>
#include <functional>
#include <bitset>
#include <map>
#include <type_traits>
#include "global_entities.h"
#include "io_field.h"
class IO_table;
enum class IO_row_spec { // https://www.w3schools.com/html/html_form_attributes.asp
auto_complete,
no_validate
//initial_state // TODO:
};
class IO_row_company { // just a stub to demonstrate the type
public:
int kludge {};
void print() const {}
template< class Archive>
void serialize( Archive & archive ) {
archive( kludge );
}
};
//class IO_row_person_opt { // OBSOLETE, will delete later once we are sure of our design.
//public:
// //vector<std::unique_ptr<IO_data_type> TODO: should this be part of the design?
// // NOTE: any std::optional<> data member should NOT have an initializer providing a value! This is depeneded upon in set_field_num();
// /* 00 */ std::optional<std::string> name {};
// /* 01 */ std::optional<double> balance {};
// /* 02 */ std::optional<int> age {}; // NOTE: std::optional here allows for a "NULLable field" in the sense of SQL.
// /* 03 */ std::optional<bool> is_cpp_programmer {}; // TODO: how to represent NOTHING or std::monostate?
// /* 04 */ std::optional<std::tm> date_of_birth {}; // this is a human readable C type, C++20 has a replacement.
// /* 05 */ std::optional<std::string> optional_data {}; // NOTE: an optional string field is not NULLable, but can be blank
// /* 06 */ std::optional<bool> yesno {};
// /* 07 */ std::optional<std::chrono::system_clock::time_point> system_time_stamp {}; // TODO: TODO is this even human readable in a decent format? c++20?
// /* 08 */ std::optional<uint64_t> guid {};
// // ^^ number above should match IO_ROW_FIELDS_NUM_PERSON
// //bool set_row_field_at_num( IO_table table, unsigned short const num, std::string const & val );
// void print() const;
//};
class IO_row_person {
public:
//vector<std::unique_ptr<IO_data_type> TODO: should this be part of the design?
// WARNING: data members should NOT have an initializer providing a value, because it will be ignored! Create a default value (within valid_values) instead.
/* 00 */ std::string name {};
/* 01 */ double balance {};
/* 02 */ int age {};
/* 03 */ bool is_cpp_programmer {};
/* 04 */ std::chrono::system_clock::time_point date_of_birth {};
/* 05 */ std::string optional_data {};
/* 06 */ bool is_opt_in {};
/* 07 */ std::chrono::system_clock::time_point system_time_stamp {}; // TODO: TODO is this even human readable in a decent format? c++20?
/* 08 */ uint64_t guid {};
std::bitset<IO_ROW_FIELDS_NUM_MAX> is_null_field {}; // Each bit represents one of the above fields,
bool is_deleted {false};
// with 1 meaning the field is null and the corresponding value is not to be used. All initialized to all false.
// ^^ ^^number above should match IO_ROW_FIELDS_NUM_PERSON, this comment is partially obsolete for now but may have relevance if we convert field specs to a std::array.
//bool set_row_field_at_num( IO_table table, unsigned short const num, std::string const & val );
void print() const;
template< class Archive>
void serialize( Archive & archive ) {
archive(
name,
balance,
age,
is_cpp_programmer,
date_of_birth,
optional_data,
is_opt_in,
system_time_stamp,
guid,
is_null_field,
is_deleted
);
}
};
//class IO_row_ordered_person {
//public:
// // WARNING: data members should NOT have an initializer providing a value, because it will be ignored! Create a default value (within valid_values) instead.
// /* 00 */ std::string name {};
// /* 01 */ double balance {};
// /* 02 */ int age {}; // NOTE: std::optional here allows for a "NULLable field" in the sense of SQL.
// /* 03 */ bool is_cpp_programmer {}; // TODO: how to represent NOTHING or std::monostate?
// /* 04 */ std::tm date_of_birth {}; // this is a human readable C type, C++20 has a replacement.
// /* 05 */ std::string optional_data {}; // NOTE: an optional string field is not NULLable, but can be blank
// /* 06 */ bool is_opt_in {};
// /* 07 */ std::chrono::system_clock::time_point system_time_stamp {}; // TODO: TODO is this even human readable in a decent format? c++20?
// /* 08 */ uint64_t guid {};
// std::bitset<IO_ROW_FIELDS_NUM_MAX> is_null_field {}; // Each bit represents one of the above fields,
// bool is_deleted {false};
// // with 1 meaning the field is null and the corresponding value is not to be used. All initialized to all false.
// // ^^ ^^number above should match IO_ROW_FIELDS_NUM_PERSON, this comment is partially obsolete for now but may have relevance if we convert field specs to a std::array.
// //bool set_row_field_at_num( IO_table table, unsigned short const num, std::string const & val );
// void print() const;
//};
using Person_pk_t = struct {
decltype( IO_row_person::name ) key_value_p0 {}; // part 0 of n
};
using Person_index1_key_t = struct {
decltype( IO_row_person::name ) key_value_p0 {}; // part 0 of n
decltype( IO_row_person::balance ) key_value_p1 {};
};
struct Person_pk_compare_t { // TODO: use variadic templates, and or combine with next struct
bool operator()( Person_pk_t const & lhs, Person_pk_t const & rhs) const {
return lhs.key_value_p0 < rhs.key_value_p0; // https://foonathan.net/2018/07/ordering-relations-programming/
}
};
struct Person_index1_compare_t { // TODO: use variadic templates
bool operator()( Person_index1_key_t const & lhs, Person_index1_key_t const & rhs) const {
return std::tie(lhs.key_value_p0, lhs.key_value_p1) < std::tie(rhs.key_value_p0, rhs.key_value_p1); // https://foonathan.net/2018/07/ordering-relations-programming/
}
};
/*template< typename Key_t, typename Data_t, typename Compar_t, typename Unique_t >
//class IO_row_index2 {
//public:
// std::variant< std::map < Key_t, Data_t, Compar_t >,
// std::multimap< Key_t, Data_t, Compar_t >
// > row_var;
// Key_t key_value {};
// IO_row_index() {
// if constexpr ( std::is_same<Unique_t,bool>::value ) { // TODO: TODO a better way to do this?
// std::map< Key_t, Data_t, Compar_t > rows;
// row_var = rows; // TODO: TODO is this a memory leak or dangling pointer?
// } else {
// std::multimap< Key_t, Data_t, Compar_t > rows;
// row_var = rows;
// }
// }
// void print() const {}
//};
*/
extern IO_row_person io_candidate_row_person;
//using IO_row_company_map_pk = IO_row_map<Person_index1_key_t, IO_row_person, Person_index1_compar_t>; // NOTE ERROR is "person" this is just a stub to allow it's use in std::variant below.
//extern IO_row_company_map_pk io_row_company_map_pk;
//using IO_row_person_map_pk = IO_row_map< decltype(IO_row_person::name), IO_row_person, Person_pk_compar_t>;
//extern IO_row_person_map_pk io_row_person_map_pk;
//using IO_row_person_index1 = IO_row_map<Person_index1_key_t, IO_row_person, Person_index1_compar_t>;
//extern IO_row_person_index1 io_row_person_index1;
/* Holds IO_fields for a row during data entry as it is validated and collected.
* And acts as location to place data into the struct/record/row of the table.
*/
using IO_row_variant = std::variant<
IO_row_company,
IO_row_person
>;
using IO_row_ptr_variant = std::variant<
IO_row_company *,
IO_row_person *
>;
using IO_row_index_variant = std::variant<
Person_pk_t,
Person_index1_key_t
>;
using IO_row_index_compare_variant = std::variant<
Person_pk_compare_t,
Person_index1_compare_t
>;
// std::map< Person_pk_t, IO_row_person, Person_pk_compare_t > rows_ordered {};
// std::map< IO_row_index_variant, IO_row_variant, Person_pk_compare_t > rows_ordered2 {};
//using IO_row_map_pk_variant = std::variant<
//IO_row_company_map_pk,
//IO_row_person_map_pk
//>;
#endif // IO_ROW_H