2023年12月22日发(作者:)
dbf文件C/C++的操作库程序。
求:dbf文件C/C++的操作库程序。
/************************************************************************
DBFOP for C++ V1.00 ,1995.1.10
Develop by John,Liao
Modified by Zhanghao. 1998.05.18
This Module include the C++ headfile ,
and C++ resource file .
This module is develop for use DBF(DBASEIII,DBASEII,MFOXBASE,FOXPRO 2.x)
and IDX(MFOXBASE).but use IDX only allow read or change the field that
isn't key word.
Support netware share .flielock,fileunlock,recordlock,recordunlock.
*************************************************************************/
/* -----------------------------------------------------------------------
The class DBF is interface to custom,all function that given
can be invoked by use the class DBF.
------------------------------------------------------------------------
1995.7.29 Change file option fxxx to xxx like _fsopen replace with sopen
1995.7.31 Change dowith option when type='N'
1995.7.31 Add option DBF::append(),DBF::clear();
1998.5.18 Add Foxpro 2.x DBF process.
-------------------------------------------------------------------------*/
#include "stdafx.h"
#ifdef DEBUG
#define debugm AfxMessageBox
#define new DEBUG_NEW
#endif
static INT2 ccc(CHAR *,INT2,INT2);
INT2 ccc(CHAR * ptsr,INT2 len,INT2 bit)
{
CHAR temp1[30],temp11[30],i1;
CHAR temp2[30],temp22[30],i2;
INT2 tempi,i;
CHAR * ps,*ps1;
for(ps1=ptsr;(*ps1==' ')&&(*ps1!='x0');ps1++);
ps=strchr(ps1,'.');
if(ps==NULL){ // NOT HAVE '.'
strcpy(temp1,ps1);
temp2[0]='x0';
}else{
*ps='x0';
strcpy(temp1,ps1);
ps++;
strcpy(temp2,ps);
}
i1=len-(bit?(bit+1):0);
if((int)strlen(temp1)>;(int)i1){
strncpy(temp11,temp1,i1);
temp11[i1]='x0';
}else{
tempi=i1-strlen(temp1);
for(i=0;i strcpy(temp11+tempi,temp1); } // ------------------------------------------ if(bit>;0){ if((int)strlen(temp2)>;(int)bit){ strncpy(temp22,temp2,bit); temp22[bit]='x0'; }else{ i2=strlen(temp2); tempi=bit-strlen(temp2); strcpy(temp22,temp2); for(i=0;i temp22[bit]='x0'; } } strcpy(ptsr,temp11); if(bit!=0){ strcat(ptsr,"."; strcat(ptsr,temp22); } return 0; } INT2 IDX_BLOCK::skip() { if(curp>;=(INT2)items-1){ return -2; } curp++; // double return 0; } INT2 IDX_BLOCK::find(CHAR * key) { INT2 compi=keylen; CHAR *p=buff+12; INT2 RetCode,i; if((int)strlen(key)<(int)keylen) compi=strlen(key); for(i=0,p=buff+12;i RetCode=strncmp(key,p,compi); if(RetCode==0) // Founded this key if(flag>;=2){ // .and. this is a leaf or leaf&root node curp=i; return 0; // Founded ,OK return to master }else{ // .and. this is a frame or root node curp=i; return -10; // This is a ROOT,Maybe in gaven BLOCK } if(RetCode<0){ //if the key < curent key in idx file if(flag<2){ //and this is FRAME or ROOT node curp=i; //in FRAME or ROOT node key is MAXKEY in given node return -10;//This is a ROOT,Maybe in gaven BLOCK } } } return -3; // Maybe in NextBlock } IDX::IDX() { Installed=0; //fp=NULL; handle=-1; rootpos=blocks=0l; key_len=0; return ; } IDX::~IDX() { if(this->;handle!=-1){ close(handle); handle=-1; } } // open function open the idx file INT2 IDX:{ pen(CHAR * filename) CHAR buff[30]; // fp=_fsopen(filename,"rb",SH_DENYNONE); // change by liaoj int 1999.3.22 handle=sopen(filename,_O_RDONLY|_O_BINARY,_SH_DENYNO,_S_IREAD); /* handle=sopen(filename,O_RDWR|O_BINARY|O_DENYNONE, SH_DENYNONE,S_IREAD|S_I_write); */ // if(fp==NULL) return -1; if(handle==-1) return -1; if(_lseek(handle,0,SEEK_SET)!=0) return -1; if(read(handle,buff,30)!=30) return -1; rootpos=*(UINT4 *)buff; blocks=*(UINT4 *)(buff+; key_len=*(INT2 *)(buff+12); Len(key_len); ock(this->;handle,rootpos); while(g()<2){ ock(this->;handle,ult()); } GoHome(); return 0; } INT2 IDX:{ UINT4 PrevBlock; if(()!=0){ PrevBlock=v(); if(PrevBlock==0xffffffffl){ return -1; } ock(this->;handle,(INT4)PrevBlock); (); } return 0; } INT2 IDX::Next() { UINT4 NextBlock; if(()!=0){ // Is already in the last node in this block NextBlock=t(); if(NextBlock==0xffffffffl){ return -2; } rev() ock(this->;handle,(INT4)NextBlock); (); } return 0; } INT2 IDX::Find(CHAR * key) { INT2 RetCode; ock(this->;handle,rootpos); for(;{ RetCode=(key); switch(RetCode){ case 0: return 0; case -1: return -1; case -2: if(v()==(UINT4)0xffffffffl){ return -1; }else{ ock(this->;handle,v()); } break; case -3: if(t()==(UINT4)0xffffffffl){ return -1; }else { ock(this->;handle,t()); } break; case -10: ock(this->;handle,ult()); break; default: // ------------------------------------------------- // Fatal Error :: return code is not allow // in class IDX_BLOCK::find(CHAR * ); // ------------------------------------------------- break; } } } INT2 IDX::Skip() { return Next(); } INT2 IDX::GoHome() { while(v()!=(UINT4)0xffffffffl){ ock(this->;handle,v()); }; (); return 0; } INT2 IDX::GoEnd() { while(t()!=(UINT4)0xffffffffl){ ock(this->;handle,t()); }; (); return 0; } UINT4 IDX_BLOCK::GetResult() { CHAR tf[5]; CHAR * p=buff+12+curp*(keylen+4); p+=keylen; tf[3]=p[0];tf[2]=p[1];tf[1]=p[2];tf[0]=p[3]; return *(UINT4 * )tf; } //INT2 IDX_BLOCK::ReadBlock(FILE * fp,UINT4 pos) INT2 IDX_BLOCK::ReadBlock(INT2 handle,UINT4 pos) { // fseek(fp,pos,SEEK_SET); _lseek(handle,pos,SEEK_SET); // fread(buff,512l,1,fp); read(handle,buff,512); flag=buff[0]; count=buff[1]; items=buff[2]; prev=*(UINT4 *)(buff+4); next=*(UINT4 *)(buff+ curp=0; return 0; } //------------------Next is DBF ---------------------- DBF:BF() ; { Installed=0; First=NULL; pIDX=NULL; handle=-1; buff=NULL; // --------------------------------- SwapBuffer=NULL; MaxRecNum=0; CurRecNum=0; // -------------------------------- current_recno=record_no=0l; record_len=0; Name[0]='x0'; changeflag=0; dbferrno=0; fieldvalue=NULL; } DBF::~DBF() { if(First!=NULL){ delete First; First=NULL; } if(SwapBuffer!=NULL) delete SwapBuffer; SwapBuffer=NULL; MaxRecNum=0; CurRecNum=0; if(pIDX!=NULL){ delete First; pIDX=NULL; } if(handle!=-1){ // this ::close(handle); handle=-1; } if(buff!=NULL){ delete buff; buff=NULL; } if(fieldvalue!=NULL){ delete fieldvalue; fieldvalue=NULL; } return; } INT2 DBF::Clear() { memset(buff,' ',record_len); return 0; } INT2 DBF::AppendBlank() { CHAR tempbuf[100]; UINT4 temp_recno; INT2 i; INT4 offset; //- if(!Installed){ // Not open this file dbferrno=ClassNotInit; sprintf(this->;dbferrmsg,"ClassNotInit!" return ClassNotInit; } if(_lseek(handle,0l,SEEK_SET)!=0){ dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!" return this->;dbferrno; } if(read(handle,tempbuf,!={ ; ; this->;dbferrno=ReadFileError; sprintf(this->;dbferrmsg,"ReadFileError!" return this->;dbferrno; } temp_recno=++(*(UINT4*)(tempbuf+4)); if(_lseek(handle,0l,SEEK_SET)!=0){ this->;dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!" return dbferrno; } if(_write(handle,tempbuf,!={ ; ; this->;dbferrno=WriteFileError; sprintf(this->;dbferrmsg,"WriteFileError!" return dbferrno; } offset=(INT4)head_len+(temp_recno-1l)*record_len; _lseek(handle,offset,SEEK_SET); ; for(i=0;i _write(handle," ",1); _write(handle,"x1a",1); this->;ReOpen(); this->;GoTo(temp_recno); return 0; } INT2 DBF::Append() { CHAR tempbuf[100]; UINT4 temp_recno; INT4 offset; if(!Installed){ // Not open this file dbferrno=ClassNotInit; sprintf(this->;dbferrmsg,"ClassNotInit!" return ClassNotInit; } if(_lseek(handle,0l,SEEK_SET)!=0){ dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!" return SeekFileError; } if(read(handle,tempbuf,!={ ; ; this->;dbferrno=ReadFileError; sprintf(this->;dbferrmsg,"ReadFileError!" return dbferrno; } temp_recno=++(*(UINT4*)(tempbuf+4));// recordnum+1; if(_lseek(handle,0l,SEEK_SET)!=0){ this->;dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!"); return dbferrno; } if(_write(handle,tempbuf,!={ ; this->;dbferrno=WriteFileError; sprintf(this->;dbferrmsg,"WriteFileError!"); return dbferrno; } offset=(INT4)head_len+(temp_recno-1l)*record_len; if(_lseek(handle,offset,SEEK_SET)!=offset){ this->;dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!"); return dbferrno; } _write(handle,buff,(UINT2)record_len); _write(handle,"x1a",1); this->;ReOpen(); this->;GoTo(temp_recno); return 0; } INT2 DBF::dbf_wbuff() { //CHAR tempbuf[100]; INT4 offset; offset=(INT4)head_len+(current_recno-1l)*record_len; if(current_recno<=0){ dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return dbferrno; } if(changeflag==0){ dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); return DBFOK; } if(_lseek(handle,offset,SEEK_SET)!=offset){ dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!"); return dbferrno; } if(_write(handle,buff,(UINT2)record_len)!=(UINT2)record_len){ dbferrno=WriteFileError; sprintf(this->;dbferrmsg,"WriteFileError!"); return dbferrno; } dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); return DBFOK; } INT2 DBF::dbf_buff() { INT4 offset=(INT4)head_len+(current_recno-1l)*record_len; if(current_recno<=0){ dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return dbferrno; } if(_lseek(handle,offset,SEEK_SET)!=offset){ dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!"); return dbferrno; } if(::eof(handle)){ dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!"); return dbferrno; } if(read(handle,buff,(UINT2)record_len)!=(UINT2)record_len){ dbferrno=ReadFileError; sprintf(this->;dbferrmsg,"ReadFileError!"); return dbferrno; } changeflag=0; dbferrno=0; sprintf(this->;dbferrmsg,"DBFOK!"); return 0; } INT2 DBF::Zap() { CHAR tempbuf[100]; if(!Installed){ // Not open this file dbferrno=ClassNotInit; sprintf(this->;dbferrmsg,"ClassNotInit!"); return dbferrno; } _lseek(handle,0l,SEEK_SET); //if(fread(tempbuf,32l,1l,fp)!=1){ if(read(handle,tempbuf,32)!=32){ this->;Close(); dbferrno=NotDBFFile; sprintf(this->;dbferrmsg,"NotDBFFile!"); return dbferrno; } *(UINT4 *)(tempbuf+4)=0l; // record_no if(chsize(handle,head_len)!=0){ // ------------------------ this->;dbferrno=ChsizeFileError; sprintf(this->;dbferrmsg,"ChsizeFileError!"); return dbferrno; } _lseek(handle,0l,SEEK_SET); if(_write(handle,tempbuf,32)!=32){ //this->;close(); this->;dbferrno=WriteFileError; sprintf(this->;dbferrmsg,"WriteFileError!"); return WriteFileError; } _lseek(handle,0l,SEEK_END); _write(handle,"x1ax0",2); MaxRecNum=0; CurRecNum=0; lock_flag=0; ReOpen(); dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); return this->;dbferrno; } INT2 DBF::Open(CHAR * filename,INT2 OpenMode_Par,INT2 DBFType_Par) { CHAR tempbuf[100]; INT2 i,j,FieldOffset; struct FIELD * tpf; if(Installed){ this->;Close(); } strcpy(Name,filename); OpenMode=OpenMode_Par; DBFType=DBFType_Par; if(OpenMode==ReadWrite){ handle=_sopen(Name,_O_RDWR|_O_BINARY,_SH_DENYNO,_S_IREAD|_S_IWRITE); }else{ handle=_sopen(Name,_O_RDONLY|_O_BINARY,_SH_DENYNO,_S_IREAD); } if(handle==-1){ dbferrno=FileOpenFailure; sprintf(this->;dbferrmsg,"FileOpenFailure!"); return dbferrno; } _lseek(handle,0l,SEEK_SET); if(read(handle,tempbuf,32)!=32){ this->;Close(); dbferrno=ReadFileError; sprintf(this->;dbferrmsg,"ReadFileError!"); return dbferrno; } record_no=*(UINT4 *)(tempbuf+4); head_len=*(UINT2 *)(tempbuf+8); record_len=*(UINT2*)(tempbuf+10); fieldnum=(head_len)/32-1; // need automatic detect the dbf file type is foxbase or clipper if(DBFType==AutoDetect){ if((head_len-1)%32==0) DBFType=Foxbase; else DBFType=Clipper; } if(buff!=NULL){ delete buff; buff=NULL; } buff=(CHAR *) new CHAR[record_len+20]; if(buff==NULL){ #ifdef DEBUG debugm("DBF::Open alloc failure!"); #endif this->;Close(); dbferrno=NotEnoughMemory; sprintf(this->;dbferrmsg,"NotEnoughMemory!"); return dbferrno; } // memset strset Clear(); // add by liaoj 1996.12.24 if(record_no==0l){ current_recno=Empty; }else { current_recno=1; dbf_buff(); } pFIELD=new FIELD[fieldnum]; if(pFIELD==NULL){ #ifdef DEBUG debugm("DBF:#endif this->;Close(); pen alloc failure!"); dbferrno=NotEnoughMemory; sprintf(this->;dbferrmsg,"NotEnoughMemory!"); return dbferrno; } _lseek(handle,32l,SEEK_SET); tpf=&(pFIELD[0]); FieldOffset=1; for(i=0;i // fread(tempbuf,32l,1l,fp); // memset read(handle,tempbuf,32); memcpy(tpf,tempbuf,18); j=strlen(tpf->;name); // ----------- Cliepper or Foxbase ----- if(DBFType==Foxbase) j=j>;11?11:j; else j=7?7:j; tpf->;name[j]=0; for(j--;j>;=0;j--){ if(tpf->;name[j]==' ') tpf->;name[j]=0; else break; } if(DBFType==Clipper){ tpf->;address=FieldOffset; FieldOffset+=tpf->;len; }else{ tpf->;address=FieldOffset; FieldOffset+=tpf->;len; } } Installed=1; changeflag=0; dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); return 0; } INT2 DBF::SetSwp(INT2 buffer_number) { if (SwapBuffer!=NULL) delete SwapBuffer; CurRecNum=0; MaxRecNum=0; SwapBuffer=(CHAR *) new CHAR[(record_len+1)*buffer_number]; if (SwapBuffer==NULL){ #ifdef DEBUG debugm("GGROUP::SetSwp alloc failure!"); #endif dbferrno=NotEnoughMemory; sprintf(this->;dbferrmsg,"NotEnoughMemory!"); return dbferrno; } CurRecNum=0; MaxRecNum=buffer_number; return DBFOK; } INT2 DBF::AppendToSwp() { if (MaxRecNum==0) return this->;Append(); if (CurRecNum>;=MaxRecNum) FlushSwp(); if (CurRecNum>;=MaxRecNum) { dbferrno=OtherError; sprintf(this->;dbferrmsg,"OtherError!"); return OtherError; } memcpy(SwapBuffer+CurRecNum*record_len,buff,(size_t)record_len); CurRecNum++; return 0; } INT2 DBF::FlushSwp() { CHAR tempbuf[100]; UINT4 temp_recno; // INT2 i; INT4 offset; if(CurRecNum==0) return 0; if(!Installed){ // Not open this file dbferrno=ClassNotInit; sprintf(this->;dbferrmsg,"ClassNotInit!"); return dbferrno; } if(_lseek(handle,0l,SEEK_SET)!=0){ dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!"); return dbferrno; } if(read(handle,tempbuf,8)!=8){ // this->;close(); dbferrno=ReadFileError; sprintf(this->;dbferrmsg,"ReadFileError!"); return dbferrno; } (*(UINT4*)(tempbuf+4))+=(UINT4)CurRecNum;//recordnum+1; temp_recno=(*(UINT4*)(tempbuf+4)); if(_lseek(handle,0l,SEEK_SET)!=0){ this->;dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!"); return dbferrno; } if(_write(handle,tempbuf,8)!=8){ this->;dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!"); return dbferrno; } offset=(INT4)head_len+(temp_recno-(UINT4)CurRecNum)*record_len; if(_lseek(handle,offset,SEEK_SET)!=offset){ this->;dbferrno=SeekFileError; sprintf(this->;dbferrmsg,"SeekFileError!"); return dbferrno; } _write(handle,SwapBuffer,(UINT2)(record_len*CurRecNum)); _write(handle,"x1a",1); this->;ReOpen(); this->;GoTo(temp_recno); CurRecNum=0; sprintf(this->;dbferrmsg,"DBFOK!"); return DBFOK; } // add support delete function in this modul // addby liaoj 19990426 INT2 DBF::Close(int Delete) { if(handle!=-1){ ::close(handle); // unlink if(Delete){ // with delete ::unlink(Name); } handle=-1; } if(pIDX!=NULL){ delete pIDX; pIDX = NULL; } if(buff!=NULL){ delete buff; buff=NULL; } if(SwapBuffer!=NULL) delete SwapBuffer; SwapBuffer=NULL; MaxRecNum=0; CurRecNum=0; if(pFIELD!=NULL){ delete pFIELD; pFIELD=NULL; } if(fieldvalue!=NULL){ delete fieldvalue; fieldvalue=NULL; } lock_flag=0; Installed=0; dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); return DBFOK; } INT2 DBF:{ INT2 RetCode; if(pIDX==NULL){ // skip Not use IDX if(current_recno==-2){ // in the DBFEOF current_recno=record_no; dbferrno=dbf_buff(); return dbferrno; } if(current_recno>;1){ // in the MIDDLE current_recno--; dbferrno=dbf_buff(); return dbferrno; } if(current_recno==1){ // in the FirstRecord rev() current_recno=DBFBOF; dbferrno=DBFOK; return dbferrno; } if((current_recno==DBFEOF)||(current_recno==Empty)){ // in the DBFEOF; dbferrno=RecordOutOfRange; return dbferrno; } dbferrno=OtherError; return dbferrno; } if(current_recno==-2){ // in the DBFBOF pIDX->;GoEnd(); current_recno=pIDX->;GetRecordNo(); if(current_recno>;record_no||current_recno<1){ // Fatal Error :: the IDX file is old dbferrno=IndexIsOutOfDate; sprintf(this->;dbferrmsg,"IndexIsOutOfDate!"); return dbferrno; } if(current_recno==0){ current_recno=Empty; dbferrno=RecordNotFound; sprintf(this->;dbferrmsg,"RecordNotFound!"); return dbferrno; }else{ dbf_buff(); } dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); return dbferrno; } if((current_recno==DBFBOF)||(current_recno==Empty)){ // in the DBFEOF; dbferrno=RecordNotFound; sprintf(this->;dbferrmsg,"RecordNotFound!"); return dbferrno; } RetCode=pIDX-> if(RetCode<0){ current_recno=-1; dbferrno=RecordNotFound; sprintf(this->;dbferrmsg,"RecordNotFound!"); rev(); return RecordNotFound; } current_recno=pIDX->;GetRecordNo(); if(current_recno>;record_no||current_recno<1){ // Fatal Error :: the IDX file is old +++++++++++++++++ dbferrno=IndexIsOutOfDate; sprintf(this->;dbferrmsg,"INdexIsOutOfDate!"); return dbferrno; } if(current_recno==0){ current_recno=-3; }else{ dbf_buff(); } dbferrno=0; sprintf(this->;dbferrmsg,"DBFOK!"); return 0; } INT2 DBF::Next() { return Skip(); } INT2 DBF::Skip() { INT2 RetCode; if(pIDX==NULL){ // skip Not use IDX if(current_recno==DBFBOF){ // in the BOF current_recno=1; dbferrno=dbf_buff(); return dbferrno; } if(current_recno current_recno++; dbferrno=dbf_buff(); return dbferrno; } if(current_recno==record_no){ // in the LastRecord current_recno=DBFEOF; dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); return dbferrno; } if((current_recno==DBFEOF)||(current_recno==Empty)){ // in the DBFEOF; dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return dbferrno; } dbferrno=OtherError; sprintf(this->;dbferrmsg,"OtherError!"); return dbferrno; }else { if(current_recno==DBFBOF){ // in the BOF pIDX->;GoHome(); current_recno=pIDX->;GetRecordNo(); if(current_recno>;record_no||current_recno<1){ // Fatal Error :: the IDX file is old } dbferrno=dbf_buff(); return dbferrno; } if((current_recno==DBFEOF)||(current_recno==Empty)){ // in the DBFEOF; dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return RecordOutOfRange; } RetCode=pIDX->;Next(); if(RetCode<0){ current_recno=DBFEOF; dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return RecordOutOfRange; } current_recno=pIDX->;GetRecordNo(); if(current_recno==0L){ current_recno=DBFEOF; // set bof() } if(current_recno>;record_no||current_recno<1){ // Fatal Error :: the IDX file is old } if(current_recno==0L){ current_recno=DBFEOF; // set EOF() dbferrno=DBFEOF; }else { dbferrno=dbf_buff(); } return dbferrno; } } INT2 DBF::GoTo(INT4 recordno) { if((recordno<=record_no)&&(recordno>;0)){ current_recno=(UINT4)recordno; dbf_buff(); dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); }else { dbferrno=RecordOutOfRange; if(recordno<=0){ current_recno=DBFBOF; }else if(recordno>;record_no){ current_recno=DBFEOF; } sprintf(this->;dbferrmsg,"RecordOutOfRange!"); } return dbferrno; } INT2 DBF::IsBOF() { if(current_recno==Empty||current_recno==DBFBOF) return 1; else return 0; } INT2 DBF::IsEOF() { if(current_recno==Empty||current_recno==DBFEOF) return 1; else return 0; } INT2 DBF::GoTop() { if(pIDX==NULL){ if(record_no!=0){ current_recno=1; dbferrno=dbf_buff(); return dbferrno; }else{ dbferrno=DBFOK; return dbferrno; } } pIDX->;GoHome(); current_recno=pIDX->;GetRecordNo(); if(current_recno>;0){ dbferrno=dbf_buff(); }else{ current_recno=Empty; // bof() .and. eof() dbferrno=DBFOK; } return dbferrno; } INT2 DBF::GoBottom() { return 0; } // 0 : ok // -1: not found() INT2 DBF::Seek(CHAR * keyword) { INT2 RetCode; if(pIDX==NULL){ dbferrno=IndexNotInit; sprintf(this->;dbferrmsg,"IndexNotInit!"); return dbferrno; } RetCode=pIDX->;Find(keyword); if(RetCode!=0){ current_recno=DBFEOF; // set to eof dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return dbferrno; } current_recno=pIDX->;GetRecordNo(); if(current_recno>;record_no||current_recno<1){ // Fatal Error IDX is not match to DBF file } dbferrno=dbf_buff(); return dbferrno; } INT2 DBF::fv(CHAR * fieldname_par,CHAR * fieldvalue_par,INT2 BufferLen) { INT2 RetCode; if((RetCode=FindField(fieldname_par))<0){ fieldvalue_par[0]='x0'; dbferrno=FieldNotFound; sprintf(this->;dbferrmsg,"FieldNotFound!"); return dbferrno; } if(RetCode>;=fieldnum){ fieldvalue_par[0]='x0'; dbferrno=FieldNotFound; sprintf(this->;dbferrmsg,"FileNotFound!"); return dbferrno; } return fv(RetCode,fieldvalue_par,BufferLen); } // -1: is eof() bof() in dbase. INT2 DBF::fv(INT2 fieldno_par,CHAR * fieldvalue_par,INT2 BufferLen) { struct FIELD * tpf; if(handle==-1||Installed!=1){ fieldvalue_par[0]='x0'; dbferrno=FieldNotFound; sprintf(this->;dbferrmsg,"FileNotFound!"); return FieldNotFound; } tpf=&(pFIELD[fieldno_par]); if(fieldno_par>;=fieldnum){ fieldvalue_par[0]='x0'; dbferrno=FieldNotFound; sprintf(this->;dbferrmsg,"FileNotFound!"); return FieldNotFound; } if((current_recno>;record_no)||(current_recno<0)){ fieldvalue_par[0]='x0'; dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return dbferrno; } if(tpf->;len strncpy(fieldvalue_par,(CHAR *)(buff+tpf->;address), tpf->;len); fieldvalue_par[tpf->;len]='x0'; }else{ strncpy(fieldvalue_par,(CHAR *)(buff+tpf->;address), BufferLen-1); fieldvalue_par[BufferLen-1]='x0'; } /* switch(tpf->;f_type){ case 'C': dbferrno=1; return 1; case 'N': dbferrno=2; return 2; case 'L': dbferrno=3; return 3; case 'M': dbferrno=4; return 4; case 'D': dbferrno=5; return 5; } */ dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); return DBFOK; } INT2 DBF::dowith(INT2 fn,CHAR * tempb) { CHAR buffer[80]; struct FIELD * tpf; tpf=&(pFIELD[fn]); INT2 i; i=strlen(tempb); //switch(pFIELD[fn].f_type){ switch(tpf->;f_type){ case 'M': case 'C': case 'D': // for(;i for(;i tempb=' '; //tempb[pFIELD[fn].len]='x0'; tempb[tpf->;len]='x0'; break; case 'N': ::ccc(tempb,(INT2)tpf->;len,(INT2)tpf->;bits); break; case 'L': if(tempb[0]=='1'||tempb[0]=='t'||fieldvalue[0]=='T') buffer[0]='T'; else if(tempb[0]=='0'||tempb[0]=='f'||tempb[0]=='F') buffer[0]='F'; else buffer[0]=tempb[0]; tempb[0]=buffer[0]; tempb[1]='x0'; break; default: dbferrno=FieldTypeError; sprintf(this->;dbferrmsg,"FieldTypeError!"); return FieldTypeError; } dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); return DBFOK; } INT2 DBF::Loca(CHAR * fieldname,CHAR * fieldvalue_par) { CHAR tempbuff[100]; loca_flag=0; if(fieldvalue!=NULL) delete fieldvalue; fieldvalue=new CHAR[strlen(fieldvalue_par)+10]; if(fieldvalue==NULL) { #ifdef DEBUG debugm("GGROUP::Loca alloc failure!"); #endif // printf("Not enough memory!"); dbferrno=NotEnoughMemory; sprintf(this->;dbferrmsg,"NotEnoughMemory!"); return dbferrno; } strcpy(fieldvalue,fieldvalue_par); if((fieldno=FindField(fieldname))<0){ dbferrno=FieldNotFound; sprintf(this->;dbferrmsg,"FileNotFound!"); return dbferrno; } loca_flag=1; if(pIDX==NULL){ current_recno=1; dbferrno=dbf_buff(); }else{ pIDX->;GoHome(); current_recno=pIDX->;GetRecordNo(); dbferrno=dbf_buff(); } if(dbferrno!=DBFOK) return dbferrno; do { // check current record weather need. fv(fieldno,tempbuff); dowith(fieldno,tempbuff); if(strcmp(tempbuff,fieldvalue)==0){ dbferrno=DBFOK; return DBFOK;// found the just record } }while((Skip()==0)&&(!this->;IsEOF())); if(this->;IsEOF()){ dbferrno=NotFound; sprintf(this->;dbferrmsg,"NotFound!"); return dbferrno; }else{ dbferrno=DBFOK; return dbferrno; } } INT2 DBF::Cont() { CHAR tempbuff[100]; if(!loca_flag){ dbferrno=OtherError; sprintf(this->;dbferrmsg,"OtherError!"); return dbferrno; } if(this->;IsEOF()){ dbferrno=NotFound; sprintf(this->;dbferrmsg,"NotFound!"); return dbferrno; } while(Skip()==0){ if(this->;IsEOF()){ dbferrno=NotFound; sprintf(this->;dbferrmsg,"NotFound!"); return dbferrno; } fv(fieldno,tempbuff); dowith(fieldno,tempbuff); if(strcmp(tempbuff,fieldvalue)==0){ dbferrno=0; return 0;// found the just record } } dbferrno=NotFound; sprintf(this->;dbferrmsg,"NotFound!"); return dbferrno; } INT2 DBF::IsDeleted() { if(current_recno<=0){ dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOf!"); return dbferrno; } dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); if(*buff==' ') return 0; else return 1; } INT2 DBF:{ if(current_recno<=0){ dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return dbferrno; } dbferrno=DBFOK; sprintf(this->;dbferrmsg,"DBFOK!"); *buff='*'; return dbferrno; } INT2 DBF::UnDelete() { if(current_recno<=0){ dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return dbferrno; } *buff=' '; dbferrno=DBFOK; return dbferrno; } INT2 DBF::OpenIDX(CHAR * idxfilename) { INT2 RetCode; if(pIDX==NULL) pIDX=new IDX(); if(pIDX==NULL){ #ifdef DEBUG debugm("DBF::OpenIDX alloc failure!"); #endif dbferrno=IndexNotInit; sprintf(this->;dbferrmsg,"IndexNotInit!"); return dbferrno; elete() } RetCode=pIDX->;open(idxfilename); if(RetCode!=0){ delete pIDX; pIDX=NULL; } current_recno=pIDX->;GetRecordNo(); dbf_buff(); dbferrno=0; return 0; } INT2 DBF::CloseIDX() { if(pIDX!=NULL){ delete pIDX; pIDX=NULL; } dbferrno=0; return 0; } INT2 DBF::Replace(INT2 fieldno_par,CHAR * fieldvalue_par) { CHAR tempbuff[200]; CHAR * tempp; struct FIELD * tpf; tempp=tempbuff; if(fieldno_par<0||fieldno_par>;=fieldnum){ dbferrno=FieldNotFound; sprintf(this->;dbferrmsg,"FieldNotFound!"); return dbferrno; } strncpy(tempbuff,fieldvalue_par,199); tempbuff[199]='x0'; dowith(fieldno_par,tempp); tpf=&(pFIELD[fieldno_par]); //memcpy(buff+pFIELD[fieldno_par].address,tempp,pFIELD[fieldno_par].len); memcpy(buff+tpf->;address,tempp,tpf->;len); changeflag=1; dbferrno=0; return 0; } INT2 DBF::Replace(CHAR * fieldname,CHAR * fieldvalue_par) { INT2 RetCode; if((RetCode=FindField(fieldname))<0){ dbferrno=FieldNotFound; sprintf(this->;dbferrmsg,"FieldNotFound!"); return dbferrno; } if(RetCode>;=fieldnum){ dbferrno=FieldNotFound; sprintf(this->;dbferrmsg,"FieldNotFound!"); return dbferrno; } return Replace(RetCode,fieldvalue_par); } // reread the record no from dbf file // return : 0: OK. // -1: FAILURE. INT2 DBF::ReOpen() { CHAR tempbuf[100]; if(!Installed){ dbferrno=ClassNotInit; sprintf(this->;dbferrmsg,"ClassNotInit!"); return dbferrno; } if(handle==-1){ dbferrno=FileNotOpen; sprintf(this->;dbferrmsg,"FileNotOpen!"); return dbferrno; } _lseek(handle,0l,SEEK_SET); if(read(handle,tempbuf,32)!=32){ this->;Close(); this->;dbferrno=NotDBFFile; sprintf(this->;dbferrmsg,"NotDBFFile!"); return dbferrno; } record_no=*(UINT4 *)(tempbuf+4); dbferrno=DBFOK; return DBFOK; } // flush current record to dbf file INT2 DBF::Flush() { return dbf_wbuff(); } // Retry read current record from dbf file INT2 DBF::ReRead() { if(current_recno<=record_no||current_recno>;=1){ return dbf_buff(); } dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return dbferrno; } INT2 DBF::Flock() { INT2 RetCode; if(lock_flag==FileLock){ // already file lock dbferrno = DBFOK; return dbferrno; } if(lock_flag==RecordLock) this->;Unlock(); // record lock lock_flag=0; if(DBFType==Foxbase){ lseek(handle,0x40000000L,SEEK_SET); RetCode=locking(handle,LK_NBLCK,0x3FFFFFFFL); // RetCode=_locking(handle,0x40000000L,0x3FFFFFFFL); }else{ lseek(handle,0x40000000L,SEEK_SET); RetCode=locking(handle,LK_NBLCK,0x3FFFFFFFL); // RetCode=_lock(handle,0x40000000L,0x3FFFFFFFL); } if(RetCode==0){ if(DBFType==Foxbase){ lock_start=0x40000000L; lock_len=0x3FFFFFFFL; }else{ lock_start=0x40000000L; lock_len=0x3FFFFFFFL; } lock_flag=FileLock; dbferrno=DBFOK; }else{ dbferrno=FlockFailure; sprintf(this->;dbferrmsg,"FlockFailure!"); } return dbferrno; } INT2 DBF::Rlock() { INT2 RetCode; INT4 tlockpos; this->;Unlock(); if(current_recno<0){ dbferrno=RecordOutOfRange; sprintf(this->;dbferrmsg,"RecordOutOfRange!"); return dbferrno; } if(DBFType==Foxbase){ tlockpos=0x40000000l+head_len+(current_recno-1)*record_len; lseek(handle,tlockpos,SEEK_SET); RetCode=locking(handle,LK_NBLCK,record_len); }else{ tlockpos=0x40000000l+head_len+(current_recno-1)*record_len; lseek(handle,tlockpos,SEEK_SET); RetCode=locking(handle,LK_NBLCK,record_len); } if(RetCode==0){ if(DBFType==Foxbase){ lock_start=tlockpos; // 0x40000000l+head_len+(current_recno-1)*record_len; lock_len=record_len; }else{ lock_start=tlockpos; // 0x40000000l+head_len+(current_recno-1)*record_len; lock_len=record_len; } lock_flag=RecordLock; dbferrno=DBFOK; }else{ dbferrno=RlockFailure; sprintf(this->;dbferrmsg,"RlockFailure!"); } return dbferrno; } INT2 DBF::Unlock() { if(lock_flag){ lock_flag=0; lseek(handle,lock_start,SEEK_SET); locking(handle,LK_UNLCK,lock_len); // ::unlock(handle,lock_start,lock_len); } dbferrno=0; return 0; } INT2 DBF::FindField(CHAR * fieldname) { INT2 i,j; CHAR tempbuffer[20]; strncpy(tempbuffer,fieldname,10); tempbuffer[10]='x0'; j=strlen(tempbuffer); for(i=0;i for(i=0;i { if(strcmp(,tempbuffer)==0) { dbferrno=0; return i; } } dbferrno=FieldNotFound; sprintf(this->;dbferrmsg,"FieldNotFOund!"); return dbferrno; } CHAR * DBF::GetFieldName(INT2 fn) { INT2 fnaddr; // 本 fn 的字段在数据库中的位置 static CHAR tmpbf[11]; // read field name from dbf. fnaddr=(fn+1)*32; _lseek(handle,fnaddr,SEEK_SET); if( read(handle,tmpbf,10) == -1 ) return ""; tmpbf[10]=0; return tmpbf; } INT2 DBF::GetFieldLen(INT2 fn) { if (fn >; fieldnum){ sprintf(this->;dbferrmsg,"FieldNotFound!"); return FieldNotFound; } return pFIELD[fn].len; } INT2 DBF::GetFieldNum() { return fieldnum; } // - DBF_HEAD:{ int i; id=0x3; year=96; month=10; day=1; recorder_num=0; head_len=0x21; record_len=0x0; reserved[20]; for(i=0;i<20;i++) reserved=0; } DBF_FIELD:{ int i; for(i=0;i<14;i++){ reserved_data=0;}; }; CDBF::CDBF() { int i; FieldNum=0; for(i=0;i pFIELD=NULL; } c_pos=0l; BF_FIELD() BF_HEAD() } INT2 CDBF::reset() { int i; for(i=0;i if(pFIELD!=NULL){ delete pFIELD; pFIELD=NULL; } } c_pos=0l; FieldNum=0; return 0; } CDBF::~CDBF() { this->;reset(); } INT2 CDBF::add(char * FieldName,char FieldType,unsigned char len,unsigned char bits) { int str_len; int i; // Check Parameter FieldType='CND' if((FieldType!='C')&&(FieldType!='N')&&(FieldType!='D')){ return -1; } pFIELD[FieldNum]=new DBF_FIELD; // - if(pFIELD[FieldNum]==NULL){ #ifdef DEBUG debugm("CDBF::add alloc failure!"); #endif return -2; } FieldNum++; // str_len=strlen(FieldName); if(str_len>;10) str_len=10; for(i=0;i for(i=str_len;i<11;i++) pFIELD[FieldNum-1]->;name='x0'; pFIELD[FieldNum-1]->;f_type=FieldType; if(FieldType=='D') pFIELD[FieldNum-1]->;len=8; else pFIELD[FieldNum-1]->;len=len; if(FieldType=='N') pFIELD[FieldNum-1]->;bits=bits; else pFIELD[FieldNum-1]->;bits=0; // ---------------------- pFIELD[FieldNum-1]->;address=c_pos+1; c_pos+=len; // ---------------------- return 0; } INT2 CDBF::create(char * FileName) { // struct date cdate; int i,rec_len; char tail[3]="x0d"; FILE * fp; CTime tttt = CTime::GetCurrentTime(); // sprintf(RqStr,"%02d%02d%02d",r()%100, // th(),()); // getdate(&cdate); // ---------------------------------------------- =r()%100; =th(); =(); // ---------------------------------------------- _len=32+32*FieldNum+1; // dbf for(i=0,rec_len=0;i rec_len+=pFIELD->;len; } _len=rec_len+1; // --------------------------------- if((fp=fopen(FileName,"wb+"))==NULL){ return -1; } if(fwrite(&(this->;head),sizeof(DBF_HEAD),1,fp)!=1){ fclose(fp); return -2; } for(i=0;i if(fwrite(pFIELD,sizeof(DBF_FIELD),1,fp)!=1){ fclose(fp); return -3; }; //Err(); } fwrite(tail,1,1,fp); fclose(fp); return 0; } // INT2 DBF::FieldValue(INT2 Fieldid,INT2& FieldValue_par) { CHAR TempBuf[310]; FieldValue(Fieldid,(CHAR *)TempBuf,300); if(dbferrno!=DBFOK){ return dbferrno; } FieldValue_par=atoi(TempBuf); return dbferrno; } INT2 DBF::Replace(INT2 Fieldid,INT2 FieldValue) { CHAR TempBuf[310]; sprintf(TempBuf,"%d",FieldValue); return Replace(Fieldid,TempBuf); } INT2 DBF::FieldValue(INT2 Fieldid,UINT2& FieldValue) { CHAR TempBuf[310]; this->;FieldValue(Fieldid,TempBuf,300); if(dbferrno!=DBFOK){ return dbferrno; } FieldValue=(UINT2)atoi(TempBuf); return dbferrno; } INT2 DBF::Replace(INT2 Fieldid,UINT2 FieldValue) { CHAR TempBuf[310]; sprintf(TempBuf,"%u",FieldValue); return Replace(Fieldid,TempBuf); } INT2 DBF::FieldValue(INT2 Fieldid,INT4& FieldValue_par) { CHAR TempBuf[310]; FieldValue(Fieldid,TempBuf,300); if(dbferrno!=DBFOK){ return dbferrno; } FieldValue_par=atol(TempBuf); return dbferrno; } INT2 DBF::Replace(INT2 Fieldid,INT4 FieldValue_par) { CHAR TempBuf[310]; sprintf(TempBuf,"%ld",FieldValue_par); return Replace(Fieldid,TempBuf); } INT2 DBF::FieldValue(INT2 Fieldid,UINT4& FieldValue_par) { CHAR TempBuf[310]; FieldValue(Fieldid,TempBuf,300); if(dbferrno!=DBFOK){ return dbferrno; } FieldValue_par=(UINT4)atol(TempBuf); return dbferrno; } INT2 DBF::Replace(INT2 Fieldid,UINT4 FieldValue_par) { CHAR TempBuf[310]; sprintf(TempBuf,"%lu",FieldValue_par); return Replace(Fieldid,TempBuf); } INT2 DBF::FieldValue(INT2 Fieldid,DOUBLE& FieldValue_par) { CHAR TempBuf[310]; FieldValue(Fieldid,TempBuf,300); if(dbferrno!=DBFOK){ return dbferrno; } FieldValue_par=(DOUBLE)atof(TempBuf); return dbferrno; } INT2 DBF::Replace(INT2 Fieldid,DOUBLE FieldValue_par) { CHAR TempBuf[310]; sprintf(TempBuf,"%50.25",FieldValue_par); return Replace(Fieldid,TempBuf); } INT2 DBF::FieldValue(INT2 Fieldid,CHAR& FieldValue_par) { CHAR TempBuf[310]; FieldValue(Fieldid,TempBuf,300); if(dbferrno!=DBFOK){ return dbferrno; } FieldValue_par=TempBuf[0]; return dbferrno; } INT2 DBF::Replace(INT2 Fieldid,CHAR FieldValue_par) { CHAR TempBuf[310]; TempBuf[0]=FieldValue_par; TempBuf[1]='x0'; return Replace(Fieldid,TempBuf); } INT2 DBF::FieldValue(CHAR* FieldName,INT2& FieldValue_par) { return FieldValue(FindField(FieldName),FieldValue_par); } INT2 DBF::Replace(CHAR* FieldName,INT2 FieldValue_par) { return Replace(FindField(FieldName),FieldValue_par); } INT2 DBF::FieldValue(CHAR* FieldName,UINT2& FieldValue_par) { return FieldValue(FindField(FieldName),FieldValue_par); } INT2 DBF::Replace(CHAR* FieldName,UINT2 FieldValue_par) { return this->;Replace(FindField(FieldName),FieldValue_par); } INT2 DBF::FieldValue(CHAR* FieldName,INT4& FieldValue_par) { return FieldValue(FindField(FieldName),FieldValue_par); } INT2 DBF::Replace(CHAR* FieldName,INT4 FieldValue_par) { return Replace(FindField(FieldName),FieldValue_par); } INT2 DBF::FieldValue(CHAR* FieldName,UINT4& FieldValue_par) { return FieldValue(FindField(FieldName),FieldValue_par); } INT2 DBF::Replace(CHAR* FieldName,UINT4 FieldValue_par) { return Replace(FindField(FieldName),FieldValue_par); } INT2 DBF::FieldValue(CHAR* FieldName,DOUBLE& FieldValue_par) { return FieldValue(FindField(FieldName),FieldValue_par); } INT2 DBF::Replace(CHAR* FieldName,DOUBLE FieldValue_par) { return Replace(FindField(FieldName),FieldValue_par); } INT2 DBF::FieldValue(CHAR* FieldName,CHAR& FieldValue_par) { return FieldValue(FindField(FieldName),FieldValue_par); } INT2 DBF::Replace(CHAR* FieldName,CHAR FieldValue_par) { return Replace(FindField(FieldName),FieldValue_par); } INT2 DBF::FieldValue(CHAR * FieldName,CHAR * ValueBuffer,INT2 ValueBufferLen) { return fv(FieldName,ValueBuffer,ValueBufferLen); } INT2 DBF::FieldValue(INT2 FieldIndex,CHAR * ValueBuffer,INT2 ValueBufferLen) { return fv(FieldIndex,ValueBuffer,ValueBufferLen); } 您对本贴的看法:鲜花[0] 臭蛋[0] YOCSEF“低排放绿色计算"报名中| 【尚观研发课程8.8折,50000年薪起】 | IBM嘉年华颁奖倒计时 | 嵌入式有奖书评,写书评,得大奖 ae66 精灵 6楼 发表于 2004-1-11 00:32 [推广获积分] 求:dbf文件C/C++的操作库程序。 头文件: CU编号: 102174 注册:2003-9-29 最后登录: 2007-03-07 帖子:152 精华:0 可用积分:161 (白手起家) 信誉积分:100 /************************************************************************ DBFOP for C++ V1.00 ,1995.1.10 Develop by John,Liao This Module include the C++ headfile , and C++ resource file . This module is develop for use DBF(DBASEIII,DBASEII,MFOXBASE) and IDX(MFOXBASE).but use IDX only allow read or change the field that isn't key word. Support netware share .rlock,rlock,unlock_. 专家积分:0 (本版:0) 空间积分:0 推广积分:0 状态:...离线... [个人空间] [短信] [博客] This module is reference to the module "wr_dbf.c,dbase.h" which develop by Owen,chen in NEWELL. 1996.12 attemp add function : del(),undel(),zap(),pack() 1996.12.24 add function zap() 1999.03.19 big change has been made as follow: A. Suport open dbf file in read only model B. Use type macro INT2,UINT2,INT4,UINT4,UCHAR,CHAR C. Megirate class CRT_DBF In this model D. Add those function, make program easier for FieldValue(INT2,INT2& FieldValue(INT2,UINT2& FieldValue(INT2,INT4& FieldValue(INT2,UINT4& FieldValue(INT2,DOUBLE&; Replace(INT2,INT2&; ; ; Replace(UINT2,UINT2&; Replace(INT,INT4&; ; Replace(INT2,UINT4&; ; ; Replace(INT2,DOUTLE4& FieldValue(INT2,CHAR&); Replace(INT2,CHAR&); FieldValue(CHAR*,INT2&); Replace(CHAR*,INT2&); FieldValue(CHAR*,UINT2&); Replace(CHAR*,UINT2&); FieldValue(CHAR*,INT4&); Replace(CHAR*,INT4&); FieldValue(CHAR*,UINT4&); Replace(CHAR*,UINT4&); FieldValue(CHAR*,DOUBLE&); Replace(CHAR*,DOUBLE&); FieldValue(CHAR*,CHAR&); Replace(CHAR*,CHAR&); E: add the length control in function FieldFind; F: change open idx file from mode read and write to readonly *************************************************************************/ #ifndef ___DBFOP_HPP___ #define ___DBFOP_HPP___ #include // define type value for the class add by liaoj 1999.03.19 //#ifndef __EXPAND_TYPE__ //#define __EXPAND_TYPE__ #define VC #ifdef VC #define INT2 short #define UINT2 unsigned short #define INT4 int #define UINT4 unsigned int #define UCHAR unsigned char #define CHAR char #define DOUBLE double #else #define INT2 int #define UINT2 unsigned int #define INT4 long #define UINT4 unsigned long #define UCHAR unsigned char #define CHAR char #define DOUBLE double #define BOOL int #define TRUE 1 #define FALSE 0 #endif //#endif // DOUBLE indecate 64 bit float // -------------- /************************************************************************* This struct is used by class IDX. Normally,a IDX block's length is 200H(512D) bytes. **************************************************************************/ struct IDX_BLOCK { INT2 keylen; // KEY WORD length,(BYTES) CHAR flag; // This block's type. // 0 - frame ,1 - root, 2 - leaf , 3 - both UCHAR count; // avalid node in this IDX block // ... count for the node UCHAR items; UINT4 prev; // position of the IDX block which prev this block. // if 0xFFFFFFFF means this block is the first block // of this idx file. UINT4 next; // position of the IDX block which next this block. // if 0xFFFFFFFF means this block is the last block CHAR buff[512]; // block size is 512 bytes INT2 curp; // current position of last move INT2 skip(); // like next(); public: INT2 GetFlag() { return (INT2) flag; }; INT2 SetKeyLen(INT2 keylen_par){keylen=keylen_par; return 0;}; UINT4 GetPrev() { return prev;}; UINT4 GetNext() { return next;}; INT2 Prev(){ if(curp==0) return -2; else curp--; return 0; } INT2 Next(){ if(curp>;=items-1) return -3; else curp++; return 0; } INT2 find(CHAR * key);// 0:Found // -1 :Not Found // -2 :Maybe in PrevBlock // -3 :Maybe in NextBlock // -10:This is ROOT ,Maybe in GetResult() UINT4 GetResult(); INT2 ReadBlock(INT2,UINT4 pos); INT2 Home() { curp=0; return 0; }; INT2 End() { if(items>;0) curp=items-1; else curp=0; return 0; } }; /************************************************************************* This class is call by class DBF inter. **************************************************************************/ class IDX { INT2 Installed; INT2 handle; // FILE * fp; UINT4 rootpos; UINT4 blocks; INT2 key_len; IDX_BLOCK block; public: IDX(); ~IDX(); INT2 open(CHAR *); // 0: OK -1:Not Found operator void *() { return (void *)Installed; }; INT2 operator !() { return !Installed; }; INT2 Find(CHAR *); // 0: OK -1:Not Found UINT4 GetRecordNo() { return ult(); }; INT2 Prev(); // 0: OK -1:HomePosCame INT2 Next(); // 0: OK -2:EndPosCame INT2 GoHome(); // 0: OK -1:The IDX is empty INT2 GoEnd(); // 0: OK -1:The IDX is empty INT2 Skip(); // 0: OK -1:HomePosCame -2:EndPosCame }; struct FIELD { CHAR name[11]; CHAR f_type; INT4 address; UCHAR len; UCHAR bits; public: // ~FIELD(); }; /**************************************************************** This is interface class. User use this module by use class DBF. this class is like <;>; in MFOXPLUS,FOX,DBASE III. use can use this class do follow work. . open a database file and it's index file.(only allow .IDX); . close a database file and it's index file if nessary. . read a field value in this database. . change a field value in this database.(if have .IDX,not change the key field). . seek a record by use IDX file. . append blank record (Must use IDX); . lock a record or a file,unlock it.(not allow multlock, if try it,class will unlock the area which locked before.) ******************************************************************/ class DBF { public: enum DBF_CONST{ FieldNotFound=-6, RecordNotFound=-5, Empty =-3, DBFEOF =-2, DBFBOF =-1, DBFOK =0x0000, AutoDetect =0x4001, Clipper , Foxbase , // ReadOnly =0x4100, ReadWrite , FileLock =0x4200, RecordLock, FlockFailure=0x5001, RlockFailure, ClassNotInit, FileOpenFailure, ReadFileError, FileNotOpen, SeekFileError, WriteFileError, ChsizeFileError, OtherError, RecordOutOfRange, NotFound, IndexNotInit, FieldTypeError, // index error IndexIsOutOfDate=0x6000, // fatal error NotEnoughMemory=0x7000, NotDBFFile, OtherFatalError, }; protected: INT2 Installed; INT2 OpenMode; // save current dbf open mode // valid value: // DBF::ReadOnly,ReadWrite CHAR * buff; // changeflag is used for buff change; // it set by replace() function; // it clear by dbf_buff; // it used by dbf_wbuff,if no change don't write to file INT2 changeflag; FIELD * pFIELD; INT4 current_recno; // -1 bof -2 eof -3 struct FIELD * First; CHAR Name[100]; // FILE * fp; INT2 handle; class IDX * pIDX; INT4 record_no; UINT2 head_len; UINT2 record_len; INT2 dbf_buff(); INT2 dbf_wbuff(); INT2 fieldnum; // ---------------------------------- CHAR * SwapBuffer; INT2 MaxRecNum; INT2 CurRecNum; // ------------------------------------------------------------ // next three var is use for flock(),rlock(),unlock() function // these used for next condition: // when a lock function is going to invoke, // the part locked in before must unlock first. // this work will be done by class automatic // ------------------------------------------------------------ INT2 lock_flag; // 0. No lock le corder INT4 lock_start; // when lock_flag=0, INT4 lock_len; // ------------------------------------------------------------ // these var define next is used for // loca(),cont() like the locate,d in MFOXPLUS // ------------------------------------------------------------ INT2 loca_flag; // 0. not call loca y call loca INT2 fieldno; // last loca fieldno CHAR * fieldvalue; INT2 dowith(INT2 fn,CHAR *tempb); INT2 unlock_temp(); INT2 DBFType; //0:fox serial, 1:clipper public: INT2 dbferrno; CHAR dbferrmsg[100]; // ---------------------------------------- INT2 GetFieldNum(); CHAR * GetFieldName(INT2 fn); INT2 GetFieldLen(INT2 fn); INT2 SetSwp(INT2 buffer_number); INT2 AppendToSwp(); INT2 FlushSwp(); // ---------------------------------------- INT2 GetErrno() { return dbferrno;}; INT2 FindField(CHAR * filedname); // -1: not find >;=0:return fieldno INT2 ff(CHAR * fieldname) {return FindField(fieldname);}; INT2 Clear(); INT2 Append(); INT2 AppendBlank(); // -1 DBF(); ~DBF(); operator void *() { return (void *)Installed;}; INT2 operator !() { return Installed;}; INT2 Open(CHAR * filename,INT2 ReadWriteMode=ReadWrite,INT2 DBFType_Par=Foxbase); INT2 GetErrNo() { return dbferrno ; }; INT4 GetRecNum() { return record_no; }; INT4 GetRecNo() { return current_recno ;}; INT2 Close(int Delete=0); // in function fv,and FieldValue // ValueBuffer=0 indecate infinite len of ValueBuffer), INT2 fv(CHAR * ,CHAR *,INT2 ValueBufferLen=0); INT2 FieldValue(CHAR * FieldName,CHAR * ValueBuffer,INT2 ValueBufferLen=0); INT2 fv(INT2,CHAR *,INT2 ValueBufferLen=0); // INT2 FieldValue(INT2 FieldIndex,CHAR * ValueBuffer,INT2 ValueBufferLen=0); //-------------------------------------------- INT2 Next(); INT2 Prev(); INT2 Skip(); INT2 GoTop(); INT2 GoBottom(); INT2 Zap(); INT2 IsDeleted(); INT2 Delete(); INT2 UnDelete(); //-------------------------------------------- INT2 GoTo(INT4 recordno); // don't use when idx is avalid INT2 IsBOF(); INT2 IsEOF(); INT2 Seek(CHAR *); // loca and cont : return DBFOK found other not found INT2 Loca(CHAR * fieldname,CHAR * fieldvalue); INT2 Cont(); INT2 OpenIDX(CHAR *); INT2 CloseIDX(); INT2 Replace(CHAR * fieldname,CHAR * fieldvalue); INT2 Replace(INT2 fieldno,CHAR * fieldvalue); INT2 ReOpen(); // only get the record_no read from file INT2 Flush(); // write current buff to file INT2 ReRead(); // read the newest of current record to buff // ------------------------------------------------------------------ INT2 Flock(); // 0: OK. 1:not locked. INT2 Rlock(); // 0: OK. 1:not locked. -1:. INT2 Unlock(); // add fuctions as follow make program easier INT2 FieldValue(INT2,INT2&); INT2 Replace(INT2,INT2); INT2 FieldValue(INT2,UINT2&); INT2 Replace(INT2,UINT2); INT2 FieldValue(INT2,INT4&); INT2 Replace(INT2,INT4); INT2 FieldValue(INT2,UINT4&); INT2 Replace(INT2,UINT4); INT2 FieldValue(INT2,DOUBLE&); INT2 Replace(INT2,DOUBLE); INT2 FieldValue(INT2,CHAR&); INT2 Replace(INT2,CHAR); INT2 FieldValue(CHAR*,INT2&); INT2 Replace(CHAR*,INT2); INT2 FieldValue(CHAR*,UINT2&); INT2 Replace(CHAR*,UINT2); INT2 FieldValue(CHAR*,INT4&); INT2 Replace(CHAR*,INT4); INT2 FieldValue(CHAR*,UINT4&); INT2 Replace(CHAR*,UINT4); INT2 FieldValue(CHAR*,DOUBLE&); INT2 Replace(CHAR*,DOUBLE); INT2 FieldValue(CHAR*,CHAR&); INT2 Replace(CHAR*,CHAR); }; // --- #define MAXFIELDNUM 60 struct DBF_HEAD { unsigned char id; unsigned char year; unsigned char month; unsigned char day; unsigned long recorder_num; unsigned int head_len; unsigned int record_len; unsigned char reserved[20]; DBF_HEAD(); }; struct DBF_FIELD { char name[11]; char f_type; long address; unsigned char len; unsigned char bits; unsigned char reserved_data[14]; DBF_FIELD(); }; class CDBF{ DBF_HEAD head; DBF_FIELD * pFIELD[MAXFIELDNUM]; int FieldNum; long c_pos; public: CDBF(); ~CDBF(); INT2 add(char* FieldName,char FieldType,unsigned char len,unsigned char bits); INT2 create(char * FileName); INT2 reset(); }; #endif


发布评论