hashfile/src/hash_file.c
HT_ErrorCode HT_DeleteEntry(int indexDesc, int id) {
    char *data;
    BF_Block *block;
    BF_Block_Init(&block);

    int no_of_buckets = table[indexDesc];
    if(no_of_buckets == 0)
        return HT_OK;
    int bucket_position = hash(id, no_of_buckets);

    CALL_BF(BF_GetBlock(indexDesc, bucket_position, block));
    data = BF_Block_GetData(block);
    int records;
    int next_block;
    memcpy(&records, data, sizeof(int));
    memcpy(&next_block, data+sizeof(int), sizeof(int));

    if(records <= 0){
            printf("Error: bucket has 0 records.\n");
        return HT_ERROR;
    }

    Record *record = (Record*)malloc(sizeof(Record));
    Record *replacer_record = (Record*)malloc(sizeof(Record));

    int flag = 0;
    while( flag == 0 ){
        if(records <= 0){
		    break;
	    }
    	for(int i = 0; i < records; i++){
		    memcpy(record, data+sizeof(int)*2+sizeof(Record)*i, sizeof(Record));
		    if (record->id == id) {
			// We found the record to delete.
			    if (records == 1){
				// If we only have one record, meaning there is no other to replace it, simply decrease the number of records in the block.
				    records--;
				    memcpy(data, &records, sizeof(int));
			    } else {
				// Else, we need to find the last record in the bucket, remove that and place it in the record's position.
				    Record *replacer_record = (Record*)malloc(sizeof(Record));

				    char *data2;
				    BF_Block *block2;
				    BF_Block_Init(&block2);

				    CALL_BF(BF_GetBlock(indexDesc, bucket_position, block2));
				    data2 = BF_Block_GetData(block2);
				    int this_records;
				    int this_block;
				    int previous_block = bucket_position;
				    memcpy(&this_records, data2, sizeof(int));
				    memcpy(&this_block, data2+sizeof(int), sizeof(int));
				
				    while(this_block != 0 && this_records == MAX_RECORDS) {
					    previous_block = this_block;
					    CALL_BF(BF_UnpinBlock(block2));
					    CALL_BF(BF_GetBlock(indexDesc, this_block, block2));
					    data2 = BF_Block_GetData(block2);
					    memcpy(&this_records, data2, sizeof(int));
					    memcpy(&this_block, data2+sizeof(int), sizeof(int));
				    }
				    if(this_records <= 0){
					    CALL_BF(BF_UnpinBlock(block2));
					    CALL_BF(BF_GetBlock(indexDesc, previous_block, block2));
					    data2 = BF_Block_GetData(block2);
					    memcpy(&this_records, data2, sizeof(int));
					    memcpy(&this_block, data2+sizeof(int), sizeof(int));
				    }
				    memcpy(replacer_record, data2+sizeof(int)*2+sizeof(Record)*(this_records-1), sizeof(Record));
				    this_records--;
				    memcpy(data2, &this_records, sizeof(int));
				    BF_Block_SetDirty(block2);
				    CALL_BF(BF_UnpinBlock(block2));
				    BF_Block_Destroy(&block2);

				    // We now have the last record in replacer_record.
				    memcpy(data+sizeof(int)*2+sizeof(Record)*i, replacer_record, sizeof(Record));
			    }
			    // In both cases, we altered the block.
			    BF_Block_SetDirty(block);
			    CALL_BF(BF_UnpinBlock(block));
			    BF_Block_Destroy(&block);
			    flag = 1;
		    }
		if(flag == 1){
			// Job is done.
			free(record);
			free(replacer_record);
			return HT_OK;
			break;
		}
	}
	if(next_block != 0){
		CALL_BF(BF_UnpinBlock(block));
		CALL_BF(BF_GetBlock(indexDesc, next_block, block));
		data = BF_Block_GetData(block);
		memcpy(&records, data, sizeof(int));
		memcpy(&next_block, data+sizeof(int), sizeof(int));
	} else {
		CALL_BF(BF_UnpinBlock(block));
		BF_Block_Destroy(&block);
		printf("Error: The id %d, could not be found\n", id);
		return HT_OK;
	}
	
    }
    return HT_OK;
}
/**
 * DeleteEntry works like this:
 *  - First we find the record position of the id we want to delete.
 *  -- If there is only one record in the block, meaning the last record of the bucket, just decrement the record number in the block.
 *  -- If there are more records in the bucket, then we find the last record, put it in the variable replacer_record, delete it and place it in the position of the record that we want to delete.
 *  If we don't find the id then we return HT_ERROR.
 */
