⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 xkdict.cpp

📁 简单数据库管理系统
💻 CPP
字号:
// xkDict.cpp: implementation of the xkDict class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "xkDBMS.h"
#include "xkDict.h"
#include "xkMemCoordinator.h"
#include "string.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
const char* sysdir_ ="c:\\xkDBMS";
extern xkMemCoordinator *pMem_;

size_t CalcTupleSize(xkAttribute *t_, size_t ac_)
{
	if(!t_)
		return 0;
	size_t num_ = 0;
	for(size_t i = 0; i < ac_; i++)
	{
		switch(t_[i].GetType()) 
		{
			case t_int:
				num_ += sizeof(int);	
				break;
			case t_float:
				num_ += sizeof(float);
				break;
			case t_string:
				num_ += sizeof(char)*256;
				break;
			case t_char:
				num_ += sizeof(char);
				break;
			default:
				break;
		}
	}
	return num_;
}

bool xkDict::CreateRelation(xkAttribute *pa_, size_t ac_, char* tname_)
{
	if(!pa_ || ac_ <= 0 || !tname_)
		return 0;
	//判断表名的唯一性
	xkRelation** iterator_;
	for(iterator_ = relations_.begin(); iterator_ != relations_.end(); iterator_++)
	{
		if(strlen(tname_) == strlen((*iterator_)->GetRelationName()) &&
			strcmp(tname_, (*iterator_)->GetRelationName()) == 0)
		{
			AfxMessageBox("已经存在该表名!");
			return false;
		}
	}

	xkTuple *pt_ = new xkTuple(pa_, ac_, CalcTupleSize(pa_, ac_), GetAllocRID());
	assert(pt_ != 0);
	xkRelation *pr_ =new xkRelation(pt_->GetRelationID(), pt_, tname_);
	assert(pr_ != 0);
	relations_.push_back(pr_);
	//在内模式中新建对应的表
	pMem_->CreateTable(pr_->GetRelationID());
	//创建一个空的表文件
	char* tablename_ = new char[strlen(sysdir_) + strlen("\\") + strlen(tname_) + 1];
	strcpy(tablename_, sysdir_);
	strcat(tablename_, "\\");
	strcat(tablename_, tname_);
	FILE *fp;
	fp = fopen(tablename_, "wb+");
	if(fp == NULL)
	{
		AfxMessageBox("无法新建表文件!");
		return 0;
	}
	delete[] tablename_;
	fclose(fp);
	return 1;
}

bool xkDict::DropRelation(const size_t RID_)
{
	xkRelation ** iterator_, *pr_ = 0;
	for(iterator_ = relations_.begin(); iterator_ != relations_.end(); iterator_++)
	{
		if((*iterator_)->GetRelationID() == RID_)
		{	
			if(*iterator_)
			{
				pr_ = *iterator_;
				//删除对应的内模式中的表
				pMem_->DropTable(RID_);
				//从数据字典上删除该关系信息
				relations_.erase(iterator_);
				delete pr_;
				SavexkDict();//保存数据字典到外存
				return 1;
			}
		}
	}
	return 0;
}
/*
 *	根据关系的ID,获取数据字典中的该关系对象
 */
xkRelation* xkDict::GetRelation(const size_t id_)
{
	xkRelation ** iterator_;
	for(iterator_ = relations_.begin(); iterator_ != relations_.end(); iterator_++)
	{
		if((*iterator_)->GetRelationID() == id_)
		{	
			return *iterator_;
		}
	}
	return 0;
}


