середнього використання. Справа в тому, що він нічого не знає про вихідних даних, які буде в собі містити. Цими даними можуть бути, наприклад, розмір структури в пам'яті і деякі її методи. Найпростішим рішенням буде введення шаблону з передачею типу збереженої структури як його параметра.
//! реальний клас, який приводиться до Dbt
template class hbRec: public hbObj
{
A data;
public :
A * getPnt (void) {return &data;}// якщо в в A масив то можна перевизначити операцію & для А
hbRec () { memset (& data, 0, sizeof (A)); dbtInit (sizeof (A), & data);}
hbRec (const hbRec & a): data (a.data) {dbtInit (sizeof (A), & data);}
hbRec (const A & a) : Data (a) {dbtInit (sizeof (A), & data);}
void SetData (const A & a) {data = a; dbtInit (sizeof (A), & data);}
virtual ~ HbRec () {}
};
Таблиці
Діаграма відносин існуючих таблиць наведена нижче:
В
За аналогією з записами існує базовий клас таблиць hbBasetbl, який підтримує роботу з усіма стандартними типами таблиць (Hash, Btree, Queue). Фактично її тип є її станом і визначається в момент відкриття.
class hbBasetbl
{
// потрібен для того щоб set_flags викликалася рівно один раз
uint Set_flg_Counter;
ushort state;
// прапор, показивающ. відкрита чи сама таблиця, необхідний для екстр. закриття в випадку некоректно
// відкриття
bool tableopen;
hbInit ini;
protected:
uint recsize;
uint keysize;// тільки для DB_HASH
Db * table;
virtual void UsrOpen (hbTxn * tx, FileConf & conf, bool openidx, hbInitRt * irt = 0, u_int32_t op_flags = 0);
virtual void UsrClose ();
void SetRecSize (uint recsize1) {recsize = recsize1;}
void SetKeySize (uint keysize1) {keysize = keysize1;}
uint GetType () {return ini.type;}
bool IsDup () {return (ini.st_flags & DB_DUP | ini.st_flags & DB_DUPSORT)> 0;}
public :
hbEnv & env;
operator Db * () {return table;}
Db * operator -> () {Return table;}
const char * GetDbName () {return ini.dbname;}
hbBasetbl (hbEnv & e, hbInit &);
virtual ~ HbBasetbl () {if (state) Close ();}
void Open (hbTxn * tx, FileConf & conf, bool openidx, hbInitRt * irt = 0, u_int32_t op_flags = 0);
void Close ();
В
virtual void Create (hbTxn * tx, FileConf & conf, hbInitRt * irt = 0, u_int32_t op_flags = 0);
virtual int Get (hbTxn * tx, hbObj * key, hbObj * val, u_int32_t flags = 0);// у стилі С (без винятків)
virtual int Pget (hbTxn * tx, hbObj * fkey, hbObj * pkey,// ​​у стилі С (без винятків)
hbObj * val, u_int32_t flags = 0);
virtual int Del (hbTxn * tx, hbObj * key, u_int32_t flags = 0);// у стилі С (без винятків)
virtual int tGet (hbTxn * tx, hbObj * key, hbObj * val, u_int32_t flags = 0);// в стилі С + +
virtual int tPget (hbTxn * tx, hbObj * fkey, hbObj * pkey, hbObj * val, u_int32_t flags = 0);// в стилі С + +
virtual int tDel (hbTxn * tx, hbObj * key, u_int32_t flags = 0); // в стилі С + +
virtual int Put (hbTxn * tx, hbObj * key, hbObj * val, u_int32_t flags = 0);
bool IsOpen () {return state;}
};
Для прискорення доступу за якимось критерієм до даних в таблицях вводяться індексні таблиці. Ними можуть бути будь-які з перерахованих, звичайно відповідно до їх особливостями. Клас hbBasetbl є з одного боку базовим класом, що містить всю рутинну роботу з прапорами і основними операціями з таблицею, а з іншого боку-фінальним класом для індексного таблиці.
Цей клас є базовим, і зовсім незручний для роботи, якщо ця таблиця є індексованої (тобто має індекси - інші індексні таблиці). Необхідний ще один клас, який буде узагальненням поняття індексованою таблиці та бути контейнером для таких індексних таблиць. Цей клас представлений нижче.
class hbPTable: public hbBasetbl {
void ErrorClose ();
void eee ();
void FixIdx (uint bulk_ret_buffer_size, int i, FileConf & conf);
void FixIdxForQueue (uint bulk_ret_buffer_size, int i, FileConf & conf);
void FixIdxForHash (uint bulk_ret_buffer_size, int i, FileConf & conf);
void CheckMainToIdx (uint bulk_ret_buffer_size, bool fix, FileConf & conf);
void CheckMainToIdxForQueue (uint bulk_ret_buffer_size, bool fix, FileConf & conf);
void CheckMainToIdxForHash (uint bulk_ret_buffer_size, bool fix, FileConf & conf);
void Check...