DeleteEntry works like this:
- First we find the record position of the id we want to delete.
If there is only one record in the block, meaning the last record of the bucket, just decrement the record number in the block.
If there are more records in the bucket, then we find the last record, put it in the variable replacer_record, delete it and place it in the position of the record that we want to delete.
If we don't find the id then we return HT_ERROR.
DeleteEntry works like this : - First we find the record position of the id we want to delete . If there is only one record in the block meaning the last record of the bucket just decrement the record number in the block . If there are more records in the bucket then we find the last record put it in the variable replacer_record delete it and place it in the position of the record that we want to delete . If we don ' t find the id then we return HT_ERROR .
HT_ErrorCode HT_DeleteEntry(int indexDesc, int id) {
    char *data;
    BF_Block *block;
    BF_Block_Init(&block);
    int no_of_buckets = table[indexDesc];
    if(no_of_buckets == 0)
        return HT_OK;
    int bucket_position = hash(id, no_of_buckets);
    CALL_BF(BF_GetBlock(indexDesc, bucket_position, block));
    data = BF_Block_GetData(block);
    int records;
    int next_block;
    memcpy(&records, data, sizeof(int));
    memcpy(&next_block, data+sizeof(int), sizeof(int));
    if(records <= 0){
            printf("Error: bucket has 0 records.\n");
        return HT_ERROR;
    }
    Record *record = (Record*)malloc(sizeof(Record));
    Record *replacer_record = (Record*)malloc(sizeof(Record));
    int flag = 0;
    while( flag == 0 ){
        if(records <= 0){
		    break;
	    }
    	for(int i = 0; i < records; i++){
		    memcpy(record, data+sizeof(int)*2+sizeof(Record)*i, sizeof(Record));
		    if (record->id == id) {
			    if (records == 1){
				    records--;
				    memcpy(data, &records, sizeof(int));
			    } else {
				    Record *replacer_record = (Record*)malloc(sizeof(Record));
				    char *data2;
				    BF_Block *block2;
				    BF_Block_Init(&block2);
				    CALL_BF(BF_GetBlock(indexDesc, bucket_position, block2));
				    data2 = BF_Block_GetData(block2);
				    int this_records;
				    int this_block;
				    int previous_block = bucket_position;
				    memcpy(&this_records, data2, sizeof(int));
				    memcpy(&this_block, data2+sizeof(int), sizeof(int));
				    while(this_block != 0 && this_records == MAX_RECORDS) {
					    previous_block = this_block;
					    CALL_BF(BF_UnpinBlock(block2));
					    CALL_BF(BF_GetBlock(indexDesc, this_block, block2));
					    data2 = BF_Block_GetData(block2);
					    memcpy(&this_records, data2, sizeof(int));
					    memcpy(&this_block, data2+sizeof(int), sizeof(int));
				    }
				    if(this_records <= 0){
					    CALL_BF(BF_UnpinBlock(block2));
					    CALL_BF(BF_GetBlock(indexDesc, previous_block, block2));
					    data2 = BF_Block_GetData(block2);
					    memcpy(&this_records, data2, sizeof(int));
					    memcpy(&this_block, data2+sizeof(int), sizeof(int));
				    }
				    memcpy(replacer_record, data2+sizeof(int)*2+sizeof(Record)*(this_records-1), sizeof(Record));
				    this_records--;
				    memcpy(data2, &this_records, sizeof(int));
				    BF_Block_SetDirty(block2);
				    CALL_BF(BF_UnpinBlock(block2));
				    BF_Block_Destroy(&block2);
				    memcpy(data+sizeof(int)*2+sizeof(Record)*i, replacer_record, sizeof(Record));
			    }
			    BF_Block_SetDirty(block);
			    CALL_BF(BF_UnpinBlock(block));
			    BF_Block_Destroy(&block);
			    flag = 1;
		    }
		if(flag == 1){
			free(record);
			free(replacer_record);
			return HT_OK;
			break;
		}
	}
	if(next_block != 0){
		CALL_BF(BF_UnpinBlock(block));
		CALL_BF(BF_GetBlock(indexDesc, next_block, block));
		data = BF_Block_GetData(block);
		memcpy(&records, data, sizeof(int));
		memcpy(&next_block, data+sizeof(int), sizeof(int));
	} else {
		CALL_BF(BF_UnpinBlock(block));
		BF_Block_Destroy(&block);
		printf("Error: The id %d, could not be found\n", id);
		return HT_OK;
	}
    }
    return HT_OK;
}
HT_ErrorCode HT_DeleteEntry ( int indexDesc , int id ) { char * data ; BF_Block * block ; BF_Block_Init ( & block ) ; int no_of_buckets = table [ indexDesc ] ; if ( no_of_buckets == 0 ) return HT_OK ; int bucket_position = hash ( id , no_of_buckets ) ; CALL_BF ( BF_GetBlock ( indexDesc , bucket_position , block ) ) ; data = BF_Block_GetData ( block ) ; int records ; int next_block ; memcpy ( & records , data , sizeof ( int ) ) ; memcpy ( & next_block , data + sizeof ( int ) , sizeof ( int ) ) ; if ( records <= 0 ) { printf ( " \n " ) ; return HT_ERROR ; } Record * record = ( Record * ) malloc ( sizeof ( Record ) ) ; Record * replacer_record = ( Record * ) malloc ( sizeof ( Record ) ) ; int flag = 0 ; while ( flag == 0 ) { if ( records <= 0 ) { break ; } for ( int i = 0 ; i < records ; i ++ ) { memcpy ( record , data + sizeof ( int ) * 2 + sizeof ( Record ) * i , sizeof ( Record ) ) ; if ( record -> id == id ) { if ( records == 1 ) { records -- ; memcpy ( data , & records , sizeof ( int ) ) ; } else { Record * replacer_record = ( Record * ) malloc ( sizeof ( Record ) ) ; char * data2 ; BF_Block * block2 ; BF_Block_Init ( & block2 ) ; CALL_BF ( BF_GetBlock ( indexDesc , bucket_position , block2 ) ) ; data2 = BF_Block_GetData ( block2 ) ; int this_records ; int this_block ; int previous_block = bucket_position ; memcpy ( & this_records , data2 , sizeof ( int ) ) ; memcpy ( & this_block , data2 + sizeof ( int ) , sizeof ( int ) ) ; while ( this_block != 0 && this_records == MAX_RECORDS ) { previous_block = this_block ; CALL_BF ( BF_UnpinBlock ( block2 ) ) ; CALL_BF ( BF_GetBlock ( indexDesc , this_block , block2 ) ) ; data2 = BF_Block_GetData ( block2 ) ; memcpy ( & this_records , data2 , sizeof ( int ) ) ; memcpy ( & this_block , data2 + sizeof ( int ) , sizeof ( int ) ) ; } if ( this_records <= 0 ) { CALL_BF ( BF_UnpinBlock ( block2 ) ) ; CALL_BF ( BF_GetBlock ( indexDesc , previous_block , block2 ) ) ; data2 = BF_Block_GetData ( block2 ) ; memcpy ( & this_records , data2 , sizeof ( int ) ) ; memcpy ( & this_block , data2 + sizeof ( int ) , sizeof ( int ) ) ; } memcpy ( replacer_record , data2 + sizeof ( int ) * 2 + sizeof ( Record ) * ( this_records - 1 ) , sizeof ( Record ) ) ; this_records -- ; memcpy ( data2 , & this_records , sizeof ( int ) ) ; BF_Block_SetDirty ( block2 ) ; CALL_BF ( BF_UnpinBlock ( block2 ) ) ; BF_Block_Destroy ( & block2 ) ; memcpy ( data + sizeof ( int ) * 2 + sizeof ( Record ) * i , replacer_record , sizeof ( Record ) ) ; } BF_Block_SetDirty ( block ) ; CALL_BF ( BF_UnpinBlock ( block ) ) ; BF_Block_Destroy ( & block ) ; flag = 1 ; } if ( flag == 1 ) { free ( record ) ; free ( replacer_record ) ; return HT_OK ; break ; } } if ( next_block != 0 ) { CALL_BF ( BF_UnpinBlock ( block ) ) ; CALL_BF ( BF_GetBlock ( indexDesc , next_block , block ) ) ; data = BF_Block_GetData ( block ) ; memcpy ( & records , data , sizeof ( int ) ) ; memcpy ( & next_block , data + sizeof ( int ) , sizeof ( int ) ) ; } else { CALL_BF ( BF_UnpinBlock ( block ) ) ; BF_Block_Destroy ( & block ) ; printf ( " \n " , id ) ; return HT_OK ; } } return HT_OK ; }
DeleteEntry works like this:
  - First we find the record position of the id we want to delete.
DeleteEntry works like this : - First we find the record position of the id we want to delete .
// We found the record to delete. // If we only have one record, meaning there is no other to replace it, simply decrease the number of records in the block. // Else, we need to find the last record in the bucket, remove that and place it in the record's position. // We now have the last record in replacer_record. // In both cases, we altered the block. // Job is done.