void xkDict::LoadxkDict()
{
	if(GetFileAttributes(sysdir_) == 0xFFFFFFFF)// no this directionary
	{
		if(!CreateDirectory(sysdir_, NULL))
		{	
			AfxMessageBox("无法创建系统目录!");
			return;
		}
	}
	char *name_ = "\\xkDictionary";
	char *dictname_ = new char[strlen(sysdir_) + strlen(name_) +1];
	strcpy(dictname_, sysdir_);
	strcat(dictname_, name_);
	FILE *fp;
	fp = fopen(dictname_,"r");
	if(fp == NULL)
	{
		AfxMessageBox("无法打开字典文件!");
		return;
	}
	//load data of dictionary
	fread(&relationID_, sizeof(size_t), 1, fp);
	size_t rcount_,tmp_;
	fread(&rcount_, sizeof(size_t), 1, fp);
	for(size_t i = 0; i < rcount_; i++)
	{
		xkRelation * pr_ = new xkRelation;
		fread(&tmp_, sizeof(size_t), 1, fp);
		pr_->SetTupleCount(tmp_);
		unsigned long k;
		fread(&k, sizeof(unsigned long), 1, fp);
		pr_->SetRelationSize(k);
		fread(&tmp_, sizeof(size_t), 1, fp);
		pr_->SetRelationID(tmp_);
		bool b;
		fread(&b, sizeof(bool), 1, fp);
		pr_->SetOpened(b);
		int len;
		fread(&len, sizeof(int), 1, fp);
		char* pn_ = new char[len + 1];
		fread(pn_, len, 1, fp);
		pn_[len] = '\0';//这里要自己定位结束标志
		pr_->SetRelationName(pn_);

		xkTuple * pt_ = new xkTuple;
		fread(&tmp_, sizeof(size_t), 1, fp);
		pt_->SetAttrCount(tmp_);
		fread(&tmp_, sizeof(size_t), 1, fp);
		pt_->SetTupleSize(tmp_);
		fread(&tmp_, sizeof(size_t), 1, fp);
		pt_->SetRelationID(tmp_);
		
		xkAttribute * pa_ =new xkAttribute[pt_->GetAttrCount()];
		for(size_t t = 0; t < pt_->GetAttrCount(); t++)
		{
			xkAttributeType a;
			fread(&a, sizeof(xkAttributeType), 1, fp);
			pa_[t].SetType(a);
			fread(&tmp_, sizeof(size_t), 1, fp);
			pa_[t].SetSize(tmp_);
			fread(&len, sizeof(int), 1, fp);
			char * pn_ =new char[len + 1];
			fread(pn_, len, 1, fp);
			pn_[len] = '\0';
			pa_[t].SetName(pn_);
			fread(&b, sizeof(bool), 1, fp);
			pa_[t].SetSelected(b);
			fread(&b, sizeof(bool), 1, fp);
			if(b)
				pa_[t].SetKey();
		}
		pt_->SetAttributes(pa_);
		pr_->SetTuple(pt_);
		relations_.push_back(pr_);
		////////////////////////////在内模式中创建该表
		pMem_->CreateTable(pr_->GetRelationID());
		/////////////////////////////////////
	}
	delete[] dictname_;
	fclose(fp);
}

void xkDict::SavexkDict()
{
	if(GetFileAttributes(sysdir_) == 0xFFFFFFFF)// no this directionary
	{
		if(!CreateDirectory(sysdir_, NULL))
		{	
			AfxMessageBox("无法创建系统目录!");
			return;
		}
	}
	char *name_ = "\\xkDictionary";
	char *dictname_ = new char[strlen(sysdir_) + strlen(name_) +1];
	strcpy(dictname_, sysdir_);
	strcat(dictname_, name_);
	FILE *fp;
	fp = fopen(dictname_,"wb+");
	if(fp == NULL)
	{
		AfxMessageBox("无法打开字典文件!");
		return;
	}
	// save data of dictionary
	fwrite(&relationID_, sizeof(size_t), 1, fp);
	size_t tmp_ = relations_.size(); 
	fwrite(&tmp_, sizeof(size_t), 1, fp);
	for(size_t i =0; i< relations_.size(); i++)
	{
		tmp_ = relations_[i]->GetTupleCount();
		fwrite(&tmp_, sizeof(size_t), 1, fp);
		unsigned long k = relations_[i]->GetRelationSize();
		fwrite(&k, sizeof(unsigned long), 1, fp);
		tmp_ = relations_[i]->GetRelationID();
		fwrite(&tmp_, sizeof(size_t), 1, fp);
		bool b = relations_[i]->isOpen();
		fwrite(&b, sizeof(bool), 1, fp);
		int len = strlen(relations_[i]->GetRelationName());
		fwrite(&len, sizeof(int), 1, fp);
		fwrite(relations_[i]->GetRelationName(), len, 1, fp);
		xkTuple * t_ = relations_[i]->GetTuple();
		tmp_ = t_->GetAttrCount();
		fwrite(&tmp_, sizeof(size_t), 1, fp);
		tmp_ = t_->GetTupleSize();
		fwrite(&tmp_, sizeof(size_t), 1, fp);
		tmp_ = t_->GetRelationID();
		fwrite(&tmp_, sizeof(size_t), 1, fp);
		xkAttribute * pa_ = t_->GetAttributes();
		for(size_t j = 0; j < t_->GetAttrCount(); j++)
		{
			xkAttributeType a = pa_[j].GetType();
			fwrite(&a, sizeof(xkAttributeType), 1, fp);
			tmp_ = pa_[j].GetSize();
			fwrite(&tmp_, sizeof(size_t), 1, fp);
			len = strlen(pa_[j].GetName());
			fwrite(&len, sizeof(int), 1, fp);
			fwrite((pa_[j].GetName()), len, 1, fp);
			b = pa_[j].GetSelected();
			fwrite(&b, sizeof(bool), 1, fp);
			b = pa_[j].IsKey();
			fwrite(&b, sizeof(bool), 1, fp);
		}		
	}
	delete[] dictname_;
	fclose(fp);
}
/*
 *	通过关键字查找所需记录
	attr_  为关键字的属性
	value_ 为关键字的值
	desired_ 存放选中记录的内容
 */
