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
|
#include "enginedata.h"
#include <iostream>
#include <cassert>
using namespace std;
Row::Row(const int _nc,const Table *const _t):nc(_nc),table(_t){
items=new RowItem[nc];
}
Row::~Row(void){
if(items)delete[] items;
}
Row::Row(Row &&other):nc(other.nc),table(other.table),items(other.items){ //move constr
other.table=nullptr;
other.items=nullptr;
}
Row::Row(const Row &other):nc(other.nc),table(other.table){ //copy constr
items=new RowItem[table->nc];
memcpy(items,other.items,table->nc*sizeof(RowItem));
}
ostream& operator<<(ostream &os,const Row &r){
os<<'[';
for(int i=0;i<r.nc;i++){
if(i)os<<", ";
os<<serialise(r.table->header[i],r.items[i]);
}
os<<']';
return os;
}
//copies from _hd, so you can freely delete or edit the passed colheader array
Table::Table(const string &_n,const int _nc,const ColHeader *const _hd):name(_n),nc(_nc){
header=new ColHeader[nc];
memcpy(header,_hd,nc*sizeof(ColHeader));
}
Table::~Table(void){
if(header)delete[] header;
}
Table::Table(Table &&other):name(move(other.name)),nc(other.nc),header(other.header),rows(move(other.rows)){
other.header=nullptr;
}
void Table::insert(Row &&row){
string key=serialise(this->header[0],row.items[0]);
cerr<<"Inserting into table '"<<this->name<<"' key="<<key<<" row="<<row<<endl;
rows.emplace(key,move(row));
}
void Table::insert(Row &row){
string key=serialise(this->header[0],row.items[0]);
cerr<<"Inserting into table '"<<this->name<<"' key="<<key<<" row="<<row<<endl;
rows.emplace(key,row);
}
Maybe<Row> Table::find(const string &key){
typedef map<string,Row>::const_iterator cit_t;
cit_t end=rows.cend();
for(cit_t it=rows.cbegin();it!=end;it++){
if(serialise(it->second.table->header[0],it->second.items[0])==key)return Maybe<Row>(it->second);
}
return Maybe<Row>();
}
string serialise(const ColHeader &header,const RowItem &rowitem){
switch(header.type){
case RH_INT32:
return serialise(rowitem.u.rh_int32);
case RH_UINT32:
return serialise(rowitem.u.rh_uint32);
case RH_BYTES:
return serialise(rowitem.u.rh_bytes,header.arg);
default:
assert(false);
}
}
string serialise(int32_t v){return to_string(v);}
string serialise(uint32_t v){return to_string(v);}
string serialise(unsigned char *v,int len){return string((char*)v,len);}
|