/**
Copyright 2000 - 2003 LogicMatrix. All rights reserved.
This software is distributed under the LogicMatrix Free Software License. This software may be used for any purpose, personal or commercial. Redistributions in binary /source code form are permitted. Commercial redistribution of larger works derived from, or works which bundle this software requires a "Commercial Redistribution License" which can be purchased from LogicMatrix. Contact LogicMatrix for details
Redistributions qualify as Free and non-commercial under one of the following terms:
1) Redistributions are made at no charge beyond the reasonable cost of materials and delivery.
2) Redistributions in binary/source code form must reproduce this Copyright Notice,these license terms, and the disclaimer/limitation of liability set forth as below, in the documentation and/or other materials
provided with the distribution.
Disclaimer
==========
The Software is provided on an "AS IS" basis. No warranty is
provided that the Software is free of defects, or fit for a
particular purpose.
Limitation of Liability
=======================
LogicMatrix shall not be liable for any damages suffered by the Licensee or any third party resulting from use of the Software.
**/
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
// datastore.h
// defines a template class to handle record files
// Author: Vijay Mathew Pandyalakal
// Date: 12/23/2001 11:08:12 AM
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#ifndef DATASTORE_H
#define DATASTORE_H
#include <cstdio>
#include <string>
using namespace std;
template <class T>
class DataStore {
private:
string FileName;
string DBName;
FILE* fp;
bool IsOpen;
public:
//~~~~~ function default constructor ~~~~~~~~~~~~~~~~~~
// initializes FileName to ""
// arguments: null
// null
// returns null
DataStore() {
IsOpen = false;
FileName = "";
DBName = "";
}
//~~~~~~ end of function default constructor~~~~~~~~~~~~~~~~~
//~~~~~ function overloaded constructor ~~~~~~~~~~~~~~~~~~
// initializes filename
// arguments: const char*
// copied to file name
// returns null
DataStore(const char* fnm,const char* db) {
IsOpen = false;
DBName = db;
FileName = DBName + "\\" + fnm;
}
//~~~~~~ end of function oveloaded constructor~~~~~~~~~~~~~~~~~
//~~~~~ function SetFileName ~~~~~~~~~~~~~~~~~~
// sets a new file name
// arguments: const char*
// arg is copied to FileName
// returns void
void SetFileName(const char* fnm,const char* db) {
DBName = db;
FileName = DBName + "\\" + fnm;
}
//~~~~~~ end of function SetFileName~~~~~~~~~~~~~~~~~
//~~~~~ function Open ~~~~~~~~~~~~~~~~~~
// opens a file in read/write binary mode
// arguments: null
// null
// returns true if file open succeeds
bool Open(bool overwrite) {
if(IsOpen == false) {
fp = fopen(FileName.c_str(),"rb+");
if(!overwrite) {
if(fp != NULL) {
fclose(fp);
return false;
}
}
if(fp == NULL) {
fp = fopen(FileName.c_str(),"wb+");
}
if(fp == NULL) {
IsOpen = false;
return false;
}
IsOpen = true;
return true;
}else {
return true;
}
}
//~~~~~~ end of function Open~~~~~~~~~~~~~~~~~
//~~~~~ function AddRecord ~~~~~~~~~~~~~~~~~~
// appends a record to the file
// arguments: T
// arg is the variable of an unspecified class
// returns true on success
bool AddRecord(T t) {
fseek(fp,0,SEEK_END);
if(fwrite((char*)&t,sizeof(T),1,fp)) {
return true;
}else {
return false;
}
}
//~~~~~~ end of function AddRecord~~~~~~~~~~~~~~~~~
//~~~~~ function FindRecord ~~~~~~~~~~~~~~~~~~
// searches for a record in the file
// arguments: unsigned long
// arg is the index position of the record in file
// returns record if found
T FindRecord(unsigned long index) {
rewind(fp);
unsigned long pos = index * sizeof(T);
fseek(fp,pos,SEEK_CUR);
T t;
fread((char*)&t,sizeof(T),1,fp);
return t;
}
//~~~~~~ end of function FindRecord~~~~~~~~~~~~~~~~~
//~~~~~ function ModifyRecord ~~~~~~~~~~~~~~~~~~
// modifies a record in file
// arguments: T,unsigned long
// write the first arg to position specified by 2nd arg
// returns true on success
bool ModifyRecord(T newT,unsigned long index) {
rewind(fp);
unsigned long pos = index * sizeof(T);
fseek(fp,pos,SEEK_CUR);
if(fwrite((char*)&newT,sizeof(T),1,fp)) {
return true;
}else {
return false;
}
}
//~~~~~~ end of function ModifyRecord~~~~~~~~~~~~~~~~~
//~~~~~ function DeleteRecord ~~~~~~~~~~~~~~~~~~
// deletes a record form file
// arguments: unsigned long
// arg specifies the index of record to delete
// returns true on success
bool DeleteRecord(unsigned long index) {
rewind(fp);
FILE* tmp;
char tmp_fnm[36];
strcpy(tmp_fnm,"tmp.pln");
//strcat(tmp_fnm,FileName);
tmp = fopen(tmp_fnm,"wb");
if(tmp == NULL) {
return false;
}
unsigned long idx = 0;
T t;
while((fread((char*)&t,sizeof(T),1,fp)) == 1) {
if(idx != index) {
fwrite((char*)&t,sizeof(T),1,tmp);
}//else {
// printf("Index: %d\n",index);
//}
idx++;
}
fclose(fp);
fclose(tmp);
tmp = fopen(tmp_fnm,"rb");
fp = fopen(FileName.c_str(),"wb+");
if(fp != NULL) {
rewind(fp);
rewind(tmp);
while((fread((char*)&t,sizeof(T),1,tmp)) == 1) {
fwrite((char*)&t,sizeof(T),1,fp);
}
fclose(tmp);
fclose(fp);
fopen(FileName.c_str(),"rb+");
unlink(tmp_fnm);
return true;
}else {
return false;
}
}
//~~~~~~ end of function DeleteRecord~~~~~~~~~~~~~~~~~
//~~~~~ function GetRecordCount ~~~~~~~~~~~~~~~~~~
// counts number of record in file
// arguments: null
// 0
// returns record count
unsigned long GetRecordCount() {
fseek(fp,0,SEEK_END);
unsigned long len = ftell(fp);
unsigned long recs = len / sizeof(T);
return recs;
}
//~~~~~~ end of function GetRecordCount~~~~~~~~~~~~~~~~~
//~~~~~ function Close ~~~~~~~~~~~~~~~~~~
// closes the file
// arguments: 0
// 0
// returns void
void Close() {
if(IsOpen == true) {
fclose(fp);
IsOpen = false;
}
}
//~~~~~~ end of function Close~~~~~~~~~~~~~~~~~
//~~~~~ function GetNextRecordNo ~~~~~~~~~~~~~~~~~~
// finds the maximum id + 1 to uniquely identify a record
// arguments: 0
// 0
// returns next id
unsigned long GetNextRecordNo() {
rewind(fp);
unsigned long ret = 0;
T t;
while((fread((char*)&t,sizeof(T),1,fp)) == 1) {
if(t.id > ret) {
ret = t.id;
}
}
ret += 1;
return ret;
}
//~~~~~~ end of function GetNextRecordNo~~~~~~~~~~~~~~~~~
~DataStore() {
if(IsOpen == true) {
Close();
}
}
};
#endif
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
// end of datastore.h
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~