#ifndef __ANALISIB_H #define __ANALISIB_H #ifndef __RELATION_H #define __RELATION_H #include #endif //__RELATION_H #ifndef __APPLICAT_H #define __APPLICAT_H #include //Definizione della classe TApplication #endif //__APPLICAT_H #ifndef _ABLI09_H #include "ablib09.h" #endif //_ABLIB09_H #ifndef _ANALISI_H #include "analisi.h" #endif //_ANALIS_H #ifndef _RELVOCI_H //#define _RELVOCI_H #include "relvoci.h" #endif //_RELVOCI_H #ifndef _RELANA_H //#define _RELANA_H #include "relana.h" #endif //_RELANA_H #define TIPO_ANALISI "A" #define TIPO_VOCE "V" #define ID_NULLO 0 //Serve per eseguire il test class TTest: public TSkeleton_application { protected: virtual void main_loop(); public: // @cmember Costruttore TTest() { } // @cmember Distruttore virtual ~TTest() { } }; class TNodeId : public TString { }; // classe per un albero navigabile in una direzione // (depth first o breadth first) class TAlbero : public TObject { protected: virtual void node2id(const TObject * node,TNodeId & id) const {return;} public: virtual bool empty() {return !goto_root();} virtual bool goto_root() pure ; virtual bool goto_firstson() pure ; virtual bool goto_rbrother() pure ; virtual TObject * curr_node() const pure ; void curr_id(TNodeId & var) const {node2id(curr_node(),var);} virtual bool goto_node(TNodeId &id) {return FALSE;} virtual bool has_son() const {return FALSE;} virtual bool has_rbrother() const {return FALSE;} TAlbero() {} virtual ~TAlbero() {} }; // classe per un albero navigabile in due direzioni class TAlbero_bidir : public TAlbero { public: virtual bool has_father() const {return FALSE;} virtual bool has_lbrother() const {return FALSE;} virtual bool goto_father() {return FALSE;} virtual bool goto_lbrother() {return FALSE;} virtual bool goto_root() {return FALSE;} virtual bool goto_firstson() {return FALSE;} virtual bool goto_rbrother() {return FALSE;} virtual TObject * curr_node() const {return NULL;} TAlbero_bidir() {} virtual ~TAlbero_bidir() {} }; typedef real TNumeric_id; /*class TNumeric_id : public real { public: TNumeric_id &operator =(const int &v) {*((real *)this)=v; return *this;} TNumeric_id &operator =(const real &v) {*((real *)this)=v; return *this;} TNumeric_id(const real &v) {*this=v;} TNumeric_id() {} };*/ //Classe per gestire l'albero di relana class TAlbero_relana : public TAlbero_bidir { TString16 _codtab; TLocalisamfile *_relana; TNumeric_id _last_id; protected: virtual void node2id(const TObject * node,TNodeId & id) const; public: // @cmember Ritorna TRUE se riesce a trovare il primo figlio virtual bool has_son() const; // @cmember Ritorna TRUE se riesce a trovare il fratello destro virtual bool has_rbrother() const; // @cmember Ritorna TRUE se riesce a trovare il padre virtual bool has_father() const; // @cmember Ritorna TRUE se riesce a trovare il fratello sinistro virtual bool has_lbrother() const; // @cmember Si posiziona sulla radice principale virtual bool goto_root(); // @cmember Si posiziona sul primo figlio virtual bool goto_firstson(); // @cmember Si posiziona sul padre virtual bool goto_father(); // @cmember Si posiziona sul fratello destro virtual bool goto_rbrother(); // @cmember Si posiziona sul fratello sinistro virtual bool goto_lbrother(); // @cmember Ritorna TRUE se puņ posizionarsi sul nodo indicato dall'id specificato virtual bool goto_node(TNodeId & id) {return(_relana->readat(atol(id))==NOERR); } // @cmember Si posiziona sul nodo specificato dall'id bool goto_id(const TNumeric_id &id); // @cmember Ritorna il nodo corrente virtual TObject * curr_node() const; // @cmember Ritorna il nodo corrente TRectype & curr() {return (TRectype &)*curr_node();} // @cmember Esegue un lock bool lock(); // @cmember Esegue un unlock void unlock(); // @cmember Inserisce un nodo nella struttura ad albero //bool insert_node(real id); // @cmember Restituisce un nuovo id (il primo disponibile) TNumeric_id &new_id(real id); // @cmember Costruttore TAlbero_relana( const char * tabcode); // @cmember Distruttore virtual ~TAlbero_relana(); }; //Classe per gestire la struttura di una tabella di analisi // basandosi sull'albero di relvoci class TAlbero_relvoci : public TAlbero { TString16 _codtab; TLocalisamfile *_relvoci; protected: virtual void node2id(const TObject * node, TNodeId & id) const; public: // @cmember Si posiziona sulla radice principale virtual bool goto_root(); // @cmember Ritorna TRUE se trova un figlio virtual bool has_son() const; // @cmember Si posiziona sul primo figlio virtual bool goto_firstson(); // @cmember Ritorna TRUE se trova un fratello destro virtual bool has_rbrother() const; // @cmember Si posiziona sul fratello destro virtual bool goto_rbrother(); // @cmember Ritorna TRUE se trova un fratello sinistro bool has_lbrother() const; // @cmember Si posiziona sul fratello sinistro bool goto_lbrother(); // @cmember Restituisce il nodo corrente virtual TObject * curr_node() const; // @cmember Restituisce il nodo specificato dall'id virtual bool goto_node(TNodeId & id) {return (_relvoci->readat(atol(id))==NOERR);} // @cmember Restituisce il nodo corrente TRectype & curr() {return (TRectype &)*curr_node();} // @cmember Esegue un lock bool lock(); // @cmember Esegue un unlock void unlock(); // @cmember Restituisce il codice della tabella che si sta usando const TString & codtab() {return _codtab;} // @cmember Costruttore TAlbero_relvoci(const char * tabcode); // @cmember Distruttore virtual ~TAlbero_relvoci() ; }; // Struttura da albero basata su un file temporaneo cached class TInsert_albero : public TAlbero_bidir { TRWrecord_cache * _ana_cache; TLocalisamfile *_f; // da rimuovere !! TRectype *_currnode; TNumeric_id _last_insert_id; TAssoc_array _status_node; // debug void write_cache() { _ana_cache->flush(); } protected: // @cmember Elimina il sottoalbero dei figli di un nodo // @cmember che sta per essere eliminato da un struttura di tipo lista doppiamente lincata bool remove_subtree(const TNumeric_id lastnode_id); // @cmember genera/setta il nuovo id TNumeric_id &new_id(TNumeric_id); void goto_node(const TNumeric_id id) { TToken_string key; key.add(_currnode->get(ABRA_CODAN)); key.add(id.string()); *_currnode = _ana_cache->get(key); } void goto_node(TRectype &node) {*_currnode = node;} public: // @cmember Inserisce un nodo in una struttura di tipo lista doppiamente lincata bool insert_node(TRectype &node, const TNumeric_id id_prec, const TNumeric_id id_padre, TNumeric_id id); // @cmember Elimina un nodo da una struttura di tipo lista doppiamente lincata bool delete_node(const TNumeric_id &id); // @cmember Lancia la rimozione di tutto l'albero bool delete_tree(); // @cmember Lancia la rimozione di tutto l'albero void zero(); // @cmember Restituisce il nodo corrente TRectype * current() const {return (TRectype * )_currnode;} // @cmember Restituisce TRUE se esiste un figlio di un nodo virtual bool has_son(); // @cmember Si posizione sul primo figlio di un nodo virtual bool goto_firstson(); // @cmember Restituisce TRUE se esiste il fratello destro di un nodo virtual bool has_rbrother(); // @cmember Si posiziona sul fratello destro di un nodo virtual bool goto_rbrother(); // @cmember Si posiziona sul primo nodo della struttura ad albero virtual bool goto_root(); // @cmember Restituisce il nodo corrente virtual TObject * curr_node() const {return _currnode;} // ***** gestione interfaccia Database/copia locale // @cmember Estrae un nodo dall'albero TRectype extract_node(const TString &codtab,TNumeric_id &id, TString& status); // @cmember Ritorna il numero di elementi dell'assoc_array status_node int status_node_items() { return _status_node.items();} // @cmember Setta lo stato del nodo: valori ammessi = nodo ggiunto, nodo odificato, nodo imosso void set_status_node(const TNumeric_id &id, const char *status); // @cmember Ritorna lo stato di un nodo const char* get_status_node(const TNumeric_id &id); // @cmember Costruttore TInsert_albero(); // @cmember Distruttore virtual ~TInsert_albero(); }; class TAnalisi_bil: public TRectype { class TArray_fratelli: public TAssoc_array { public: void setkey(const char *tipocod, const char *codvc, TToken_string &key) const; bool find1stkey(const char *tipocod, const char *codvc, TToken_string &key); void mark_used(const char *key); bool used(TObject *o); }; TArray_fratelli _nodifratelli; TLocalisamfile *_analisi; TLocalisamfile *_voci; TAlbero_relvoci *_relaz; TAlbero_relana *_ana; TInsert_albero *_inter_tree; TRectype * _newrec; //buffer per l'inserimento dodo per nodo protected: // @cmember Esegue una navigazione dell'albero di rel_voci e di rel_ana // @cmember parallelamente verificanto eventualmente delle inconsistenze void naviga_relazioni(const TNumeric_id & id_relana,const TNumeric_id & prec,const TNumeric_id & padre ); // @cmember Sincronizza la copia locale basandosi su relvoci (per la struttura) e su relana (per le info aggiuntive) TRectype * sincronizza_relana(const TNumeric_id &begin_relana,TNumeric_id &id_relana); // @cmember Esegue un lock di una struttura ad albero bool lock_struttura(); // @cmember Esegue un unlock di una struttura ad albero bool unlock_struttura(); // @cmember Esegue un lock su una tabella di analisi bool lock_tabella(); // @cmember Sblocca una tabella di analisi bool unlock_tabella(); public: // @cmember Costruttore TAnalisi_bil(); // #cmember Distruttore virtual ~TAnalisi_bil() ; // @cmember Ritrona il tipo di analisi const TString &type() {return get(ABAN_TIPOAN);} // @cmember Setta il tipo di analisi void set_type(const char * tipo) {put(ABAN_TIPOAN,tipo);} // @cmember Esegue la lettura della testata di un record da LF_ANALISI virtual int read(TBaseisamfile& analisi, word isop=_isequal, word lockop=_nolock); // @cmember Esegue la lettura della testata di un record alla posizione nrec da LF_ANALISI virtual int readat(TBaseisamfile& f, TRecnotype nrec, word lockop = _nolock); // @cmember Serve per lanciare la scrittura del body del record virtual int write(TBaseisamfile& analisi) const; // @cmember Elimina una intera tabella di analisi con tutto il suo contenuto virtual int remove(TBaseisamfile& f) const; // @cmember Azzera l record virtual void zero(); // @cmember Esegue la scrittura del body del record scrive il contenuto di una tabella di analisi int commit_body(TLocalisamfile &relana) const; // @cmember Esegue la lettura del body del rocord: legge il contenuto di una tabella di analisi int read_body(bool lockstruct); // @cmember Restituisce l'oggetto ad albero "copia locale" TInsert_albero & user_tree() {return *_inter_tree;} }; #endif //__ANALISI_H