Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
I
ISC_144 - B+ Tree Project
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Releases
Package registry
Model registry
Operate
Environments
Terraform modules
Monitor
Incidents
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
This is an archived project. Repository and other project resources are read-only.
Show more breadcrumbs
florian.burgener
ISC_144 - B+ Tree Project
Commits
9df79d44
Commit
9df79d44
authored
2 years ago
by
Florian Burgener
Browse files
Options
Downloads
Patches
Plain Diff
Huge refactoring
parent
c0240b1a
Branches
Branches containing commit
No related tags found
No related merge requests found
Changes
5
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
main.c
+157
-0
157 additions, 0 deletions
main.c
src/BPTree.c
+95
-115
95 additions, 115 deletions
src/BPTree.c
src/BPTree.h
+1
-1
1 addition, 1 deletion
src/BPTree.h
src/main.c
+42
-143
42 additions, 143 deletions
src/main.c
src/tests/BPTreeTests.c
+44
-43
44 additions, 43 deletions
src/tests/BPTreeTests.c
with
339 additions
and
302 deletions
main.c
0 → 100644
+
157
−
0
View file @
9df79d44
#include
<stdio.h>
#include
<stdlib.h>
#include
"Directory.h"
#include
"DirectoryRecord.h"
void
clear_buffer
()
{
int
c
;
while
((
c
=
getchar
())
!=
'\n'
&&
c
!=
EOF
)
{
}
}
void
append_record
(
Directory
*
directory
)
{
char
phone_number
[
PHONE_NUMBER_MAXLEN
];
printf
(
"Enter the phone number: "
);
scanf
(
"%10s"
,
phone_number
);
clear_buffer
();
char
name
[
NAME_MAXLEN
];
printf
(
"Enter the name: "
);
scanf
(
"%20s"
,
name
);
clear_buffer
();
char
surname
[
SURNAME_MAXLEN
];
printf
(
"Enter the surname: "
);
scanf
(
"%20s"
,
surname
);
clear_buffer
();
int
birth_date_year
,
birth_date_month
,
birth_date_day
;
do
{
printf
(
"Enter the birth date (Y-m-d): "
);
}
while
(
scanf
(
"%d-%d-%d"
,
&
birth_date_year
,
&
birth_date_month
,
&
birth_date_day
)
!=
3
);
clear_buffer
();
printf
(
"
\n
Is the information entered correct? (Y/n) "
);
char
choice
=
getchar
();
if
(
choice
!=
'\n'
)
{
getchar
();
}
if
(
choice
==
'n'
)
{
printf
(
"
\n
===>The procedure has been cancelled.
\n
"
);
}
else
{
DirectoryRecord
*
record
=
DirectoryRecord_init
(
false
,
phone_number
,
name
,
surname
,
birth_date_year
,
birth_date_month
,
birth_date_day
);
if
(
Directory_append
(
directory
,
record
))
{
printf
(
"
\n
===>The record has been saved in the directory.
\n
"
);
}
else
{
printf
(
"
\n
===>This phone number is already associated with a record. The record has not been saved.
\n
"
);
}
DirectoryRecord_destroy
(
&
record
);
}
}
void
search_record
(
Directory
*
directory
)
{
printf
(
"Enter the phone number that corresponds to the record you are looking for: "
);
char
phone_number
[
PHONE_NUMBER_MAXLEN
];
scanf
(
"%10s"
,
phone_number
);
clear_buffer
();
DirectoryRecord
*
record
=
Directory_search
(
directory
,
phone_number
);
printf
(
"
\n
"
);
if
(
record
==
NULL
)
{
printf
(
"===>No records were found for this phone number.
\n
"
);
}
else
{
printf
(
"========================
\n
"
);
DirectoryRecord_print
(
record
);
DirectoryRecord_destroy
(
&
record
);
printf
(
"========================
\n
"
);
}
}
void
delete_record
(
Directory
*
directory
)
{
printf
(
"Enter the phone number that corresponds to the record you wish to delete: "
);
char
phone_number
[
PHONE_NUMBER_MAXLEN
];
scanf
(
"%10s"
,
phone_number
);
clear_buffer
();
DirectoryRecord
*
record
=
Directory_search
(
directory
,
phone_number
);
printf
(
"
\n
"
);
if
(
record
==
NULL
)
{
printf
(
"===>No records were found for this phone number.
\n
"
);
}
else
{
printf
(
"========================
\n
"
);
DirectoryRecord_print
(
record
);
DirectoryRecord_destroy
(
&
record
);
printf
(
"========================
\n
"
);
printf
(
"
\n
Are you sure you want to delete this record? (Y/n) "
);
char
choice
=
getchar
();
if
(
choice
!=
'\n'
)
{
getchar
();
}
if
(
choice
==
'n'
)
{
printf
(
"
\n
===>The procedure has been cancelled.
\n
"
);
}
else
{
Directory_delete
(
directory
,
phone_number
);
printf
(
"Delete done
\n
"
);
}
}
}
int
main
()
{
Directory
*
directory
=
Directory_init
(
"directory_database"
);
while
(
true
)
{
BPTree_print
(
directory
->
index
,
0
);
printf
(
"Enter 1 to add a member.
\n
"
);
printf
(
"Enter 2 to search for a member via their phone number.
\n
"
);
printf
(
"Enter 3 to delete a member.
\n
"
);
printf
(
"Enter 4 to display all members.
\n
"
);
printf
(
"Enter 5 to exit the program.
\n
"
);
printf
(
"What do you want to do? "
);
int
action
;
scanf
(
"%d"
,
&
action
);
clear_buffer
();
if
(
action
<
1
||
action
>
5
)
{
system
(
"clear"
);
continue
;
}
if
(
action
==
5
)
{
break
;
}
printf
(
"
\n
"
);
switch
(
action
)
{
case
1
:
append_record
(
directory
);
break
;
case
2
:
search_record
(
directory
);
break
;
case
3
:
delete_record
(
directory
);
break
;
case
4
:
Directory_print
(
directory
);
break
;
}
printf
(
"
\n
Press enter to continue..."
);
getchar
();
system
(
"clear"
);
}
Directory_destroy
(
&
directory
);
return
EXIT_SUCCESS
;
}
This diff is collapsed.
Click to expand it.
src/BPTree.c
+
95
−
115
View file @
9df79d44
...
@@ -7,34 +7,19 @@
...
@@ -7,34 +7,19 @@
#include
"Array.h"
#include
"Array.h"
static
bool
has_maximum_keys
(
BPTreeNode
*
node
);
// BPTreeNode
static
BPTreeNode
*
find_leaf
(
BPTreeNode
*
root
,
uint64_t
key
,
BPTreeNodeArray
**
parents
);
static
bool
has_maximum_keys
(
BPTreeNode
*
node
)
{
return
node
->
keys
->
size
==
2
*
node
->
order
;
}
static
BPTreeNode
*
find_leaf
(
BPTreeNode
*
root
,
uint64_t
key
,
BPTreeNodeArray
**
parents
)
{
BPTreeNode
*
current
=
root
;
// CAUTION : 10 is not enough.
*
parents
=
BPTreeNodeArray_init
(
10
);
while
(
!
current
->
is_leaf
)
{
BPTreeNodeArray_append
(
*
parents
,
current
);
int
child_index
=
lower_bound
(
current
->
keys
,
key
);
if
(
child_index
<
current
->
keys
->
size
&&
current
->
keys
->
items
[
child_index
]
==
key
)
{
child_index
+=
1
;
}
current
=
current
->
children
->
items
[
child_index
];
}
return
current
;
static
BPTreeNode
*
BPTreeNode_init
(
int
order
,
bool
is_leaf
)
{
BPTreeNode
*
root
=
(
BPTreeNode
*
)
malloc
(
sizeof
(
BPTreeNode
));
root
->
order
=
order
;
root
->
is_leaf
=
is_leaf
;
root
->
keys
=
IntegerArray_init
(
2
*
root
->
order
);
root
->
data
=
IntegerArray_init
(
2
*
root
->
order
);
root
->
children
=
BPTreeNodeArray_init
(
2
*
root
->
order
+
1
);
root
->
next
=
NULL
;
return
root
;
}
}
// BPTreeNode
static
void
BPTreeNode_destroy
(
BPTreeNode
**
node
)
{
static
void
BPTreeNode_destroy
(
BPTreeNode
**
node
)
{
IntegerArray_destroy
(
&
(
*
node
)
->
keys
);
IntegerArray_destroy
(
&
(
*
node
)
->
keys
);
IntegerArray_destroy
(
&
(
*
node
)
->
data
);
IntegerArray_destroy
(
&
(
*
node
)
->
data
);
...
@@ -46,14 +31,7 @@ static void BPTreeNode_destroy(BPTreeNode **node) {
...
@@ -46,14 +31,7 @@ static void BPTreeNode_destroy(BPTreeNode **node) {
// BPTree
// BPTree
BPTreeNode
*
BPTree_init
(
int
order
)
{
BPTreeNode
*
BPTree_init
(
int
order
)
{
BPTreeNode
*
root
=
(
BPTreeNode
*
)
malloc
(
sizeof
(
BPTreeNode
));
return
BPTreeNode_init
(
order
,
true
);
root
->
order
=
order
;
root
->
is_leaf
=
true
;
root
->
keys
=
IntegerArray_init
(
2
*
root
->
order
);
root
->
data
=
IntegerArray_init
(
2
*
root
->
order
);
root
->
children
=
BPTreeNodeArray_init
(
2
*
root
->
order
+
1
);
root
->
next
=
NULL
;
return
root
;
}
}
void
BPTree_destroy
(
BPTreeNode
**
root
)
{
void
BPTree_destroy
(
BPTreeNode
**
root
)
{
...
@@ -102,6 +80,18 @@ bool BPTree_search(BPTreeNode *root, uint64_t key, uint64_t *data) {
...
@@ -102,6 +80,18 @@ bool BPTree_search(BPTreeNode *root, uint64_t key, uint64_t *data) {
return
BPTree_search
(
root
->
children
->
items
[
child_index
],
key
,
data
);
return
BPTree_search
(
root
->
children
->
items
[
child_index
],
key
,
data
);
}
}
// "traverse" function for insertion and deletion.
static
BPTreeNode
*
traverse
(
BPTreeNode
*
node
,
uint64_t
key
)
{
int
virtual_insertion_index
=
lower_bound
(
node
->
keys
,
key
);
if
(
virtual_insertion_index
<
node
->
keys
->
size
&&
node
->
keys
->
items
[
virtual_insertion_index
]
==
key
)
{
virtual_insertion_index
+=
1
;
}
return
node
->
children
->
items
[
virtual_insertion_index
];
}
// BPTree : Insertion
// BPTree : Insertion
static
void
insert_non_full
(
BPTreeNode
*
node
,
uint64_t
key
,
uint64_t
data
,
BPTreeNode
*
previous_split_right_node
)
{
static
void
insert_non_full
(
BPTreeNode
*
node
,
uint64_t
key
,
uint64_t
data
,
BPTreeNode
*
previous_split_right_node
)
{
...
@@ -119,47 +109,47 @@ static void insert_non_full(BPTreeNode *node, uint64_t key, uint64_t data, BPTre
...
@@ -119,47 +109,47 @@ static void insert_non_full(BPTreeNode *node, uint64_t key, uint64_t data, BPTre
static
void
redistribute_keys
(
BPTreeNode
*
left_node
,
BPTreeNode
*
right_node
,
int
left_index
,
int
right_index
)
{
static
void
redistribute_keys
(
BPTreeNode
*
left_node
,
BPTreeNode
*
right_node
,
int
left_index
,
int
right_index
)
{
for
(
int
i
=
right_index
;
i
<
left_node
->
keys
->
size
;
i
++
)
{
for
(
int
i
=
right_index
;
i
<
left_node
->
keys
->
size
;
i
++
)
{
IntegerArray_append
(
right_node
->
keys
,
left_node
->
keys
->
items
[
i
]);
IntegerArray_append
(
right_node
->
keys
,
left_node
->
keys
->
items
[
i
]);
if
(
left_node
->
is_leaf
)
{
IntegerArray_append
(
right_node
->
data
,
left_node
->
data
->
items
[
i
]);
}
}
}
left_node
->
keys
->
size
=
left_index
;
left_node
->
keys
->
size
=
left_index
;
if
(
left_node
->
is_leaf
)
{
for
(
int
i
=
right_index
;
i
<
left_node
->
data
->
size
;
i
++
)
{
IntegerArray_append
(
right_node
->
data
,
left_node
->
data
->
items
[
i
]);
}
if
(
left_node
->
data
->
size
>
0
)
{
left_node
->
data
->
size
=
left_index
;
left_node
->
data
->
size
=
left_index
;
}
}
}
}
static
uint64_t
split_leaf
(
BPTreeNode
*
node
,
uint64_t
key
,
uint64_t
data
,
BPTreeNode
**
right_node
)
{
static
uint64_t
split_leaf
(
BPTreeNode
*
node
,
uint64_t
key
,
uint64_t
data
,
BPTreeNode
**
split_
right_node
)
{
int
virtual_insertion_index
=
lower_bound
(
node
->
keys
,
key
);
int
virtual_insertion_index
=
lower_bound
(
node
->
keys
,
key
);
int
median_index
=
node
->
keys
->
size
/
2
;
int
median_index
=
node
->
keys
->
size
/
2
;
uint64_t
median_value
;
uint64_t
median_value
;
*
right_node
=
BPTree_init
(
node
->
order
);
*
split_
right_node
=
BPTree
Node
_init
(
node
->
order
,
true
);
if
(
virtual_insertion_index
<
median_index
)
{
if
(
virtual_insertion_index
<
median_index
)
{
median_value
=
node
->
keys
->
items
[
median_index
-
1
];
median_value
=
node
->
keys
->
items
[
median_index
-
1
];
redistribute_keys
(
node
,
*
right_node
,
median_index
-
1
,
median_index
-
1
);
redistribute_keys
(
node
,
*
split_
right_node
,
median_index
-
1
,
median_index
-
1
);
int
insertion_index
=
IntegerArray_insert_sorted
(
node
->
keys
,
key
);
int
insertion_index
=
IntegerArray_insert_sorted
(
node
->
keys
,
key
);
IntegerArray_insert_at_index
(
node
->
data
,
insertion_index
,
data
);
IntegerArray_insert_at_index
(
node
->
data
,
insertion_index
,
data
);
}
else
if
(
virtual_insertion_index
>
median_index
)
{
}
else
if
(
virtual_insertion_index
>
median_index
)
{
median_value
=
node
->
keys
->
items
[
median_index
];
median_value
=
node
->
keys
->
items
[
median_index
];
redistribute_keys
(
node
,
*
right_node
,
median_index
,
median_index
);
redistribute_keys
(
node
,
*
split_
right_node
,
median_index
,
median_index
);
int
insertion_index
=
IntegerArray_insert_sorted
((
*
right_node
)
->
keys
,
key
);
int
insertion_index
=
IntegerArray_insert_sorted
((
*
split_
right_node
)
->
keys
,
key
);
IntegerArray_insert_at_index
((
*
right_node
)
->
data
,
insertion_index
,
data
);
IntegerArray_insert_at_index
((
*
split_
right_node
)
->
data
,
insertion_index
,
data
);
}
else
{
}
else
{
median_value
=
key
;
median_value
=
key
;
redistribute_keys
(
node
,
*
right_node
,
median_index
,
median_index
);
redistribute_keys
(
node
,
*
split_
right_node
,
median_index
,
median_index
);
int
insertion_index
=
IntegerArray_insert_sorted
((
*
right_node
)
->
keys
,
key
);
int
insertion_index
=
IntegerArray_insert_sorted
((
*
split_
right_node
)
->
keys
,
key
);
IntegerArray_insert_at_index
((
*
right_node
)
->
data
,
insertion_index
,
data
);
IntegerArray_insert_at_index
((
*
split_
right_node
)
->
data
,
insertion_index
,
data
);
}
}
if
(
node
->
next
!=
NULL
)
{
if
(
node
->
next
!=
NULL
)
{
(
*
right_node
)
->
next
=
node
->
next
;
(
*
split_
right_node
)
->
next
=
node
->
next
;
}
}
node
->
next
=
*
right_node
;
node
->
next
=
*
split_
right_node
;
return
median_value
;
return
median_value
;
}
}
...
@@ -171,108 +161,98 @@ static void redistribute_children(BPTreeNode *left_node, BPTreeNode *right_node,
...
@@ -171,108 +161,98 @@ static void redistribute_children(BPTreeNode *left_node, BPTreeNode *right_node,
left_node
->
children
->
size
=
left_index
;
left_node
->
children
->
size
=
left_index
;
}
}
static
uint64_t
split_internal
(
BPTreeNode
*
node
,
uint64_t
key
,
BPTreeNode
*
right_child
_node
,
BPTreeNode
**
right_node
)
{
static
uint64_t
split_internal
(
BPTreeNode
*
node
,
uint64_t
key
,
BPTreeNode
*
previous_split_right
_node
,
BPTreeNode
**
split_
right_node
)
{
int
virtual_insertion_index
=
lower_bound
(
node
->
keys
,
key
);
int
virtual_insertion_index
=
lower_bound
(
node
->
keys
,
key
);
int
median_index
=
node
->
keys
->
size
/
2
;
int
median_index
=
node
->
keys
->
size
/
2
;
uint64_t
median_value
;
uint64_t
median_value
;
*
right_node
=
BPTree_init
(
node
->
order
);
*
split_right_node
=
BPTreeNode_init
(
node
->
order
,
false
);
(
*
right_node
)
->
is_leaf
=
false
;
if
(
virtual_insertion_index
<
median_index
)
{
if
(
virtual_insertion_index
<
median_index
)
{
median_value
=
node
->
keys
->
items
[
median_index
-
1
];
median_value
=
node
->
keys
->
items
[
median_index
-
1
];
redistribute_keys
(
node
,
*
right_node
,
median_index
-
1
,
median_index
);
redistribute_keys
(
node
,
*
split_
right_node
,
median_index
-
1
,
median_index
);
redistribute_children
(
node
,
*
right_node
,
median_index
,
median_index
);
redistribute_children
(
node
,
*
split_
right_node
,
median_index
,
median_index
);
int
insertion_index
=
IntegerArray_insert_sorted
(
node
->
keys
,
key
);
int
insertion_index
=
IntegerArray_insert_sorted
(
node
->
keys
,
key
);
BPTreeNodeArray_insert_at_index
(
node
->
children
,
insertion_index
+
1
,
right_child
_node
);
BPTreeNodeArray_insert_at_index
(
node
->
children
,
insertion_index
+
1
,
previous_split_right
_node
);
}
else
if
(
virtual_insertion_index
>
median_index
)
{
}
else
if
(
virtual_insertion_index
>
median_index
)
{
median_value
=
node
->
keys
->
items
[
median_index
];
median_value
=
node
->
keys
->
items
[
median_index
];
redistribute_keys
(
node
,
*
right_node
,
median_index
,
median_index
+
1
);
redistribute_keys
(
node
,
*
split_
right_node
,
median_index
,
median_index
+
1
);
redistribute_children
(
node
,
*
right_node
,
median_index
+
1
,
median_index
+
1
);
redistribute_children
(
node
,
*
split_
right_node
,
median_index
+
1
,
median_index
+
1
);
int
insertion_index
=
IntegerArray_insert_sorted
((
*
right_node
)
->
keys
,
key
);
int
insertion_index
=
IntegerArray_insert_sorted
((
*
split_
right_node
)
->
keys
,
key
);
BPTreeNodeArray_insert_at_index
((
*
right_node
)
->
children
,
insertion_index
+
1
,
right_child
_node
);
BPTreeNodeArray_insert_at_index
((
*
split_
right_node
)
->
children
,
insertion_index
+
1
,
previous_split_right
_node
);
}
else
{
}
else
{
median_value
=
key
;
median_value
=
key
;
redistribute_keys
(
node
,
*
right_node
,
median_index
,
median_index
);
redistribute_keys
(
node
,
*
split_
right_node
,
median_index
,
median_index
);
redistribute_children
(
node
,
*
right_node
,
median_index
+
1
,
median_index
+
1
);
redistribute_children
(
node
,
*
split_
right_node
,
median_index
+
1
,
median_index
+
1
);
BPTreeNodeArray_insert_at_index
((
*
right_node
)
->
children
,
0
,
right_child
_node
);
BPTreeNodeArray_insert_at_index
((
*
split_
right_node
)
->
children
,
0
,
previous_split_right
_node
);
}
}
return
median_value
;
return
median_value
;
}
}
static
uint64_t
insert_full
(
BPTreeNode
*
node
,
uint64_t
key
,
uint64_t
data
,
BPTreeNode
*
previous_split_right_node
,
BPTreeNode
**
split_right_node
)
{
if
(
node
->
is_leaf
)
{
return
split_leaf
(
node
,
key
,
data
,
split_right_node
);
}
return
split_internal
(
node
,
key
,
previous_split_right_node
,
split_right_node
);
}
static
void
grow
(
BPTreeNode
*
root
,
uint64_t
median_value
,
BPTreeNode
*
split_right_node
)
{
static
void
grow
(
BPTreeNode
*
root
,
uint64_t
median_value
,
BPTreeNode
*
split_right_node
)
{
BPTreeNode
*
left_node
=
BPTree_init
(
root
->
order
);
BPTreeNode
*
left_node
=
BPTreeNode_init
(
root
->
order
,
split_right_node
->
is_leaf
);
left_node
->
is_leaf
=
split_right_node
->
is_leaf
;
root
->
is_leaf
=
false
;
root
->
is_leaf
=
false
;
IntegerArray_copy
(
root
->
keys
,
left_node
->
keys
);
IntegerArray_copy
(
root
->
keys
,
left_node
->
keys
);
IntegerArray_clear
(
root
->
keys
);
IntegerArray_append
(
root
->
keys
,
median_value
);
IntegerArray_copy
(
root
->
data
,
left_node
->
data
);
IntegerArray_copy
(
root
->
data
,
left_node
->
data
);
IntegerArray_clear
(
root
->
data
);
BPTreeNodeArray_copy
(
root
->
children
,
left_node
->
children
);
BPTreeNodeArray_copy
(
root
->
children
,
left_node
->
children
);
IntegerArray_clear
(
root
->
keys
);
IntegerArray_clear
(
root
->
data
);
BPTreeNodeArray_clear
(
root
->
children
);
BPTreeNodeArray_clear
(
root
->
children
);
IntegerArray_append
(
root
->
keys
,
median_value
);
BPTreeNodeArray_append
(
root
->
children
,
left_node
);
BPTreeNodeArray_append
(
root
->
children
,
left_node
);
BPTreeNodeArray_append
(
root
->
children
,
split_right_node
);
BPTreeNodeArray_append
(
root
->
children
,
split_right_node
);
}
}
static
void
insert_full
(
BPTreeNode
*
root
,
BPTreeNodeArray
*
parents
,
BPTreeNode
*
node
,
uint64_t
key
,
uint64_t
data
,
BPTreeNode
*
previous_split_right_node
)
{
static
bool
_BPTree_insert
(
BPTreeNode
*
parent
,
BPTreeNode
*
root
,
uint64_t
*
key
,
uint64_t
data
,
BPTreeNode
**
split_right_node
)
{
uint64_t
median_value
;
BPTreeNode
*
previous_split_right_node
=
NULL
;
BPTreeNode
*
split_right_node
;
if
(
!
root
->
is_leaf
&&
!
_BPTree_insert
(
root
,
traverse
(
root
,
*
key
),
key
,
data
,
&
previous_split_right_node
))
{
return
false
;
}
i
f
(
node
->
is_leaf
)
{
i
nt
index
;
median_value
=
split_leaf
(
node
,
key
,
data
,
&
split_right_no
de
);
bool
is_found
=
IntegerArray_binary_search
(
root
->
keys
,
*
key
,
&
in
de
x
);
}
else
{
if
(
root
->
is_leaf
&&
is_found
)
{
median_value
=
split_internal
(
node
,
key
,
previous_split_right_node
,
&
split_right_node
)
;
return
false
;
}
}
if
(
node
==
root
)
{
if
(
!
root
->
is_leaf
&&
previous_split_right_
node
==
NULL
)
{
grow
(
root
,
median_value
,
split_right_node
)
;
*
split_right_node
=
NULL
;
}
else
{
return
true
;
BPTreeNode
*
parent
=
BPTreeNodeArray_pop
(
parents
);
}
if
(
has_maximum_keys
(
parent
))
{
if
(
root
->
keys
->
size
<
2
*
root
->
order
)
{
// 0 is passed instead of data because the recursion is necessarily done on an internal node.
insert_non_full
(
root
,
*
key
,
data
,
previous_split_right_node
);
insert_full
(
root
,
parents
,
parent
,
median_value
,
0
,
split_right_node
);
*
split_right_node
=
NULL
;
}
else
{
return
true
;
insert_non_full
(
parent
,
median_value
,
data
,
split_right_node
);
}
}
}
}
void
BPTree_insert
(
BPTreeNode
*
root
,
uint64_t
key
,
uint64_t
data
)
{
*
key
=
insert_full
(
root
,
*
key
,
data
,
previous_split_right_node
,
split_right_node
);
BPTreeNodeArray
*
parents
;
BPTreeNode
*
leaf
=
find_leaf
(
root
,
key
,
&
parents
);
int
index
;
if
(
parent
==
NULL
)
{
if
(
IntegerArray_binary_search
(
leaf
->
keys
,
key
,
&
index
))
{
grow
(
root
,
*
key
,
*
split_right_node
);
BPTreeNodeArray_destroy
(
&
parents
);
return
;
}
}
if
(
has_maximum_keys
(
leaf
))
{
return
true
;
insert_full
(
root
,
parents
,
leaf
,
key
,
data
,
NULL
);
}
}
else
{
insert_non_full
(
leaf
,
key
,
data
,
NULL
);
}
BPTreeNodeArray_destroy
(
&
parents
);
bool
BPTree_insert
(
BPTreeNode
*
root
,
uint64_t
key
,
uint64_t
data
)
{
BPTreeNode
*
previous_split_right_node
;
return
_BPTree_insert
(
NULL
,
root
,
&
key
,
data
,
&
previous_split_right_node
);
}
}
// BPTree : Deletion
// BPTree : Deletion
static
BPTreeNode
*
traverse
(
BPTreeNode
*
node
,
uint64_t
key
)
{
int
virtual_insertion_index
=
lower_bound
(
node
->
keys
,
key
);
if
(
virtual_insertion_index
<
node
->
keys
->
size
&&
node
->
keys
->
items
[
virtual_insertion_index
]
==
key
)
{
virtual_insertion_index
+=
1
;
}
return
node
->
children
->
items
[
virtual_insertion_index
];
}
static
uint64_t
find_smallest_key
(
BPTreeNode
*
root
)
{
static
uint64_t
find_smallest_key
(
BPTreeNode
*
root
)
{
if
(
root
->
is_leaf
)
{
if
(
root
->
is_leaf
)
{
return
root
->
keys
->
items
[
0
];
return
root
->
keys
->
items
[
0
];
...
@@ -390,7 +370,7 @@ static void steal_internal(BPTreeNode *parent, BPTreeNode *node, BPTreeNode *sib
...
@@ -390,7 +370,7 @@ static void steal_internal(BPTreeNode *parent, BPTreeNode *node, BPTreeNode *sib
}
}
}
}
static
void
deletion_rebalance
(
BPTreeNode
*
node
,
BPTreeNode
*
parent
)
{
static
void
deletion_rebalance
(
BPTreeNode
*
parent
,
BPTreeNode
*
node
)
{
BPTreeNode
*
sibling
=
find_sibling
(
parent
,
node
);
BPTreeNode
*
sibling
=
find_sibling
(
parent
,
node
);
if
(
sibling
->
keys
->
size
==
sibling
->
order
)
{
if
(
sibling
->
keys
->
size
==
sibling
->
order
)
{
...
@@ -406,8 +386,8 @@ static void deletion_rebalance(BPTreeNode *node, BPTreeNode *parent) {
...
@@ -406,8 +386,8 @@ static void deletion_rebalance(BPTreeNode *node, BPTreeNode *parent) {
}
}
}
}
static
bool
_BPTree_delete
(
BPTreeNode
*
root
,
uint64_t
key
,
BPTreeNode
*
parent
)
{
static
bool
_BPTree_delete
(
BPTreeNode
*
parent
,
BPTreeNode
*
root
,
uint64_t
key
)
{
if
(
!
root
->
is_leaf
&&
!
_BPTree_delete
(
traverse
(
root
,
key
),
key
,
root
))
{
if
(
!
root
->
is_leaf
&&
!
_BPTree_delete
(
root
,
traverse
(
root
,
key
),
key
))
{
return
false
;
return
false
;
}
}
...
@@ -429,12 +409,12 @@ static bool _BPTree_delete(BPTreeNode *root, uint64_t key, BPTreeNode *parent) {
...
@@ -429,12 +409,12 @@ static bool _BPTree_delete(BPTreeNode *root, uint64_t key, BPTreeNode *parent) {
}
}
if
(
parent
!=
NULL
&&
root
->
keys
->
size
<
root
->
order
)
{
if
(
parent
!=
NULL
&&
root
->
keys
->
size
<
root
->
order
)
{
deletion_rebalance
(
root
,
paren
t
);
deletion_rebalance
(
parent
,
roo
t
);
}
}
return
true
;
return
true
;
}
}
bool
BPTree_delete
(
BPTreeNode
*
root
,
uint64_t
key
)
{
bool
BPTree_delete
(
BPTreeNode
*
root
,
uint64_t
key
)
{
return
_BPTree_delete
(
root
,
key
,
NULL
);
return
_BPTree_delete
(
NULL
,
root
,
key
);
}
}
This diff is collapsed.
Click to expand it.
src/BPTree.h
+
1
−
1
View file @
9df79d44
...
@@ -20,7 +20,7 @@ void BPTree_destroy(BPTreeNode **root);
...
@@ -20,7 +20,7 @@ void BPTree_destroy(BPTreeNode **root);
void
BPTree_print
(
BPTreeNode
*
root
,
int
depth
);
void
BPTree_print
(
BPTreeNode
*
root
,
int
depth
);
bool
BPTree_search
(
BPTreeNode
*
root
,
uint64_t
key
,
uint64_t
*
data
);
bool
BPTree_search
(
BPTreeNode
*
root
,
uint64_t
key
,
uint64_t
*
data
);
void
BPTree_insert
(
BPTreeNode
*
root
,
uint64_t
key
,
uint64_t
data
);
bool
BPTree_insert
(
BPTreeNode
*
root
,
uint64_t
key
,
uint64_t
data
);
bool
BPTree_delete
(
BPTreeNode
*
root
,
uint64_t
key
);
bool
BPTree_delete
(
BPTreeNode
*
root
,
uint64_t
key
);
#endif
#endif
This diff is collapsed.
Click to expand it.
src/main.c
+
42
−
143
View file @
9df79d44
#include
<
stdio
.h>
#include
<
assert
.h>
#include
<stdlib.h>
#include
<stdlib.h>
#include
"
Director
y.h"
#include
"
Arra
y.h"
#include
"
DirectoryRecord
.h"
#include
"
BPTree
.h"
void
clear_buffer
()
{
int
main
()
{
int
c
;
BPTreeNode
*
root
=
BPTree_init
(
2
);
while
((
c
=
getchar
())
!=
'\n'
&&
c
!=
EOF
)
{
}
}
void
append_record
(
Directory
*
directory
)
{
char
phone_number
[
PHONE_NUMBER_MAXLEN
];
printf
(
"Enter the phone number: "
);
scanf
(
"%10s"
,
phone_number
);
clear_buffer
();
char
name
[
NAME_MAXLEN
];
printf
(
"Enter the name: "
);
scanf
(
"%20s"
,
name
);
clear_buffer
();
char
surname
[
SURNAME_MAXLEN
];
printf
(
"Enter the surname: "
);
scanf
(
"%20s"
,
surname
);
clear_buffer
();
int
birth_date_year
,
birth_date_month
,
birth_date_day
;
do
{
printf
(
"Enter the birth date (Y-m-d): "
);
}
while
(
scanf
(
"%d-%d-%d"
,
&
birth_date_year
,
&
birth_date_month
,
&
birth_date_day
)
!=
3
);
clear_buffer
();
printf
(
"
\n
Is the information entered correct? (Y/n) "
);
char
choice
=
getchar
();
if
(
choice
!=
'\n'
)
{
getchar
();
}
if
(
choice
==
'n'
)
{
printf
(
"
\n
===>The procedure has been cancelled.
\n
"
);
}
else
{
DirectoryRecord
*
record
=
DirectoryRecord_init
(
false
,
phone_number
,
name
,
surname
,
birth_date_year
,
birth_date_month
,
birth_date_day
);
if
(
Directory_append
(
directory
,
record
))
{
printf
(
"
\n
===>The record has been saved in the directory.
\n
"
);
}
else
{
printf
(
"
\n
===>This phone number is already associated with a record. The record has not been saved.
\n
"
);
}
DirectoryRecord_destroy
(
&
record
);
}
}
void
search_record
(
Directory
*
directory
)
{
printf
(
"Enter the phone number that corresponds to the record you are looking for: "
);
char
phone_number
[
PHONE_NUMBER_MAXLEN
];
scanf
(
"%10s"
,
phone_number
);
clear_buffer
();
DirectoryRecord
*
record
=
Directory_search
(
directory
,
phone_number
);
printf
(
"
\n
"
);
if
(
record
==
NULL
)
{
uint64_t
input
[]
=
{
8
,
12
,
11
,
47
,
22
,
95
,
86
,
40
,
33
,
78
,
28
,
5
,
75
,
88
,
21
,
56
,
82
,
51
,
93
,
66
,
48
,
70
,
57
,
65
,
35
,
4
,
60
,
41
,
49
,
55
,
68
,
72
,
23
,
31
,
30
,
42
,
18
,
87
,
24
,
58
};
printf
(
"===>No records were found for this phone number.
\n
"
);
IntegerArray
*
keys
=
IntegerArray_init
(
40
);
}
else
{
for
(
int
i
=
0
;
i
<
30
;
i
++
)
{
printf
(
"========================
\n
"
);
IntegerArray_append
(
keys
,
input
[
i
]);
DirectoryRecord_print
(
record
);
DirectoryRecord_destroy
(
&
record
);
printf
(
"========================
\n
"
);
}
}
}
void
delete_record
(
Directory
*
directory
)
{
printf
(
"Enter the phone number that corresponds to the record you wish to delete: "
);
char
phone_number
[
PHONE_NUMBER_MAXLEN
];
scanf
(
"%10s"
,
phone_number
);
clear_buffer
();
DirectoryRecord
*
record
=
Directory_search
(
directory
,
phone_number
);
printf
(
"
\n
"
);
if
(
record
==
NULL
)
{
IntegerArray_print
(
keys
);
printf
(
"===>No records were found for this phone number.
\n
"
);
}
else
{
printf
(
"========================
\n
"
);
DirectoryRecord_print
(
record
);
DirectoryRecord_destroy
(
&
record
);
printf
(
"========================
\n
"
);
printf
(
"
\n
Are you sure you want to delete this record? (Y/n) "
);
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
BPTree_insert
(
root
,
keys
->
items
[
i
],
keys
->
items
[
i
]
*
1000
);
char
choice
=
getchar
();
if
(
choice
!=
'\n'
)
{
getchar
();
}
if
(
choice
==
'n'
)
{
printf
(
"
\n
===>The procedure has been cancelled.
\n
"
);
}
else
{
Directory_delete
(
directory
,
phone_number
);
printf
(
"Delete done
\n
"
);
}
}
}
}
int
main
()
{
Directory
*
directory
=
Directory_init
(
"directory_database"
);
while
(
true
)
{
BPTree_print
(
directory
->
index
,
0
);
printf
(
"Enter 1 to add a member.
\n
"
);
printf
(
"Enter 2 to search for a member via their phone number.
\n
"
);
printf
(
"Enter 3 to delete a member.
\n
"
);
printf
(
"Enter 4 to display all members.
\n
"
);
printf
(
"Enter 5 to exit the program.
\n
"
);
printf
(
"What do you want to do? "
);
int
action
;
scanf
(
"%d"
,
&
action
);
clear_buffer
();
if
(
action
<
1
||
action
>
5
)
{
system
(
"clear"
);
continue
;
}
if
(
action
==
5
)
{
break
;
}
printf
(
"
\n
"
);
switch
(
action
)
{
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
case
1
:
uint64_t
data
;
append_record
(
directory
);
bool
found
=
BPTree_search
(
root
,
keys
->
items
[
i
],
&
data
);
break
;
case
2
:
search_record
(
directory
);
break
;
case
3
:
delete_record
(
directory
);
break
;
case
4
:
Directory_print
(
directory
);
break
;
}
printf
(
"
\n
Press enter to continue..."
);
assert
(
found
==
true
);
getchar
();
assert
(
data
==
keys
->
items
[
i
]
*
1000
);
system
(
"clear"
);
}
}
Directory_destroy
(
&
directory
);
BPTree_delete
(
root
,
65
);
BPTree_delete
(
root
,
57
);
BPTree_delete
(
root
,
47
);
BPTree_delete
(
root
,
28
);
BPTree_delete
(
root
,
51
);
BPTree_insert
(
root
,
100
,
100
*
1000
);
BPTree_delete
(
root
,
48
);
BPTree_delete
(
root
,
41
);
BPTree_delete
(
root
,
60
);
BPTree_delete
(
root
,
5
);
BPTree_delete
(
root
,
8
);
BPTree_delete
(
root
,
21
);
BPTree_delete
(
root
,
86
);
BPTree_delete
(
root
,
100
);
BPTree_delete
(
root
,
88
);
BPTree_delete
(
root
,
95
);
BPTree_delete
(
root
,
49
);
BPTree_delete
(
root
,
56
);
BPTree_delete
(
root
,
55
);
BPTree_print
(
root
,
0
);
IntegerArray_destroy
(
&
keys
);
BPTree_destroy
(
&
root
);
return
EXIT_SUCCESS
;
return
EXIT_SUCCESS
;
}
}
This diff is collapsed.
Click to expand it.
src/tests/BPTreeTests.c
+
44
−
43
View file @
9df79d44
/**
* @file BPTreeTests.c
* @author Florian Burgener (florian.burgener@etu.hesge.ch)
* @brief Unit tests of the BPTree data structure.
* @version 1.0
* @date 2022-06-07
*/
#include
<stdbool.h>
#include
<stdbool.h>
#include
<stdint.h>
#include
<stdint.h>
#include
<stdio.h>
#include
<stdlib.h>
#include
<stdlib.h>
#include
"../Array.h"
#include
"../Array.h"
...
@@ -10,18 +16,13 @@
...
@@ -10,18 +16,13 @@
#define RANDOM_MIN 0
#define RANDOM_MIN 0
#define RANDOM_MAX 1000
#define RANDOM_MAX 1000
BPTreeNode
*
tree
;
void
setUp
()
{
void
setUp
(
void
)
{
}
}
void
tearDown
(
void
)
{
void
tearDown
()
{
if
(
tree
!=
NULL
)
{
BPTree_destroy
(
&
tree
);
}
}
}
// BEGIN :
Compliance with B+ Tre
e rules
// BEGIN :
Functions that check that a B+ Tree is compliant with th
e rules
static
BPTreeNode
*
find_first_leaf
(
BPTreeNode
*
root
)
{
static
BPTreeNode
*
find_first_leaf
(
BPTreeNode
*
root
)
{
if
(
root
->
is_leaf
)
{
if
(
root
->
is_leaf
)
{
...
@@ -218,7 +219,7 @@ static bool check_BPTree_compliance(BPTreeNode *root) {
...
@@ -218,7 +219,7 @@ static bool check_BPTree_compliance(BPTreeNode *root) {
return
is_compliant
;
return
is_compliant
;
}
}
// END :
BP
Tree
C
omplian
ce
// END :
Functions that check that a B+
Tree
is c
omplian
t with the rules
/**
/**
* @brief Performs a linear search for an item in an array.
* @brief Performs a linear search for an item in an array.
...
@@ -271,7 +272,7 @@ static uint64_t transform_key_to_data(uint64_t key) {
...
@@ -271,7 +272,7 @@ static uint64_t transform_key_to_data(uint64_t key) {
// **** BEGIN : test_BPTree_insert
// **** BEGIN : test_BPTree_insert
static
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
BPTreeNode
**
root
,
int
order
)
{
static
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
int
order
)
{
int
size
=
1
;
int
size
=
1
;
// Test 10 times, variable i being the seed.
// Test 10 times, variable i being the seed.
...
@@ -282,16 +283,16 @@ static void test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_g
...
@@ -282,16 +283,16 @@ static void test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_g
// will have the size of 1 then 2, 4, 8, 16, 32, ...
// will have the size of 1 then 2, 4, 8, 16, 32, ...
for
(
int
j
=
0
;
j
<
8
;
j
++
)
{
for
(
int
j
=
0
;
j
<
8
;
j
++
)
{
IntegerArray
*
keys
=
generate_random_numbers_array
(
size
,
RANDOM_MIN
,
RANDOM_MAX
);
IntegerArray
*
keys
=
generate_random_numbers_array
(
size
,
RANDOM_MIN
,
RANDOM_MAX
);
*
root
=
BPTree_init
(
order
);
BPTreeNode
*
root
=
BPTree_init
(
order
);
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
BPTree_insert
(
*
root
,
keys
->
items
[
i
],
transform_key_to_data
(
keys
->
items
[
i
]));
BPTree_insert
(
root
,
keys
->
items
[
i
],
transform_key_to_data
(
keys
->
items
[
i
]));
// After each insertion is verified that the B+ Tree is compliant with the rules.
// After each insertion is verified that the B+ Tree is compliant with the rules.
TEST_ASSERT
(
check_BPTree_compliance
(
*
root
));
TEST_ASSERT
(
check_BPTree_compliance
(
root
));
}
}
IntegerArray_destroy
(
&
keys
);
IntegerArray_destroy
(
&
keys
);
BPTree_destroy
(
root
);
BPTree_destroy
(
&
root
);
size
*=
2
;
size
*=
2
;
}
}
...
@@ -301,34 +302,34 @@ static void test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_g
...
@@ -301,34 +302,34 @@ static void test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_g
}
}
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_1
()
{
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_1
()
{
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
1
);
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
1
);
}
}
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_2
()
{
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_2
()
{
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
2
);
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
2
);
}
}
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_3
()
{
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_3
()
{
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
3
);
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
3
);
}
}
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_4
()
{
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_4
()
{
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
4
);
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
4
);
}
}
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_8
()
{
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_8
()
{
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
8
);
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
8
);
}
}
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_16
()
{
void
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_order_16
()
{
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
16
);
test_BPTree_insert_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
16
);
}
}
// **** END : test_BPTree_insert
// **** END : test_BPTree_insert
// **** BEGIN : test_BPTree_delete
// **** BEGIN : test_BPTree_delete
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
BPTreeNode
**
root
,
int
order
)
{
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
int
order
)
{
int
size
=
1
;
int
size
=
1
;
// Test 10 times, variable i being the seed.
// Test 10 times, variable i being the seed.
...
@@ -339,20 +340,20 @@ void test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_or
...
@@ -339,20 +340,20 @@ void test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_or
// will have the size of 1 then 2, 4, 8, 16, 32, ...
// will have the size of 1 then 2, 4, 8, 16, 32, ...
for
(
int
j
=
0
;
j
<
8
;
j
++
)
{
for
(
int
j
=
0
;
j
<
8
;
j
++
)
{
IntegerArray
*
keys
=
generate_random_numbers_array
(
size
,
RANDOM_MIN
,
RANDOM_MAX
);
IntegerArray
*
keys
=
generate_random_numbers_array
(
size
,
RANDOM_MIN
,
RANDOM_MAX
);
*
root
=
BPTree_init
(
order
);
BPTreeNode
*
root
=
BPTree_init
(
order
);
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
BPTree_insert
(
*
root
,
keys
->
items
[
i
],
transform_key_to_data
(
keys
->
items
[
i
]));
BPTree_insert
(
root
,
keys
->
items
[
i
],
transform_key_to_data
(
keys
->
items
[
i
]));
}
}
while
(
keys
->
size
>
0
)
{
while
(
keys
->
size
>
0
)
{
int
index
=
rand
()
%
keys
->
size
;
int
index
=
rand
()
%
keys
->
size
;
BPTree_delete
(
*
root
,
keys
->
items
[
index
]);
BPTree_delete
(
root
,
keys
->
items
[
index
]);
IntegerArray_delete_at_index
(
keys
,
index
);
IntegerArray_delete_at_index
(
keys
,
index
);
}
}
IntegerArray_destroy
(
&
keys
);
IntegerArray_destroy
(
&
keys
);
BPTree_destroy
(
root
);
BPTree_destroy
(
&
root
);
size
*=
2
;
size
*=
2
;
}
}
...
@@ -362,34 +363,34 @@ void test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_or
...
@@ -362,34 +363,34 @@ void test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_or
}
}
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_1
()
{
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_1
()
{
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
1
);
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
1
);
}
}
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_2
()
{
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_2
()
{
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
2
);
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
2
);
}
}
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_3
()
{
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_3
()
{
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
3
);
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
3
);
}
}
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_4
()
{
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_4
()
{
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
4
);
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
4
);
}
}
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_8
()
{
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_8
()
{
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
8
);
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
8
);
}
}
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_16
()
{
void
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_order_16
()
{
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
&
tree
,
16
);
test_BPTree_delete_should_comply_with_BPTree_rules_using_BPTree_of_given_order
(
16
);
}
}
// **** END : test_BPTree_delete
// **** END : test_BPTree_delete
// **** BEGIN : test_BPTree_search
// **** BEGIN : test_BPTree_search
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
BPTreeNode
**
root
,
int
order
)
{
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
int
order
)
{
int
size
=
256
;
int
size
=
256
;
// Test 10 times, variable i being the seed.
// Test 10 times, variable i being the seed.
...
@@ -397,47 +398,47 @@ void test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTr
...
@@ -397,47 +398,47 @@ void test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTr
srand
(
i
);
srand
(
i
);
IntegerArray
*
keys
=
generate_random_numbers_array
(
size
,
RANDOM_MIN
,
RANDOM_MAX
);
IntegerArray
*
keys
=
generate_random_numbers_array
(
size
,
RANDOM_MIN
,
RANDOM_MAX
);
*
root
=
BPTree_init
(
order
);
BPTreeNode
*
root
=
BPTree_init
(
order
);
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
BPTree_insert
(
*
root
,
keys
->
items
[
i
],
transform_key_to_data
(
keys
->
items
[
i
]));
BPTree_insert
(
root
,
keys
->
items
[
i
],
transform_key_to_data
(
keys
->
items
[
i
]));
}
}
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
for
(
int
i
=
0
;
i
<
keys
->
size
;
i
++
)
{
uint64_t
data
;
uint64_t
data
;
bool
is_found
=
BPTree_search
(
*
root
,
keys
->
items
[
i
],
&
data
);
bool
is_found
=
BPTree_search
(
root
,
keys
->
items
[
i
],
&
data
);
TEST_ASSERT
(
is_found
);
TEST_ASSERT
(
is_found
);
TEST_ASSERT_EQUAL_UINT64
(
transform_key_to_data
(
keys
->
items
[
i
]),
data
);
TEST_ASSERT_EQUAL_UINT64
(
transform_key_to_data
(
keys
->
items
[
i
]),
data
);
}
}
IntegerArray_destroy
(
&
keys
);
IntegerArray_destroy
(
&
keys
);
BPTree_destroy
(
root
);
BPTree_destroy
(
&
root
);
}
}
}
}
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_1
()
{
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_1
()
{
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
&
tree
,
1
);
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
1
);
}
}
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_2
()
{
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_2
()
{
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
&
tree
,
2
);
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
2
);
}
}
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_3
()
{
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_3
()
{
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
&
tree
,
3
);
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
3
);
}
}
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_4
()
{
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_4
()
{
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
&
tree
,
4
);
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
4
);
}
}
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_8
()
{
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_8
()
{
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
&
tree
,
8
);
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
8
);
}
}
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_16
()
{
void
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_order_16
()
{
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
&
tree
,
16
);
test_BPTree_search_should_find_the_keys_that_exist_in_the_BPTree_using_BPTree_of_given_order
(
16
);
}
}
// **** END : test_BPTree_search
// **** END : test_BPTree_search
...
...
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment