campo-sirio/include/relation.h
guy 12f4ee0441 applicat.cpp Tolti include inutili
codeb.c         Sostituita la x4go con la d4go
isam.cpp        Tolta una riga vuota
maskfld.cpp     Aggiunto controllo sugli id duplicati
relation.cpp    Aggiunto test di cancellato nel metodo TCursor::changed
realtion.h      Aggiunto const al metodo TFieldref::len


git-svn-id: svn://10.65.10.50/trunk@4027 c028cbd2-c16b-5b4b-a496-9718f37d4682
1996-12-20 12:09:45 +00:00

649 lines
25 KiB
C++
Executable File

#ifndef __RELATION_H
#define __RELATION_H
#ifndef __ISAM_H
#include <isam.h>
#endif
#ifndef __SORT_H
class TSort;
#endif
// @doc EXTERNAL
// @class TRelation | Classe per la definizione delle relazioni esistenti tra i file
//
// @base public | TObject
class TRelation : public TObject
// @author:(INTERNAL) Sandro
{
// @cfriend TRelationdef
friend class TRelationdef;
// @cfriend TRelation_description
friend class TRelation_description;
// @cfriend TCursor
friend class TCursor;
// @access:(INTERNAL) Private Member
// @cmember:(INTERNAL) Stato della relazione
TToken_string _status;
// @cmember:(INTERNAL) Array dei descrittori dei file
TArray _files;
// @cmember:(INTERNAL) Array di <c TRelationdef>
TArray _reldefs;
// @cmember:(INTERNAL) Codice dell'ultimo errore occorso
int _errors;
// @access Protected Member
protected:
// @cmember Ritorna l'indice di <p _files> del numero logico passato
int log2ind(int logicnum) const;
// @cmember Ritorna l'indice di <p _files> del alias del file passato
int alias2ind(int alias) const;
// @cmember Ritorna l'indice di <p _files> del nome del file passato
int name2ind(const char* name) const;
// @cmember Ritorna la <c TRelationdef> <p i>-esima
TRelationdef& reldef(int i) const
{ return (TRelationdef&)_reldefs[i]; }
// @cmember Ritorna il descrittore del file <p i>-esimo
TLocalisamfile& file(int i = 0) const
{ return (TLocalisamfile&)_files[i]; }
// @cmember Permette di posizionare l'albero di relazioni tra i file
int position_rels(TIsamop op = _isequal, TReclock lockop = _nolock, TDate& atdate = (TDate&)botime, int first = 0);
// @access Public Member
public: // TObject
// @cmember Controlla se si tratta di un oggetto valido
virtual bool ok() const
{ return good(); }
// @cmember Permette di stampare l'oggetto su <p out>
virtual void print_on(ostream& out) const;
public:
// @cmember Aggiorna l'albero delle relazioni
int update()
{ return position_rels(_isequal, _nolock);}
// @cmember Azzera l'abero delle relazioni
void zero();
//@cmember Sposta la relazione sul record successivo del file principale (chiama <mf TRelation::position_rels>)
virtual int next(TReclock lockop = _nolock)
{ return file().next(lockop) == NOERR ? position_rels(_isequal, lockop) : file().status(); }
//@cmember Sposta la relazione sul record precedente del file principale (chiama <mf TRelation::position_rels>)
virtual int prev(TReclock lockop = _nolock)
{ return file().prev(lockop) == NOERR ? position_rels(_isequal, lockop) : file().status(); }
//@cmember Sposta la relazione sul record successivo del file principale (chiama <mf TRelation::position_rels>)
virtual int next(TDate& atdate)
{ return file().next(atdate) == NOERR ? position_rels(_isequal, _nolock, atdate) : file().status(); }
//@cmember Sposta la relazione sul record precedente del file principale (chiama <mf TRelation::position_rels>)
virtual int prev(TDate& atdate)
{ return file().prev(atdate) == NOERR ? position_rels(_isequal, _nolock, atdate) : file().status(); }
//@cmember Sposta la relazione sul primo record del file principale (chiama <mf TRelation::position_rels>)
virtual int first(TReclock lockop = _nolock)
{ return file().first(lockop) == NOERR ? position_rels(_isequal, lockop) : file().status(); }
//@cmember Sposta la relazione sull'ultimo record del file principale (chiama <mf TRelation::position_rels>)
virtual int last(TReclock lockop = _nolock)
{ return file().last(lockop) == NOERR ? position_rels(_isequal, lockop) : file().status(); }
//@cmember Salta <p nrec> posizione dalla corrente sul file principale (chiama <mf TRelation::position_rels>)
virtual int skip(TRecnotype nrec, TReclock lockop = _nolock)
{ return file().skip(nrec, lockop) == NOERR ? position_rels(_isequal, lockop) : file().status(); }
//@cmember Legge il record (chiama <mf TRelation::position_rels>)
virtual int read(TIsamop op = _isgteq, TReclock lockop = _nolock, TDate& atdate = (TDate&)botime)
{ return file().read(op, lockop, atdate) == NOERR ? position_rels(_isequal, lockop, atdate) : file().status();}
// @cmember Ritorna il descrittore del file
TLocalisamfile& lfile(int logicnum = 0) const;
// @cmember Ritorna il descrittore del file
TLocalisamfile& lfile(const char* name) const;
// @cmember Ritorna il descrittore del file (chiama <mf TRelation::lfile>)
TLocalisamfile& operator[] (int logicnum) const
{ return lfile(logicnum); }
// @cmember Abilita/disabilita la scrittura dei record collegati sul file
void write_enable(int logicnum = 0, const bool on = TRUE) ;
// @cmember Abilita/disabilita la scrittura sul file
void write_enable(const char* name, const bool on = TRUE) ;
// @cmember Disabilita la scrittura sul file (chiama <mf TRelation::write_enable>)
void write_disable(int logicnum = 0)
{ write_enable(logicnum, FALSE); }
// @cmember Disabilita la scrittura sul file (chiama <mf TRelation::write_enable>)
void write_disable(const char* name)
{ write_enable(name, FALSE); }
// @cmember Ritorna il record corrente del file <p logicnum>
// (chiama <mf TRelation::lfile>)
TRectype& curr(int logicnum = 0) const
{ return lfile(logicnum).curr(); }
// @cmember Posiziona il numero logico sul record successivo
bool next_match(int logicnum, const char* fieldlist = NULL, int nkey = 0);
// @cmember Aggiunge una nuovo file alla relazione partendo dal descrittore del file
bool add(TLocalisamfile* f, const char* relexprs, int key, int linkto, int alias, bool allow_lock);
// @cmember Aggiunge una nuovo file alla relazione partendo dal numero logico del file
bool add(int logicnum, const char* relexprs, int key = 1, int linkto = 0, int alias = 0, bool allow_lock = FALSE);
// @cmember Aggiunge una nuovo file alla relazione partendo dal nome della tabella
bool add(const char* tabname, const char* relexprs, int key = 1, int linkto = 0, int alias = 0, bool allow_lock = FALSE);
// @cmember Sostituisce nella relazione un file
void replace(TLocalisamfile* f, int index = 0);
// @cmember Aggiunge il record corrente
virtual int write (bool force = TRUE, TDate& atdate = (TDate&)botime);
// @cmember Riscrive il record corrente
virtual int rewrite (bool force = TRUE, TDate& atdate = (TDate&)botime);
// @cmember Elimina il record corrente
virtual int remove (TDate& atdate = (TDate&)botime);
// @cmember Controlla se e' stata raggiunta la fine del file
// (se <p logicnum> = 0 dell'intera relazione, altrimenti del file indicato )
bool eof( int logicnum = 0) const
{ return lfile(logicnum).eof(); }
// @cmember Controlla se e' stata raggiunta l'inizio del file
// (se <p logicnum> = 0 dell'intera relazione, altrimenti del file indicato )
bool bof( int logicnum = 0) const
{ return lfile(logicnum).bof(); }
// @cmember Ritorna lo stao del file indicato (se <p logicnum> = 0 dell'intera relazione,
// altrimenti del file indicato )
bool status(int logicnum = 0) const
{ return lfile(logicnum).status(); }
// @cmember Controlla se l'ultima operazione sul file e' stat effettuata correttamente
// (se <p logicnum> = 0 dell'intera relazione, altrimenti del file indicato )
bool good( int logicnum = 0) const
{ return lfile(logicnum).good(); }
// @cmember Controlla se l'ultima operazione sul file ha generato un errore
// (se <p logicnum> = 0 dell'intera relazione, altrimenti del file indicato )
bool bad( int logicnum = 0) const
{ return lfile(logicnum).bad(); }
// @cmember Controlla se e' il file e' vuoto
// (se <p logicnum> = 0 dell'intera relazione, altrimenti del file indicato )
bool empty( int logicnum = 0) const
{ return lfile(logicnum).empty(); }
// @cmember Controlla se la relazione e' corretta
bool isconsistent (bool reset = FALSE);
// @cmember Controlla se c'e' un record ed e' il primo match (non si e' mai fatta
// <mf TRelation::position_rels>)
bool is_first_match(int logicnum);
// @cmember Ritorna il numero di files collegati
int items()
{ return _reldefs.items(); }
// @cmember Ritorna TRUE se il file <p logicnum> e' nella relazione
bool exist(int logicnum) const;
// @cmember Salva la posizione attuale di tutti i file della relazione
void save_status () ;
// @cmember Ripristina la posizione attuale di tutti i file della relazione
void restore_status () ;
// positioning operators. return status
// @cmember Sposta il puntatore corrente di <p npos> posizioni in avanti
// (ritorna lo stato)
TRecnotype operator +=(const TRecnotype npos)
{ return skip(npos); }
// @cmember Sposta il puntatore corrente di <p npos> posizioni in dietro
// (ritorna lo stato)
TRecnotype operator -=(const TRecnotype npos)
{ return skip(-npos); }
// @cmember Sposta il puntatore corrente di una posizione in avanti
// (ritorna lo stato)
TRecnotype operator ++()
{ return next(); }
// @cmember Sposta il puntatore corrente di una posizione in dietro
// (ritorna lo stato)
TRecnotype operator --()
{ return prev(); }
// @cmember Costruttore dal numero logico del file
TRelation(int logicnum);
// @cmember Costruttore dal nome della tabella
TRelation(const char* tabname);
// @cmember Costruttore dal nome del file
TRelation(TLocalisamfile* f);
// @cmember Distruttore
virtual ~TRelation();
};
class TExpression;
// @doc EXTERNAL
// @type FILTERFUNCTION | Prototipo funzione che controlla se il record debba essere incluso nel cursore
typedef bool (*FILTERFUNCTION)(const TRelation* r);
// @doc EXTERNAL
// @class TCursor | Classe per la definizione di un cursore su di una relazione
//
// @base public | TContainer
class TCursor : public TContainer
// @author:(INTERNAL) Villa
// @access:(INTERNAL) Private Member
{
// @cmember:(INTERNAL) Relazione su cui costruire il cursore
TRelation* _if;
// @cmember:(INTERNAL) Chiave del file principale
int _nkey;
// @cmember:(INTERNAL) Posizione corrente
TRecnotype _pos;
// @cmember:(INTERNAL) Numero totale di record che verificano il filtro
TRecnotype _totrec;
// @cmember:(INTERNAL) Numero dell'ultimo record
TRecnotype _lastrec;
// @cmember:(INTERNAL) Chiave dell'ultimo record
TRecnotype _lastkrec;
// @cmember:(INTERNAL) Nome assoluto del file principale
TFilename _filename;
// @cmember:(INTERNAL) Filtro definito con la <mf TCursor::set_filter>
TString _filter;
// @cmember:(INTERNAL) Nome della chiave iniziale
TString _keyfrom;
// @cmember:(INTERNAL) Nome della chiave finale
TString _keyto;
// @cmember:(INTERNAL) Espressione del filtro relativo
TExpression* _fexpr;
// @cmember:(INTERNAL) Indica se e' stata messa in attesa (non puo' essere modificato)
bool _frozen;
// @cmember:(INTERNAL) Flag che permette l'update della relazione per l'espressione-filtro
bool _filter_update;
// @cmember:(INTERNAL) Flag che permette l'update della relazione per la funzione-filtro
bool _filterfunction_update;
// @cmember:(INTERNAL) Funzione filtro
FILTERFUNCTION _filterfunction;
// @cmember:(INTERNAL) Nome del file indice
TFilename _indexname;
// @cmember:(INTERNAL) Crea (o aggiorna) effettivamente l'indice del cursore
TRecnotype update();
// @access Protected Member
protected:
// @cmember Apre il file di indice
FILE* open_index(bool create = FALSE);
// @cmember Ritorna se e' stato modificato il cursore (cioe' quando occorre fare l'update)
virtual bool changed();
// @cmember Costruisce il cursore a partire dal record
virtual TRecnotype buildcursor(TRecnotype rp);
// @cmember Permette di creare una pagina di cursori
virtual int filtercursor(int pagecnt, TRecnotype* page);
// @cmember Posiziona il cursore in modo che il record corrente corriponda alla
// posizione dell'indice temporaneo
TRecnotype readrec();
// @cmember Setta il filtro sul cursore
void filter(const char* filter, const TRectype* from = NULL, const TRectype* to = NULL);
// @cmember Indica se e' possibile fare l'update sulla relazione (se e' possibile
// sia sull'espressione-filtro che sulla funzione-filtro)
bool update_relation() const
{return (_filter_update || _filterfunction_update);}
// @access Public Member
public:
// @cmember Si sposta alla posizione <p nr>
TRecnotype operator =(const TRecnotype nr);
// @cmember Si sposta di <p nr> posizioni dalla corrente in avanti
TRecnotype operator +=(const TRecnotype nr);
// @cmember Si sposta di <p nr> posizioni dalla corrente in dietro
TRecnotype operator -=(const TRecnotype npos)
{ return operator +=(-npos); }
// @cmember Ritorna il primo oggetto del cursor
TObject* first_item( )
{ operator =( 0 ); return &curr( ); }
// @cmember Ritorna l'oggetto del cursor successivo al corrente
TObject* succ_item( )
{ operator +=( 1 ); return &curr( ); }
// @cmember Ritorna l'oggetto del cursor precedente al corrente
TObject* pred_item( )
{ operator -=( 1 ); return &curr( );}
// @cmember Ritorna l'ultimo oggetto del cursor
TObject* last_item( )
{ operator =( items( ) -1 ); return &curr( ); }
// @cmember Ritorna il numero di oggetti del cursor
long objects( )
{ return items( ); }
// @cmember Ritorna la posizione corrente
TRecnotype& pos()
{ return _pos; }
// @cmember Ritorna il numero totale di record
TRecnotype items();
// @cmember Ritorna la dimensione del file principale
TRecnotype size() const
{ return file().eod(); }
// @cmember Ritorna il nome della chiave iniziale
const TString& from() const
{ return _keyfrom; }
// @cmember Ritorna il nome della chiave finale
const TString& to() const
{ return _keyto; }
// @cmember Ritorna il descrittore del file principale
TRectype& curr(int log = 0) const
{ return _if->curr(log); }
// @cmember Ritorna il descrittore della tabella
TRectype& curr(const char * tab) const
{ return _if->lfile(tab).curr(); }
//@cmember Testa la presenza di un record senza spostare il cursore
int test(TIsamop op = _isequal, TReclock lockop = _nolock) const;
// @cmember Legge il record
TRecnotype read(TIsamop op = _isgteq, TReclock lockop = _nolock, TDate& atdate = (TDate&)botime);
// @cmember Mette un lock sul record
int lock(TReclock = _lock);
// @cmember Toglie un lock sul record (chiama <mf TCursor::lock>)
int unlock()
{ return lock(_unlock); }
// @cmember Controlla che si tratti di un oggetto valido
virtual bool ok() const;
// @cmember Ritorna il filtro
const char* filter() const
{ return _filter; }
// @cmember Permette di mettere in attesa il cursore
void freeze(bool on = TRUE)
{ _frozen = on; }
// @cmember Controlla se il cursore e' congelato
bool frozen() const
{ return _frozen; }
// @cmember Permette di modificare l'espressione-filtro
void setfilter(const char* filter_expr, bool update=FALSE)
{ filter(filter_expr); _filter_update = update; }
// @cmember Setta la regione-filtro dal record <p from> al record <p to>
void setregion(const TRectype& from, const TRectype& to)
{ filter(NULL,&from, &to); }
// @cmember Ritorna la relazione del cursore
TRelation* relation() const
{ return _if; }
// @cmember Ritorna il file della relazione con numero logico <p lnum>
TLocalisamfile& file(int lnum = 0) const
{ return _if->lfile(lnum); }
// @cmember Ritorna il file della relazione con nome <p name>
TLocalisamfile& file(const char* name) const
{ return _if->lfile(name); }
// @cmember Riposiziona l'albero delle relazione (chiama <mf TRelation::position_rels>)
int repos()
{ return _if->position_rels(); }
// @cmember Ritorna l'espressione-filtro
TExpression* expression() const
{ return _fexpr; }
// @cmember Ritorna la funzione-filtro
FILTERFUNCTION filterfunction() const
{ return _filterfunction; }
// @cmember Setta la chiave del file principale alla chiave del cursore
void setkey()
{ file().setkey(_nkey); }
// @cmember Setta la chiave del file principale alla chiave del cursore
void setkey(int nkey);
// @cmember Ritorna la chiave del cursor
int key() const
{ return _nkey; }
// @cmember Posizione il numero logico sul record successivo (chiama <mf TRelation::next_match>)
bool next_match(int lognum, const char* fl = NULL, int nk = 0);
// @cmember Controlla se c'e' un record ed e' il primo match (chiama <mf TRelation::is_first_match>)
bool is_first_match(int ln);
// @cmember Setta la fuzione-filtro
void set_filterfunction(FILTERFUNCTION ff, bool update=FALSE)
{ _filterfunction = ff; _lastrec = 0L; _filterfunction_update = update;}
// @cmember Controllla se esiste un fuiltro sul cursor
bool has_filter() const
{ return _filter.not_empty() || _filterfunction; }
// @cmember Salva la posizione attuale di tutti i file del cursore
void save_status ()
{ _if->save_status(); }
// @cmember Ripristina la posizione attuale di tutti i file del cursore
void restore_status ()
{ _if->restore_status(); }
// @cmember Costruttore
TCursor(TRelation* f, const char* filter = "", int key = 1, const TRectype* from = NULL, const TRectype* to = NULL);
// @cmember Distruttore
virtual ~TCursor();
};
// @doc EXTERNAL
// @class TSorted_cursor | Costruisce e gestisce un cursore ordinato per chiavi diverse da quelle specificate nel file.
class TSorted_cursor : public TCursor
// @author:(INTERNAL) Angelo
// @comm Il formato dell'espressione deve essere: [LF->]FIELDNAME[[from,to]][+<pipe>-]... Inoltre tutta l'espressione puo' essere racchiusa
// dall'operatore UPPER(), per controlli non case-sensitive.
// <nl><p FIELDNAME> e' il nome del campo per quale si vuole effettuare il sort, LF indica il numero logico del file (appartenente alla relazione!).
// <nl><p from> e <p to> sono parametri opzionali usati per specificare un sottocampo. Per default prende l'intera lunghezza.
// <nl><p +> e <p -> sono parametri opzionali usati per specificare il tipo di ordinamento: <p +> significa crescente, <p -> significa
// decrescente. Per default l'ordinamento e' crescente. E' cosi' possibile creare chiavi con campi non appartententi al
// file principale della relazione.
// <nl>Es. "CODCF-<pipe>TIPOCF<pipe>SOTTOCONTO+<pipe>UPPER(20->RAGSOC[1,40]-)"
// @access:(INTERNAL) Private Member
{
// @cmember:(INTERNAL) Espressione per l'ordinamento
TToken_string _order_expr;
// @cmember:(INTERNAL) Puntatore all'oggetto per ordinare il cursore (vedi <c TSort>)
TSort* _sort;
// @cmember:(INTERNAL) Indica se l'espressione e' cambiata
bool _is_changed_expr;
// @cmember:(INTERNAL) Indica se l'espressione e' valida
bool _is_valid_expr;
// @access Protected Member
protected:
// @cmember Controlla la validita' dell'espressione
bool check_expr(TString& s);
// @cmember Controlla se la singola espressione contiene l'operatore UPPER(), ritornandone l'argomento
bool is_upper(TString& s);
// @cmember Costruisce il cursore a partire dal record (vedi <c TCursor>)
virtual TRecnotype buildcursor(TRecnotype rp);
// @cmember Permette di creare una pagina di cursori (vedi <c TCursor>)
virtual int filtercursor(int pagecnt, TRecnotype* page);
// @cmember Ritorna se e' stato modificato il cursore (cioe' quando occorre fare l'update) (vedi <c TCursor>)
virtual bool changed();
// @access Public Member
public:
// @cmember Si sposta alla posizione <p nr>
TRecnotype operator =(const TRecnotype nr)
{return TCursor::operator =(nr); }
// @cmember Permette di cambiare l'ordinamento del cursore.
void change_order(const char* order_expr);
// @cmember Costruttore
TSorted_cursor(TRelation *f,const char * order_expr, const char * filter = "", int key = 1, const TRectype* from = NULL, const TRectype* to = NULL);
// @cmember Distruttore
virtual ~TSorted_cursor();
};
// @doc EXTERNAL
// @class TFieldref | Classe per la definizione di riferimenti ad un campo di una relazione
//
// @base public | TObject
class TFieldref : public TObject
// @author:(INTERNAL) Guido
// @access:(INTERNAL) Private Member
{
// @cmember:(INTERNAL) Numero del file
short _fileid;
// @cmember:(INTERNAL) Nome tabella o stringa col numero del file
TString _id;
// @cmember:(INTERNAL) Nome del campo
TString _name;
// @cmember:(INTERNAL) Sottostringa di partenza
int _from;
// @cmember:(INTERNAL) Sottostringa di arrivo
int _to;
// @access Protected Member
protected:
// @cmember Stampa l'oggetto
virtual void print_on(ostream& out) const;
// @cmember Duplica l'oggetto TFieldref
virtual TObject* dup() const;
// @access Public Memeber
public:
// @cmember Costruttore
TFieldref();
// @cmember Costruttore
TFieldref(const TString&, short defid);
// @cmember Operatore di assegnamento
TFieldref& operator =(const TString& s);
// @cmember Controlla la validita' dell'oggetto (TRUE se il numero del file e' valido)
virtual bool ok() const
{ return _name.not_empty(); }
// @cmember Ritorna il numero del file
int file() const
{ return _fileid; }
// @cmember Setta il numero del file
void set_file(int f);
// @cmember Ritorna il nome del campo
const TString& name() const
{ return _name; }
// @cmember Setta il nome del campo
void set_name(const char* n)
{ _name = n; }
// @cmember Setta <p from>
void set_from(int f)
{ if (f > 0) f--; else f = 0; _from = f; }
// @cmember Setta <p to>
void set_to(int t)
{ _to = t; }
// @cmember Ritorna <p from>
int from() const
{ return _from; }
// @cmember Ritorna <p to>
int to() const
{ return _to; }
// @cmember Ritorna la lunghezza del campo di <p TRectype>
int len(const TRectype &rec) const;
// @cmember Cerca nella relazione il campo e ne ritorna il contenuto
const char* read(const TRelation&) const;
// @cmember Cerca nel record il campo e ne ritorna il contenuto
const char* read(const TRectype&) const;
// @cmember Cerca nella relazione il campo e vi scrive <p val>
void write(const char* val, TRelation&) const;
// @cmember Cerca nel record il campo e vi scrive <p val>
void write(const char* val, TRectype& rec) const;
};
int name2log(const char* name);
// @doc INTERNAL
// @class TRelation_description | Gestisce l'uso interattivo di una relazione (scelta campi, descrizione)
//
// @base public | TObject
class TRelation_description : public TObject
// @author:(INTERNAL) Guido
// @access:(INTERNAL) Private Member
{
// @cmember:(INTERNAL) Relazione descritta
TRelation* _rel;
// @cmember:(INTERNAL) Nome dei files della relazione
TString_array _files;
// @cmember:(INTERNAL) Array di campi
TArray _fields;
// @cmember:(INTERNAL) Numero logico del file corrente
int _cur_file;
// @cmember:(INTERNAL) Numero del campo corrente
int _cur_field;
// @cmember:(INTERNAL) UNUSED
bool _menu;
// @cmember:(INTERNAL) File corrente
TToken_string _cfile;
// @cmember:(INTERNAL) Campo corrente
TToken_string _cfield;
// @access Protected Member
protected:
// @cmember Inizializza l'array di stringhe con i nomi dei files
void init_files_array();
// @cmember Legge la relazione
void read_rel();
// @access Public Member
public:
// @cmember Controlla se si tratta di un oggetto valido (se il numero dei files e' <gt> di 0)
virtual bool ok() const
{ return _files.items() > 0; }
public:
// @cmember Seleziona il file <p id>
bool choose_file (int id = 0);
// @cmember Setta come file corrente quello con numero logico <p id>
bool set_cur_file(int id = 0);
// @cmember Seleziona il campo <p fld> del file selezionato
bool choose_field(const char* fld = "");
// @cmember Costruisce un menu'
bool build_menu(const char* title = "Database");
// @cmember Rimuove il menu' costruito con <mf TRelation_description::build_menu>
bool remove_menu();
// @cmember Ritorna il numero logico del file selezionato (vedi <mf TRelation_description::choose_file>)
int file_num();
// @cmember Ritorna la descrizione del file selezionato (vedi <mf TRelation_description::choose_file>)
const char* file_desc();
// @cmember Setta la descrizione del file selezionato
void file_desc(const char* desc);
// @cmember Setta la descrizione del campo
bool set_field_description(const char* field, const char* des);
// @cmember Ritorna la descrizione del campo
const char* get_field_description(const char* field);
// @cmember Ritorna la descrizione del campo selezionato (vedi <mf TRelation_description::choose_file>)
const char* field_desc();
// @cmember Setta la descrizione del campo selezionato
void field_desc(const char* desc);
// @cmember Ritorna il nome del campo selezionato (vedi <mf TRelation_description::choose_field>)
const char* field_name();
// @cmember Ritorna la lunghezza del campo selezionato (vedi <mf TRelation_description::choose_field>)
int field_len();
// @cmember Ritorna il tipo del campo selezionato (vedi <mf TRelation_description::choose_field>)
TFieldtypes field_type();
// @cmember Ritorna l'array di tutti nomi dei files
const TString_array& get_all_desc() const
{ return _files; }
// @cmember Cambia la relazione descritta
void change_relation(TRelation& rel, TString_array& arr);
// @cmember Stampa l'oggetto
virtual void print_on(ostream& out) const;
// @cmember Costruttore
TRelation_description(TRelation& r);
// @cmember Distruttore
virtual ~TRelation_description();
// @devnote Domani o doman l'altro gestira' l'editing interattivo e grafico
};
#endif
// ** EOF relation.h