bool xkRelation::GetSelectedTuple(const xkAttribute & attr_, const void* value_,void* desired_)
{
	if(!attr_.IsKey())
		return false;
	xkTable *pt_ = pMem_->GetTable(RID_);
	return pt_->GetSelectedRecord(attr_, value_, desired_, pMem_->GetMem());
}
/*
 *	attr_为关键字的属性
	originalval_为关键字的原始值
	value_为记录的更新值
 */
bool xkRelation::UpdateTuple(const xkAttribute & attr_, const void* originalval_, const void* value_)
{
	if(!attr_.IsKey())
		return false;
	xkTable *pt_ = pMem_->GetTable(RID_);
	return pt_->UpdateRecord(attr_, (const char*)originalval_, value_, pMem_->GetMem());
}

/*
 *	source_为新纪录的值
	size_为新记录的大小
 */
bool xkRelation::InsertTuple(const void* source_, const size_t size_)
{
	xkTable *pt_ = pMem_->GetTable(RID_);
	return pt_->InsertRecord(source_, size_, pMem_->GetMem());
}

/*
 *	attr_为关键字的属性
	originalval_为关键字的原始值
 */
bool xkRelation::DeleteTuple(const xkAttribute & attr_, const void* originalval_)
{
	if(!attr_.IsKey())
		return false;
	xkTable *pt_ = pMem_->GetTable(RID_);
	return pt_->DeleteRecord(attr_, (const char*)originalval_, pMem_->GetMem());
}

int	xkDict::FindTable(const char* tablename_)
{
	assert(tablename_ != 0);
	xkRelation** iterator_;
	for(iterator_ = relations_.begin(); iterator_ != relations_.end(); iterator_++)
	{
		if(strcmp((*iterator_)->GetRelationName() ,tablename_) == 0)
		{	
			return (*iterator_)->GetRelationID();
		}
	}
	return -1;
}

void xkDict::GetAllTablename(Vector<char*>& vec_)
{
	xkRelation** iterator_;
	vec_.clear();
	for(iterator_ = relations_.begin(); iterator_ != relations_.end(); iterator_++)
	{
		vec_.push_back((*iterator_)->GetRelationName());
	}
}

void xkDict::GetTableAttributename(const size_t id_, Vector<char*>& vec_)
{
//	assert(id_ >= 0 && id_ < relations_.size());
	vec_.clear();
	xkRelation ** iterator_;
	for(iterator_ = relations_.begin(); iterator_ != relations_.end(); iterator_++)
	{
		if((*iterator_)->GetRelationID() == id_)
		{
			xkTuple* pt_ = (*iterator_)->GetTuple();
			size_t attrcount_ = pt_->GetAttrCount();
			xkAttribute* pa_ = pt_->GetAttributes();
			for(size_t i = 0; i < attrcount_; i++)
				vec_.push_back(pa_[i].GetName());
			return;
		}
	}
	return;
}

void xkDict::GetTableAttribute(const size_t id_, xkAttriStruct& pas_)
{
	//assert(id_ >= 0 && id_ < relations_.size());
	xkRelation ** iterator_;
	for(iterator_ = relations_.begin(); iterator_ != relations_.end(); iterator_++)
	{
		if((*iterator_)->GetRelationID() == id_)
		{
			xkTuple* pt_ = (*iterator_)->GetTuple();
			pas_.attrcount_ = pt_->GetAttrCount();
			pas_.pa_ = pt_->GetAttributes();
			return;
		}
	}
	return;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -