BPTree.cpp
资源名称:minisqlc.rar [点击查看]
上传用户:lkd6667
上传日期:2015-05-13
资源大小:1448k
文件大小:43k
源码类别:
其他数据库
开发平台:
C/C++
- //!BPTree.cpp 2007/6/28
- #include "BPtree.h"
- #include "Glob_Var.h"
- extern unsigned int BTreeNodeSize;
- extern _M_Buffer Buffer;
- extern unsigned int SizeOfPageHead;
- extern char CurLocation[256];
- extern char CurRelationName[33];
- /*=========================================================================
- ========= definition for BPTree_Index =============
- =========================================================================*/
- /////////////////////////////////////////////////////////////////////////////////////////////////////////
- //constructor and destructor
- BPTree_Index::BPTree_Index() {
- }
- BPTree_Index::~BPTree_Index(){
- }
- /////////////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree_Index::createHead(char* KeyStr) {
- setKeyInfo(KeyStr); // calculate the Keysize and KeyAttrNum
- // calculate the MaxItemNum in a node
- // Next_Empty_Block | IsLeaf | ItemOnNode | p[0],k[0],...,p[MaxItemNum]
- IdxHead.MaxItemNum = ( BTreeNodeSize - 2*sizeof(_F_FileAddr) - sizeof(bool) - sizeof(int) )
- / ( sizeof(_F_FileAddr) + IdxHead.KeySize );
- //no empty block
- IdxHead.FirstEmptyBlock.ulFilePageID = 0;
- IdxHead.FirstEmptyBlock.uiOffset = 0;
- IdxHead.LastEmptyBlock.ulFilePageID = 0;
- IdxHead.LastEmptyBlock.uiOffset = 0;
- //the first address of the BTree node
- IdxHead.FirstNewBlock.ulFilePageID = 1;
- IdxHead.FirstNewBlock.uiOffset = SizeOfPageHead + BTreeNodeSize;
- // initialize the root address
- IdxHead.root.ulFilePageID = 1;
- IdxHead.root.uiOffset = SizeOfPageHead;
- // the start node isn't existed
- IdxHead.start.ulFilePageID = 0;
- IdxHead.start.uiOffset = 0;
- // the key information
- KeyInfo = KeyStr;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////////////
- // write the infomation to the head of the btree index file
- void BPTree_Index::writeHeadToFile() {
- // get the start address which store the head
- char address[256];
- strcpy(address,CurLocation);
- strcat(address,CurRelationName);
- strcat(address,".idx");
- _M_File test = Buffer[address];
- _F_FileAddr ptr = test.GetIdxPoint();
- // write IdxHead
- void* temp = (void*)(&IdxHead);
- _F_FileAddr next;
- next = MemWrite( temp,sizeof(Index_Head),&ptr);
- // write Key information
- temp = (void*)KeyInfo;
- MemWrite(temp,strlen(KeyInfo) + 1,&next);
- }
- ////////////////////////////////////////////////////////////////////////////////////////////////////////////
- // read the infomation from the head of the btree index file
- void BPTree_Index::readHeadFromFile() {
- // get the start address which store the head
- char address[256];
- strcpy(address,CurLocation);
- strcat(address,CurRelationName);
- strcat(address,".idx");
- _M_File test = Buffer[address];
- _F_FileAddr ptr = test.GetIdxPoint();
- // read IdxHead
- Index_Head* temp;
- temp = (Index_Head*) ( ptr.MemAddr() );
- IdxHead = *temp;
- // read key information
- ptr.ShiftOffset(sizeof(Index_Head));
- KeyInfo = (char*) (ptr.MemAddr());
- }
- ////////////////////////////////////////////////////////////////////////////////////////////////////////////
- // calculate the KeySize and count the KeyAttrNum
- void BPTree_Index::setKeyInfo(char* KeyStr) {
- IdxHead.KeyAttrNum = 0; // the number of fields(attributes) in primary key
- IdxHead.KeySize = 0; // sizeof(Key_Attr) * KeyAttrNum
- char* temp = KeyStr;
- for( int i=0; temp[i]!=0; i++)
- {
- IdxHead.KeyAttrNum++;
- switch(temp[i])
- {
- case 'i' : IdxHead.KeySize += sizeof(int); break;
- case 'f' : IdxHead.KeySize += sizeof(float); break;
- case 'c' : {
- //deal with the max length in a string defined by the user
- int num = 0;
- for( i=i+1; isdigit(temp[i]); i++)
- {
- num = num * 10 + temp[i] - '0';
- }
- i--; // move the index back
- num++; // for ' ' which is the end of a string
- IdxHead.KeySize += num;
- break;
- }
- default : throw(1021);
- }
- }
- }
- // /////////////////////////////////////////////////////////////////////////////////////////////////////////
- int BPTree_Index::getKeySize() {
- return IdxHead.KeySize;
- }
- int BPTree_Index::getKeyAttrNum() {
- return IdxHead.KeyAttrNum;
- }
- int BPTree_Index::getMaxItemNum() {
- return IdxHead.MaxItemNum;
- }
- _F_FileAddr BPTree_Index::getRoot() {
- return IdxHead.root;
- }
- _F_FileAddr BPTree_Index::getStartNode() {
- return IdxHead.start;
- }
- char* BPTree_Index::getKeyInfo() {
- return KeyInfo;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////////////
- /*=========================================================================
- ========= definition for BPTreeNode =============
- =========================================================================*/
- /////////////////////////////////////////////////////////////////////////////////////////////
- // initialize the node
- BPTreeNode::BPTreeNode() {
- // read the head of the file
- BPTree_Index temp;
- temp.readHeadFromFile();
- MaxItem = temp.getMaxItemNum(); // get the MaxItem
- KeyInfo = temp.getKeyInfo(); // get the KeyInfo
- KeySize = temp.getKeySize(); // get the size of key
- ItemOnNode = 0; // the key number is 0
- p = new _F_FileAddr[MaxItem+1];
- for(int i=0;i<MaxItem+1;i++)
- {
- p[i].ulFilePageID = 0;
- p[i].uiOffset = 0;
- }
- k = new pKey_Attr[MaxItem];
- for(int j=0;j<MaxItem;j++)
- k[j] = NULL;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- void BPTreeNode::initialize() {
- for(int j=0;j<ItemOnNode;j++)
- k[j] = NULL;
- ItemOnNode = 0;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // write the separate space into one block
- // MemPtr is the first address of the block
- void BPTreeNode::writeNodeToFile(_F_FileAddr ptr) {
- void* MemPtr;
- MemPtr = ptr.MemAddr();
- // write Next_Empty_Block into the block
- MemWrite((void*)(&Next_Empty_Block),sizeof(_F_FileAddr),&ptr);
- // move to the first address of IsLeaf
- MemPtr = (void*)((char*)MemPtr + sizeof(_F_FileAddr));
- // write IsLeaf into the block
- bool* pIsLeaf = (bool*)MemPtr;
- *pIsLeaf = IsLeaf;
- // move to the first address of ItemNode in the block
- MemPtr = (void*)((char*)MemPtr + sizeof(bool));
- // write ItemOnNode into the block
- int *pItemOnNode = (int*)MemPtr;
- *pItemOnNode = ItemOnNode;
- // move the the first address of p[o] in the block
- MemPtr = (void*)((char*)MemPtr + sizeof(int));
- int i;
- for(i=0;i<ItemOnNode;i++)
- {
- // write the p[i]
- _F_FileAddr* pp = (_F_FileAddr*)MemPtr;
- pp->ulFilePageID = p[i].ulFilePageID;
- pp->uiOffset = p[i].uiOffset;
- // move to the first address of k[i] in the block
- MemPtr = (void*)((char*)MemPtr + sizeof(_F_FileAddr));
- // write the k[i]
- pKey_Attr pField = k[i];
- for(int j=0;KeyInfo[j]!=0;j++)
- {
- switch(KeyInfo[j])
- {
- case 'i' : // int value
- int *pIntValue;
- pIntValue = (int*)MemPtr;
- *pIntValue = pField->value.IntValue;
- pField = pField->next;
- MemPtr = (void*)((char*)MemPtr + sizeof(int));
- break;
- case 'f' : // float value
- float *pFloatValue;
- pFloatValue = (float*)MemPtr;
- *pFloatValue = pField->value.FloatValue;
- pField = pField->next;
- MemPtr = (void*)((char*)MemPtr + sizeof(float));
- break;
- case 'c' : // string
- int num = 0;
- for(j=j+1; isdigit(KeyInfo[j]);j++)
- {
- num = num * 10 + KeyInfo[j] - '0';
- }
- j--; // move the index back
- num++; // for ' ' which is the end of a string
- char* pCharValue = (char*)MemPtr;
- strcpy(pCharValue,pField->value.pCharValue);
- pField = pField->next;
- MemPtr = (void*)((char*)MemPtr + num);
- break;
- }
- }// KeyInfo[i] = ' '
- }// i = ItemOnNode
- if( 0 == IsLeaf) // not a leaf
- {
- //Write the p[ItemOnNode]
- _F_FileAddr* pp = (_F_FileAddr*)MemPtr;
- pp->ulFilePageID = p[i].ulFilePageID;
- pp->uiOffset = p[i].uiOffset;
- }
- else // is is a leaf
- {
- // move to the address of p[MaxItem]
- MemPtr = (void*)( (char*)MemPtr + (MaxItem - ItemOnNode) * (KeySize + sizeof(_F_FileAddr)) );
- //Write the p[MaxItem] into the block
- _F_FileAddr* pp = (_F_FileAddr*)MemPtr;
- pp->ulFilePageID = p[MaxItem].ulFilePageID;
- pp->uiOffset = p[MaxItem].uiOffset;
- }
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // the struct of node
- // NodeType | ItemOnNode | p[0],k[0],p[1],k[1],......,p[MaxItem-1],k[MaxItem-1],p[MaxItem]
- void BPTreeNode::readNodeFromFile(_F_FileAddr ptr) {
- // move to the address of NodeType
- void* temp = ptr.MemAddr();
- // get the Next_Empty_Block
- _F_FileAddr* pNext = (_F_FileAddr*)temp;
- Next_Empty_Block.ulFilePageID = pNext->ulFilePageID;
- Next_Empty_Block.uiOffset = pNext->uiOffset;
- // move to the address of NodeType
- temp = (void*)((char*)temp + sizeof(_F_FileAddr));
- // get the NodeType
- bool* pIsLeaf = (bool*)temp;
- IsLeaf = *pIsLeaf;
- // move to the address of ItemOnNode
- temp = (void*)((char*)temp + sizeof(bool));
- // get the ItemOnNode
- int* pItemOnNode = (int*)temp;
- ItemOnNode = *pItemOnNode;
- // move to the first address of p[0]
- temp = (void*)((char*)temp + sizeof(int));
- // read p[i] and k[i]
- int i;
- for(i=0;i<ItemOnNode;i++)
- {
- // get the p[i]
- _F_FileAddr* pp;
- pp = (_F_FileAddr*)temp;
- p[i].ulFilePageID = pp->ulFilePageID;
- p[i].uiOffset = pp->uiOffset;
- // move to the first address of k[i] in the block
- temp = (void*)((char*)temp + sizeof(_F_FileAddr));
- // get the k[i]
- pKey_Attr pField;
- for(int j=0; KeyInfo[j]!=' ';j++)
- {
- if(j == 0) // the first node
- pField = k[i] = new Key_Attr;
- else
- {
- pField->next = new Key_Attr;
- pField = pField->next;
- }
- switch(KeyInfo[j])
- {
- case 'i' : // int value
- int* pIntValue;
- pIntValue = (int*) temp;
- pField->value.IntValue = *pIntValue;
- pField->next = NULL;
- temp = (void*)((char*)temp + sizeof(int));
- break;
- case 'f' : // float value
- float* pFloatValue;
- pFloatValue = (float*) temp;
- pField->value.FloatValue = *pFloatValue;
- pField->next = NULL;
- temp = (void*)((char*)temp + sizeof(float));
- break;
- case 'c' : // string
- int num = 0;
- for( j=j+1; isdigit(KeyInfo[j]); j++)
- {
- num = num * 10 + KeyInfo[j] - '0';
- }
- j--; // move the index back
- num++; // for ' ' which is the end of a string
- char* pCharValue = new char [num];
- char* str = (char*)temp;
- strcpy(pCharValue,str);
- pField->value.pCharValue = pCharValue;
- pField->next = NULL;
- temp = (void*)((char*)temp + num);
- break;
- }
- } //KeyInfo[i] = ' '
- } // i = ItemOnNode
- if( 0 == IsLeaf)
- {
- // get the p[ItemOnNode]
- _F_FileAddr* pp;
- pp = (_F_FileAddr*)temp;
- p[i].ulFilePageID = pp->ulFilePageID;
- p[i].uiOffset = pp->uiOffset;
- }
- else
- {
- // move to the address of p[MaxItem]
- temp = (void*)( (char*)temp + (MaxItem - ItemOnNode) * (KeySize + sizeof(_F_FileAddr)) );
- // get the p[MaxItem]
- _F_FileAddr* pp;
- pp = (_F_FileAddr*)temp;
- p[MaxItem].ulFilePageID = pp->ulFilePageID;
- p[MaxItem].uiOffset = pp->uiOffset;
- }
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // delete the space allocate for the node
- BPTreeNode::~BPTreeNode() {
- // delete the link list of keys
- for(int i=0;i<ItemOnNode;i++)
- {
- pKey_Attr head,temp;
- head = temp = k[i];
- for(int j=0;KeyInfo[j]!=0;j++)
- {
- switch(KeyInfo[j])
- {
- case 'i' : // int
- head = head->next;
- delete temp;
- temp = head;
- break;
- case 'f' : // float
- head = head->next;
- delete temp;
- temp = head;
- break;
- case 'c' : // char
- delete [] (head->value.pCharValue);
- head = head->next;
- delete temp;
- temp = head;
- while(isdigit(KeyInfo[++j])) ; //skip digital number
- j--;
- break;
- }
- }
- }
- // detele the array of p and k
- delete [] p ;
- delete [] k;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // compare the key1 and key2
- // if Key1 is greater than key2,return 1
- // if key1 is equal with key2, return 0
- // if key1 is less than key2,return -1
- int BPTreeNode::compare(pKey_Attr Key1,pKey_Attr Key2) {
- for(int i=0;KeyInfo[i]!=' ';i++)
- {
- switch(KeyInfo[i])
- {
- case 'i' :
- if(Key1->value.IntValue > Key2->value.IntValue)
- return 1;
- else if(Key1->value.IntValue < Key2->value.IntValue)
- return -1;
- else
- break;
- case 'f' :
- if(Key1->value.FloatValue > Key2->value.FloatValue)
- return 1;
- else if(Key1->value.FloatValue < Key2->value.FloatValue)
- return -1;
- else
- break;
- case 'c' :
- while(isdigit(KeyInfo[++i])) ;
- i--;
- int temp = strcmp(Key1->value.pCharValue,Key2->value.pCharValue);
- if(temp == 0)
- break;
- else if(temp > 0)
- return 1;
- else
- return -1;
- }
- Key1 = Key1->next;
- Key2 = Key2->next;
- }
- return 0;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // insert a key in the node which isn a leaf
- void BPTreeNode::insertKeyInLeaf(_F_FileAddr pRec,pKey_Attr pPrimKey) {
- if( 0 == ItemOnNode ) // The node is empty
- {
- p[0] = pRec;
- k[0] = pPrimKey;
- }
- // p[ItemOnNode + 1] = p[ItemOnNode];
- for(int i=ItemOnNode-1;i>=0;i--)
- {
- if(compare(pPrimKey,k[i]) < 0)
- {
- p[i+1] = p[i];
- k[i+1] = k[i];
- continue;
- }
- else
- break;
- }
- p[i+1] = pRec;
- k[i+1] = pPrimKey;
- ItemOnNode++;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // insert a key in the node which isn't a leaf
- void BPTreeNode::insertKeyNotLeaf(pKey_Attr pPrimKey,_F_FileAddr pRec) {
- // the node is never empty
- for(int i=ItemOnNode-1;i>=0;i--)
- {
- if(compare(pPrimKey,k[i]) < 0)
- {
- p[i+2] = p[i+1];
- k[i+1] = k[i];
- continue;
- }
- else
- break;
- }
- p[i+2] = pRec;
- k[i+1] = pPrimKey;
- ItemOnNode++;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // delete a key in a leaf and adjust the node
- void BPTreeNode::deleteKeyInLeaf(pKey_Attr pPrimKey) {
- int i;
- for(i=0;i<ItemOnNode;i++)
- {
- if( compare(pPrimKey,k[i]) == 0 )
- break;
- }
- deleteKeySpace(k[i]); // delete the space of k[i]
- // adjust the node
- for(;i<ItemOnNode-1;i++)
- {
- p[i] = p[i+1];
- k[i] = k[i+1];
- }
- p[ItemOnNode-1].ulFilePageID = 0;
- p[ItemOnNode-1].uiOffset = 0;
- k[ItemOnNode-1] = NULL;
- ItemOnNode--;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // delete the key in the node, and automatic adjust the node
- void BPTreeNode::deleteKeyNotLeaf(pKey_Attr pPrimKey) {
- int i;
- for(i=0;i<ItemOnNode;i++)
- {
- if( compare(pPrimKey,k[i]) == 0 )
- break;
- }
- deleteKeySpace(k[i]); // delete the space of k[i]
- // adjust the node
- for(;i<ItemOnNode-1;i++)
- {
- k[i] = k[i+1];
- p[i+1] = p[i+2];
- }
- k[ItemOnNode-1] = NULL;
- p[ItemOnNode].ulFilePageID = 0;
- p[ItemOnNode].uiOffset = 0;
- ItemOnNode--;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // delete the space of the first key in the node
- void BPTreeNode::deleteFirstKey() {
- pKey_Attr head,temp;
- head = temp = k[0];
- for(int j=0;KeyInfo[j]!=0;j++)
- {
- switch(KeyInfo[j])
- {
- case 'i' : // int
- head = head->next;
- delete temp;
- temp = head;
- break;
- case 'f' : // float
- head = head->next;
- delete temp;
- temp = head;
- break;
- case 'c' : // char
- delete [] (head->value.pCharValue);
- head = head->next;
- delete temp;
- temp = head;
- while(isdigit(KeyInfo[++j])) ; //skip digital number
- j--;
- break;
- }
- }
- for(int i=0;i<ItemOnNode-1;i++)
- {
- p[i] = p[i+1];
- k[i] = k[i+1];
- }
- p[ItemOnNode-1] = p[ItemOnNode];
- p[ItemOnNode].ulFilePageID = 0;
- p[ItemOnNode].uiOffset = 0;
- k[ItemOnNode - 1] = NULL;
- ItemOnNode--;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // delete the space of the key
- void BPTreeNode::deleteKeySpace(pKey_Attr Key) {
- pKey_Attr head,temp;
- head = temp = Key;
- for(int j=0;KeyInfo[j]!=0;j++)
- {
- switch(KeyInfo[j])
- {
- case 'i' : // int
- head = head->next;
- delete temp;
- temp = head;
- break;
- case 'f' : // float
- head = head->next;
- delete temp;
- temp = head;
- break;
- case 'c' : // char
- delete [] (head->value.pCharValue);
- head = head->next;
- delete temp;
- temp = head;
- while(isdigit(KeyInfo[++j])) ; //skip digital number
- j--;
- break;
- }
- }
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- // create a key equal to Key1,and automatic open a new space
- pKey_Attr BPTreeNode::createKey(pKey_Attr Key1) {
- pKey_Attr Key2,temp;
- for(int j=0; KeyInfo[j]!=' ';j++)
- {
- if(j == 0) // the first node
- Key2 = temp = new Key_Attr;
- else
- {
- temp->next = new Key_Attr;
- temp = temp->next;
- }
- switch(KeyInfo[j])
- {
- case 'i' : // int value
- temp->value.IntValue = Key1->value.IntValue;
- temp->next = NULL;
- break;
- case 'f' : // float value
- temp->value.FloatValue = Key1->value.FloatValue;
- temp->next = NULL;
- break;
- case 'c' : // string
- int num = 0;
- for( j=j+1; isdigit(KeyInfo[j]); j++)
- {
- num = num * 10 + KeyInfo[j] - '0';
- }
- j--; // move the index back
- num++; // for ' ' which is the end of a string
- char* pCharValue = new char [num];
- char* str = Key1->value.pCharValue;
- strcpy(pCharValue,str);
- temp->value.pCharValue = pCharValue;
- temp->next = NULL;
- break;
- }
- Key1 = Key1->next; // move to the next node
- } //KeyInfo[i] = ' '
- return Key2;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////
- bool BPTreeNode::isNotEnoughPoints() {
- int n = MaxItem + 1;
- if( 0 == IsLeaf ) // it isn't a leaf
- {
- int m;
- if( !(n%2) )
- m = n/2 ; // n = NodeL.MaxItem + 1
- else
- m = n/2 + 1;
- if( (ItemOnNode + 1) < m) // not enough points ,ItemOnNode+1 is the number of points
- return true;
- else
- return false;
- }
- else // it is a leaf
- {
- int m;
- if( ! ((n-1)%2) )
- m = (n-1)/2 ; // n = NodeL.MaxItem + 1
- else
- m = (n-1)/2 + 1;
- if( ItemOnNode < m ) // not enough points
- return true;
- else
- return false;
- }
- }
- ////////////////////////////////////////////////////////////////////////////////////////////////////
- /*=========================================================================
- ========= definition for BPTree =============
- =========================================================================*/
- ////////////////////////////////////////////////////////////////////////////////////////////////////
- //constructor
- BPTree::BPTree() {
- _F_FileAddr temp;
- temp.ulFilePageID = 0;
- temp.uiOffset = 0;
- for(int i=0; i<DEPTH; i++)
- SearchPath[i] = temp;
- }
- //destructor
- BPTree::~BPTree() {
- }
- ////////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree::setPath() {
- char address[256];
- strcpy(address, CurLocation);
- strcat(address, CurRelationName);
- strcat(address, ".idx");
- _M_File test = Buffer[address];
- }
- ////////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree::create(char *KeyStr) {
- setPath();
- BPTree_Index idx;
- idx.createHead(KeyStr);
- idx.writeHeadToFile();
- BPTreeNode root;
- root.IsLeaf = 1;
- root.writeNodeToFile(idx.getRoot());
- }
- ////////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree::createNewRoot(_F_FileAddr p0, pKey_Attr pPrimKey, _F_FileAddr p1) {
- _F_FileAddr Newroot;
- Newroot = createNodeInFile();
- BPTree_Index idx;
- idx.readHeadFromFile();
- idx.IdxHead.root = Newroot;
- idx.writeHeadToFile();
- BPTreeNode Root;
- Root.IsLeaf = 0;
- Root.ItemOnNode = 1;
- Root.p[0] = p0;
- Root.p[1] = p1;
- Root.k[0] = pPrimKey;
- Root.writeNodeToFile(Newroot);
- }
- ////////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree::grantRoot(_F_FileAddr pfa) {
- BPTree_Index idx;
- idx.readHeadFromFile();
- idx.IdxHead.root = pfa;
- idx.writeHeadToFile();
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree::deleteNodeInFile(_F_FileAddr pfa) {
- BPTree_Index idx;
- idx.readHeadFromFile();
- //make the first empty block point to the new delete block
- if(idx.IdxHead.FirstEmptyBlock.ulFilePageID == 0) {
- idx.IdxHead.FirstEmptyBlock = pfa;
- idx.IdxHead.LastEmptyBlock = pfa;
- }
- else {
- // make the last empty block point to the new delete block
- BPTreeNode NextNode;
- NextNode.readNodeFromFile(idx.IdxHead.LastEmptyBlock);
- NextNode.Next_Empty_Block = pfa;
- NextNode.writeNodeToFile(idx.IdxHead.LastEmptyBlock);
- // change the index head
- idx.IdxHead.LastEmptyBlock = pfa;
- }
- idx.writeHeadToFile();
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //--
- bool BPTree::search(pKey_Attr pPrimKey, pKey_Location pKeyLoca) {
- setPath();
- BPTree_Index idx;
- idx.readHeadFromFile();
- _F_FileAddr pfa = idx.getRoot();
- BPTreeNode Node;
- for(int level=0; level<DEPTH; level++) {
- Node.readNodeFromFile(pfa);
- SearchPath[level] = pfa;
- //not leaf
- if(Node.IsLeaf == 0) {
- for(int i=0; i<=Node.ItemOnNode; i++) {
- if(i == Node.ItemOnNode) {
- pfa = Node.p[i];
- break;
- }
- else if(Node.compare(pPrimKey, Node.k[i]) < 0) {
- pfa = Node.p[i];
- break;
- }
- else if(Node.compare(pPrimKey,Node.k[i]) >= 0)
- continue;
- }
- }
- else {
- //is leaf
- for(int j=0; j<=Node.ItemOnNode; j++) {
- if(j == Node.ItemOnNode) {
- pKeyLoca->ptr = pfa;
- pKeyLoca->offset = Node.MaxItem;
- return false;
- }
- else if(Node.compare(pPrimKey, Node.k[j]) == 0) {
- pKeyLoca->ptr = pfa;
- pKeyLoca->offset = j;
- return true;
- }
- else if( Node.compare(pPrimKey,Node.k[j]) > 0 ) // pPrimKey > k[i]
- continue;
- else {
- pKeyLoca->ptr = pfa;
- pKeyLoca->offset = j;
- return false;
- }
- }
- }
- }
- throw 1028;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //--
- bool BPTree::isRoot(_F_FileAddr pfa) {
- return SearchPath[0] == pfa;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //--
- bool BPTree::isEmpty() {
- Key_Location KeyLoca;
- // cout<<"begin isEmpty()"<<endl;//=======//
- KeyLoca = getStart();
- BPTreeNode FirstNode;
- FirstNode.readNodeFromFile(KeyLoca.ptr);
- // cout<<"end isEmpty()"<<endl; //=====//
- if(FirstNode.ItemOnNode == 0)
- return true;
- return false;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //--
- Key_Location BPTree::moveToNextKey(Key_Location KeyLoca) {
- Key_Location temp;
- BPTreeNode node;
- node.readNodeFromFile(KeyLoca.ptr);
- if( node.MaxItem == KeyLoca.offset ) {
- if(node.p[node.MaxItem].ulFilePageID == 0)
- temp.ptr.ulFilePageID = 0;
- else {
- // get the address of the first key in the next node
- BPTreeNode NextNode;
- NextNode.readNodeFromFile(node.p[node.MaxItem]);
- temp.ptr = node.p[node.MaxItem];
- temp.offset = 0;
- }
- return temp;
- }
- int i = KeyLoca.offset + 1;
- // the next key is empty or full
- if( 0 == node.p[i].ulFilePageID || node.MaxItem == i) {
- i = node.MaxItem; // the last p[MaxItem]
- if( 0 == node.p[i].ulFilePageID )
- temp.ptr.ulFilePageID = 0;
- else {
- BPTreeNode NextNode;
- NextNode.readNodeFromFile(node.p[i]);
- temp.ptr = node.p[i];
- temp.offset = 0;
- }
- }
- else {
- // the address of the next key in the current node
- temp.ptr = KeyLoca.ptr;
- temp.offset = KeyLoca.offset + 1;
- }
- return temp;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //this method returns the address of the first key in the leftest leaf node
- //--
- Key_Location BPTree::getStart() {
- BPTree_Index idx;
- idx.readHeadFromFile();
- _F_FileAddr ptr = idx.getRoot();
- for( ; ; ) {
- BPTreeNode Node;
- Node.readNodeFromFile(ptr);
- if( 1 == Node.IsLeaf ) {
- Key_Location temp;
- temp.ptr = ptr;
- temp.offset = 0;
- return temp;
- }
- else
- ptr = Node.p[0];
- }
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //--
- _F_FileAddr BPTree::getParent(_F_FileAddr ptr) {
- for(int i=0; SearchPath[i].ulFilePageID != 0; i++) {
- if(SearchPath[i] == ptr)
- return SearchPath[i-1];
- }
- throw 1022;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //this method returns the address specified by Key_Location
- //--
- _F_FileAddr BPTree::getCurRecAddr(Key_Location KeyLoca) {
- BPTreeNode node;
- node.readNodeFromFile(KeyLoca.ptr);
- return node.p[KeyLoca.offset];
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //--
- _F_FileAddr BPTree::createNodeInFile() {
- BPTree_Index idx;
- idx.readHeadFromFile();
- //the index file has no empty block
- if( 0 == idx.IdxHead.FirstEmptyBlock.ulFilePageID ) {
- // firstly,we should check whether the block overflow the current page
- // If so,use the next page
- void* CheckOverflow = (void*) new char[BTreeNodeSize];
- _F_FileAddr Next = MemWrite(CheckOverflow, BTreeNodeSize, &idx.IdxHead.FirstNewBlock);
- _F_FileAddr temp = idx.IdxHead.FirstNewBlock;
- idx.IdxHead.FirstNewBlock = Next;
- idx.writeHeadToFile();
- return temp;
- }
- else {
- int flag = 0;
- if(idx.IdxHead.FirstEmptyBlock == idx.IdxHead.LastEmptyBlock)
- flag = 1;
- _F_FileAddr temp = idx.IdxHead.FirstEmptyBlock;
- if( 1 == flag) {
- //there is just one empty block
- idx.IdxHead.FirstEmptyBlock.ulFilePageID = 0;
- idx.IdxHead.FirstEmptyBlock.uiOffset = 0;
- idx.IdxHead.LastEmptyBlock.ulFilePageID = 0;
- idx.IdxHead.LastEmptyBlock.uiOffset = 0;
- }
- else {
- // change FisrtEmptyBlock point to the next block
- BPTreeNode NextNode;
- NextNode.readNodeFromFile(temp);
- idx.IdxHead.FirstEmptyBlock = NextNode.Next_Empty_Block;
- }
- idx.writeHeadToFile();
- return temp;
- }
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //this method returns the address of the last key in the rightest node
- //--
- Key_Location BPTree::getEnd() {
- BPTree_Index idx;
- idx.readHeadFromFile();
- _F_FileAddr ptr = idx.getRoot();
- for( ; ; ) {
- BPTreeNode Node;
- Node.readNodeFromFile(ptr);
- if( 1 == Node.IsLeaf ) {
- Key_Location temp;
- temp.ptr = ptr;
- temp.offset = Node.ItemOnNode - 1;
- return temp; // return the first address of the first Key in the first node
- }
- else
- ptr = Node.p[Node.ItemOnNode];
- }
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //--
- void BPTree::insert(pKey_Attr pPrimKey, _F_FileAddr pRec) {
- setPath();
- Key_Location KeyLoca;
- if(search(pPrimKey, &KeyLoca))
- throw 1024;
- else
- insert_entry(KeyLoca.ptr, pPrimKey, pRec);
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////
- //--
- void BPTree::insert_entry(_F_FileAddr L, pKey_Attr pPrimKey, _F_FileAddr pRec) {
- BPTreeNode NodeL;
- NodeL.readNodeFromFile(L);
- //if L has less than n-1 key values
- if(NodeL.ItemOnNode < NodeL.MaxItem) {
- if(NodeL.IsLeaf ==1)
- NodeL.insertKeyInLeaf(pRec, pPrimKey);
- else
- NodeL.insertKeyNotLeaf(pPrimKey, pRec);
- }
- else {
- //create a new node
- _F_FileAddr L_ = createNodeInFile();
- BPTreeNode NodeL_;
- pKey_Attr pPrimKey_;
- int n = NodeL.MaxItem + 1;
- if(NodeL.IsLeaf ==1) {
- NodeL_.IsLeaf = 1;
- int m;
- if( !(n%2) )
- m = n/2 ;
- else
- m = n/2 + 1;
- //p[0]k[0]...k[m-1]p[m] | k[m]...
- // pPrimKey < k[m-1]
- if( NodeL.compare(NodeL.k[m-1], pPrimKey) > 0) {
- m--;
- pPrimKey_ = NodeL.createKey(NodeL.k[m]);
- }
- // k[m] > pPrimKey >= k[m-1]
- else if( (m == n - 1) || ( NodeL.compare(NodeL.k[m], pPrimKey) > 0 ) )
- pPrimKey_ = NodeL.createKey(pPrimKey);
- else
- // pPrimKey > k[m]
- pPrimKey_ = NodeL.createKey(NodeL.k[m]);
- //copy p[m]....to L_
- for(int i=m; i<NodeL.MaxItem; i++) {
- NodeL_.p[i-m] = NodeL.p[i];
- NodeL_.k[i-m] = NodeL.k[i];
- //erase
- NodeL.k[i] = NULL;
- NodeL.p[i].ulFilePageID = 0;
- NodeL.p[i].uiOffset = 0;
- NodeL_.ItemOnNode++;
- NodeL.ItemOnNode--;
- }
- if(NodeL.compare(pPrimKey, pPrimKey_) < 0)
- NodeL.insertKeyInLeaf(pRec,pPrimKey);
- else
- NodeL_.insertKeyInLeaf(pRec,pPrimKey);
- }
- else { //NodeL is not a leaf
- NodeL_.IsLeaf = 0;
- int m;
- if( !(n%2) )
- m = n/2 ;
- else
- m = n/2 + 1;
- m = NodeL.MaxItem - m;
- //p[0],k[0]....k[m]p[m+1] | k[m+1]...
- //pPrimKey > k[m+1]
- if( NodeL.compare(pPrimKey, NodeL.k[m+1]) > 0 ) {
- m++;
- pPrimKey_ = NodeL.createKey(NodeL.k[m]);
- }
- // k[m] < pPrimKey <= k[m+1]
- else if( NodeL.compare(pPrimKey, NodeL.k[m]) > 0 ) {
- m++;
- pPrimKey_ = NodeL.createKey(pPrimKey);
- }
- // pPrimKey <= k[m]
- else {
- pPrimKey_ = NodeL.createKey(NodeL.k[m]);
- }
- // move and delete
- NodeL_.p[0].ulFilePageID = 0;
- NodeL_.p[0].uiOffset = 0;
- NodeL_.k[0] = NodeL.k[m];
- NodeL.k[m] = NULL;
- NodeL_.ItemOnNode++;
- NodeL.ItemOnNode--;
- for(int i=m+1; i<NodeL.MaxItem; i++) {
- NodeL_.p[i-m] = NodeL.p[i];
- NodeL_.k[i-m] = NodeL.k[i];
- //erase
- NodeL.k[i] = NULL;
- NodeL.p[i].ulFilePageID = 0;
- NodeL.p[i].uiOffset = 0;
- NodeL_.ItemOnNode++;
- NodeL.ItemOnNode--;
- }
- NodeL_.p[i-m] = NodeL.p[i];
- NodeL.p[i].ulFilePageID = 0;
- NodeL.p[i].uiOffset = 0;
- if( NodeL.compare(pPrimKey, pPrimKey_) < 0 )
- NodeL.insertKeyNotLeaf(pPrimKey, pRec);
- else
- NodeL_.insertKeyNotLeaf(pPrimKey,pRec);
- NodeL_.deleteFirstKey();
- }
- if( !isRoot(L) )
- insert_entry(getParent(L), pPrimKey_, L_);
- else
- createNewRoot(L, pPrimKey_, L_);
- if(NodeL.IsLeaf == 1) {
- NodeL_.p[NodeL.MaxItem] = NodeL.p[NodeL.MaxItem];
- NodeL.p[NodeL.MaxItem] = L_;
- }
- NodeL_.writeNodeToFile(L_);
- }
- NodeL.writeNodeToFile(L);
- }
- //////////////////////////////////////////////////////////////////////////////////////////////////////////
- bool BPTree::canCoalesce(BPTreeNode* pNode, BPTreeNode* pNode_) {
- if(pNode->IsLeaf == 1)
- return (pNode->ItemOnNode + pNode_->ItemOnNode <= pNode->MaxItem);
- else
- return (pNode->ItemOnNode + pNode_->ItemOnNode < pNode->MaxItem);
- }
- //////////////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree::coalesce(BPTreeNode* pNodeL, BPTreeNode* pNodeL_, pKey_Attr pPrimKey_, bool IsLLeftOfL_) {
- if( 0 == pNodeL->IsLeaf ) {
- if(IsLLeftOfL_) {
- //move right
- int j = pNodeL->ItemOnNode + 1;
- pNodeL_->p[pNodeL_->ItemOnNode + j] = pNodeL_->p[pNodeL_->ItemOnNode];
- for(int i=pNodeL_->ItemOnNode-1; i>=0; i--) {
- pNodeL_->k[i + j] = pNodeL_->k[i];
- pNodeL_->p[i + j] = pNodeL_->p[i];
- }
- //assign V' to the pNodeL_
- pNodeL_->k[j-1] = pPrimKey_;
- pNodeL_->p[j-1] = pNodeL->p[pNodeL->ItemOnNode];
- // move all elements in pNodeL to pNodeL_
- for(i=0; i<pNodeL->ItemOnNode; i++) {
- pNodeL_->p[i] = pNodeL->p[i];
- pNodeL_->k[i] = pNodeL->k[i];
- }
- // set ItemOnNode in pNodeL_
- pNodeL_->ItemOnNode = pNodeL_->ItemOnNode + pNodeL->ItemOnNode + 1;
- pNodeL->initialize();
- }
- else { //L is right of L_
- int j = pNodeL_->ItemOnNode + 1;
- pNodeL_->k[pNodeL_->ItemOnNode] = pPrimKey_;
- for(int i=0;i<pNodeL->ItemOnNode;i++) {
- pNodeL_->p[i+j] = pNodeL->p[i];
- pNodeL_->k[i+j] = pNodeL->k[i];
- }
- pNodeL_->p[i+j] = pNodeL->p[i];
- pNodeL_->ItemOnNode = pNodeL_->ItemOnNode + pNodeL->ItemOnNode + 1;
- pNodeL->initialize();
- }
- }
- else { // (pNodeL->IsLeaf == 1)
- if(IsLLeftOfL_) {
- int j = pNodeL->ItemOnNode;
- for(int i=0; i<pNodeL_->ItemOnNode; i++) {
- pNodeL->p[i+j] = pNodeL_->p[i];
- pNodeL->k[i+j] = pNodeL_->k[i];
- }
- pNodeL->ItemOnNode += pNodeL_->ItemOnNode;
- pNodeL->p[pNodeL->MaxItem] = pNodeL_->p[pNodeL_->MaxItem];
- pNodeL_->initialize();
- }
- else { // L is right of L_
- int j = pNodeL_->ItemOnNode;
- for(int i=0; i<pNodeL->ItemOnNode; i++) {
- pNodeL_->p[i+j] = pNodeL->p[i];
- pNodeL_->k[i+j] = pNodeL->k[i];
- }
- pNodeL_->ItemOnNode += pNodeL->ItemOnNode;
- pNodeL_->p[pNodeL_->MaxItem] = pNodeL->p[pNodeL->MaxItem];
- pNodeL->initialize();
- }
- }
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////////////
- //this method swaps the pointers to node L and L_
- void BPTree::swapVariables(_F_FileAddr L, _F_FileAddr L_) {
- BPTreeNode ParentNode;
- ParentNode.readNodeFromFile(getParent(L));
- int m,n;
- // find the indexes of L and L_
- for(int i=0; i <= ParentNode.ItemOnNode; i++) {
- if( ParentNode.p[i] == L )
- m = i;
- if( ParentNode.p[i] == L_ )
- n = i;
- }
- // swap
- _F_FileAddr temp;
- temp = ParentNode.p[m];
- ParentNode.p[m] = ParentNode.p[n];
- ParentNode.p[n] = temp;
- ParentNode.writeNodeToFile(getParent(L));
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////////////
- //this method makes pL_ and ppPrimKey points the infomation that is a neighbour of L
- // and pIsLLeftOnL_ indicate whether L is left neighbour of L_ or not
- void BPTree::setNb(_F_FileAddr L, _F_FileAddr* pL_, pKey_Attr* ppPrimKey_, bool* pIsLLeftOfL_) {
- BPTreeNode ParentNode;
- ParentNode.readNodeFromFile(getParent(L));
- for(int i=0; i<=ParentNode.ItemOnNode; i++) {
- if( ParentNode.p[i] == L )
- break;
- }
- if( 0 == i ) { // L is the leftest son of the parent node
- (*pL_) = ParentNode.p[1];
- (*ppPrimKey_) = ParentNode.createKey(ParentNode.k[0]);
- (*pIsLLeftOfL_) = true; // L is on the left of L_
- }
- else {
- (*pL_) = ParentNode.p[i-1];
- (*ppPrimKey_) = ParentNode.createKey(ParentNode.k[i-1]);
- (*pIsLLeftOfL_) = false;
- }
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////////////
- //this method replaces the key equal to Key_ with Key in the node pointed by ptr
- //--
- void BPTree::replaceKey(_F_FileAddr ptr, pKey_Attr Key_, pKey_Attr Key) {
- BPTreeNode Node;
- Node.readNodeFromFile(ptr);
- for(int i=0; i<Node.ItemOnNode; i++) {
- if( 0 == Node.compare(Node.k[i], Key_) )
- break;
- }
- Node.deleteKeySpace(Node.k[i]);
- Node.k[i] = Key;
- Node.writeNodeToFile(ptr);
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree::reDistribute(BPTreeNode* pNodeL, BPTreeNode* pNodeL_, pKey_Attr pPrimKey_,
- bool IsLLeftOfL_, _F_FileAddr L) {
- int m;
- if( !IsLLeftOfL_ ) {
- if( !pNodeL->IsLeaf ) {
- m = pNodeL_->ItemOnNode;
- // move all k[i] and p[i] in L to right by one
- pNodeL->p[pNodeL->ItemOnNode+1] = pNodeL->p[pNodeL->ItemOnNode];
- for(int i=pNodeL->ItemOnNode-1; i>=0; i--) {
- pNodeL->k[i+1] = pNodeL->k[i];
- pNodeL->p[i+1] = pNodeL->p[i];
- }
- pNodeL->k[0] = pPrimKey_;
- pNodeL->p[0] = pNodeL_->p[m];
- pNodeL->ItemOnNode++;
- //replace K_ in parent of L by k[m-1]
- replaceKey(getParent(L), pPrimKey_, pNodeL_->k[m-1]);
- //remove k[m-1] and p[m] from L_
- pNodeL_->k[m-1] = NULL;
- pNodeL_->p[m].ulFilePageID = 0;
- pNodeL_->p[m].uiOffset = 0;
- pNodeL_->ItemOnNode--;
- }
- else { //(pNodeL->IsLeaf == 1)
- m = pNodeL_->ItemOnNode - 1;
- // move all k[i] and p[i] in L to right by one
- for(int i=pNodeL->ItemOnNode-1; i>=0; i--) {
- pNodeL->k[i+1] = pNodeL->k[i];
- pNodeL->p[i+1] = pNodeL->p[i];
- }
- pNodeL->k[0] = pNodeL_->k[m];
- pNodeL->p[0] = pNodeL_->p[m];
- pNodeL->ItemOnNode++;
- //replace K_ in parent of L by k[m]
- pKey_Attr temp = pNodeL_->createKey(pNodeL_->k[m]);
- replaceKey(getParent(L), pPrimKey_, temp);
- pNodeL->deleteKeySpace(pPrimKey_);
- //remove p[m] and k[m] from L_
- pNodeL_->k[m] = NULL;
- pNodeL_->p[m].ulFilePageID = 0;
- pNodeL_->p[m].uiOffset = 0;
- pNodeL_->ItemOnNode--;
- }
- }
- else { //(IsLLeftOfL_)
- if( !pNodeL->IsLeaf ) {
- pNodeL->k[pNodeL->ItemOnNode] = pPrimKey_;
- pNodeL->p[pNodeL->ItemOnNode + 1] = pNodeL_->p[0];
- pNodeL->ItemOnNode++;
- replaceKey(getParent(L), pPrimKey_, pNodeL_->k[0]);
- // move pNodeL_ to the left by one
- for(int i=1; i<pNodeL_->ItemOnNode; i++) {
- pNodeL_->k[i-1] = pNodeL_->k[i];
- pNodeL_->p[i-1] = pNodeL_->p[i];
- }
- pNodeL_->p[i-1] = pNodeL_->p[i];
- pNodeL_->k[pNodeL_->ItemOnNode-1] = NULL;
- pNodeL_->p[pNodeL_->ItemOnNode].ulFilePageID = 0;
- pNodeL_->p[pNodeL_->ItemOnNode].uiOffset = 0;
- pNodeL_->ItemOnNode--;
- }
- else { //(pNodeL->IsLeaf)
- pNodeL->k[pNodeL->ItemOnNode] = pNodeL_->k[0];
- pNodeL->p[pNodeL->ItemOnNode] = pNodeL_->p[0];
- pNodeL->ItemOnNode++;
- for(int i=1; i<pNodeL_->ItemOnNode; i++) {
- pNodeL_->k[i-1] = pNodeL_->k[i];
- pNodeL_->p[i-1] = pNodeL_->p[i];
- }
- pNodeL_->k[pNodeL_->ItemOnNode-1] = NULL;
- pNodeL_->p[pNodeL_->ItemOnNode-1].ulFilePageID = 0;
- pNodeL_->p[pNodeL_->ItemOnNode-1].uiOffset = 0;
- pNodeL_->ItemOnNode--;
- pKey_Attr temp = pNodeL_->createKey(pNodeL_->k[0]);
- replaceKey(getParent(L), pPrimKey_, temp);
- pNodeL->deleteKeySpace(pPrimKey_);
- }
- }
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree::myDelete(pKey_Attr pPrimKey, _F_FileAddr& pRec) {
- setPath();
- Key_Location KeyLoca;
- if(search(pPrimKey, &KeyLoca)) {
- pRec = getCurRecAddr(KeyLoca);
- delete_entry(KeyLoca.ptr, pPrimKey, pRec);
- }
- else
- throw 1023;
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////////////
- void BPTree::delete_entry(_F_FileAddr L, pKey_Attr pPrimKey, _F_FileAddr pRec) {
- BPTreeNode NodeL;
- NodeL.readNodeFromFile(L);
- // delete the (V,P) entry
- if( 1 == NodeL.IsLeaf )
- NodeL.deleteKeyInLeaf(pPrimKey);
- else
- NodeL.deleteKeyNotLeaf(pPrimKey);
- // L is root and has only one son and not a leaf
- if( isRoot(L) && ( 0 == NodeL.ItemOnNode ) && (0 == NodeL.IsLeaf) ) {
- grantRoot(NodeL.p[0]); // grant root to the son
- deleteNodeInFile(L); // delete node
- }
- else
- if( !isRoot(L) && NodeL.isNotEnoughPoints() ) {// isn't root and not enough points
- //set L_ neighbour of L
- bool IsLLeftOfL_;
- _F_FileAddr L_;
- pKey_Attr pPrimKey_;
- setNb(L, &L_, &pPrimKey_, &IsLLeftOfL_);
- BPTreeNode NodeL_;
- NodeL_.readNodeFromFile(L_);
- if( canCoalesce(&NodeL, &NodeL_)) {
- if(IsLLeftOfL_)
- swapVariables(L,L_);
- coalesce(&NodeL, &NodeL_, pPrimKey_, IsLLeftOfL_);
- if( NodeL.IsLeaf && IsLLeftOfL_ ) // differe from book
- swapVariables(L,L_);
- delete_entry(getParent(L), pPrimKey_, L);
- if( NodeL.IsLeaf && IsLLeftOfL_ ) // L is a leaf and L < L_. Different from the book
- deleteNodeInFile(L_); // delete the node pointed by L_
- else
- deleteNodeInFile(L); // delete the node pointed by L
- }
- else
- reDistribute(&NodeL, &NodeL_, pPrimKey_, IsLLeftOfL_, L);
- NodeL_.writeNodeToFile(L_);
- }
- NodeL.writeNodeToFile(L); // if though the node is delete
- }
- ///////////////////////////////////////////////////////////////////////////////////////////////////////////