Finished implementation
This commit is contained in:
parent
6559d2a156
commit
754dadd12f
1 changed files with 165 additions and 51 deletions
|
|
@ -146,7 +146,7 @@ IntList list_obtain() {
|
||||||
* @param p_list The pointer to the list to release. The value of the pointer
|
* @param p_list The pointer to the list to release. The value of the pointer
|
||||||
* is set to 0, if the list was successfully released, otherwise it is left untouched.
|
* is set to 0, if the list was successfully released, otherwise it is left untouched.
|
||||||
*/
|
*/
|
||||||
void list_release(IntList* p_list) { // no need to use the tail & size as its going to free everything anyways, TODO: check here later
|
void list_release(IntList* p_list) { // no need to use the tail & size as its going to free everything anyways
|
||||||
if (p_list == 0 || *p_list == 0) {
|
if (p_list == 0 || *p_list == 0) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
@ -211,7 +211,7 @@ int list_get_size(IntList list) {
|
||||||
* @return `True` if the list contains at least one instance of the value,
|
* @return `True` if the list contains at least one instance of the value,
|
||||||
* `false ` otherwise.
|
* `false ` otherwise.
|
||||||
*/
|
*/
|
||||||
bool list_contains(IntList list, int value) { // TODO: rewrite
|
bool list_contains(IntList list, int value) {
|
||||||
if (!list_is_valid(list)) {
|
if (!list_is_valid(list)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
@ -235,20 +235,32 @@ bool list_contains(IntList list, int value) { // TODO: rewrite
|
||||||
* @return The value stored at the given position or 0, if the position
|
* @return The value stored at the given position or 0, if the position
|
||||||
* is not available.
|
* is not available.
|
||||||
*/
|
*/
|
||||||
int list_get_at(IntList list, unsigned int index) { // TODO: rewrite?
|
int list_get_at(IntList list, unsigned int index) {
|
||||||
if (!list_is_valid(list)) {
|
if (!list_is_valid(list) || list_is_empty(list)) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned int i = 0;
|
unsigned int i = 0;
|
||||||
|
|
||||||
|
// first half
|
||||||
|
if (index < list->size / 2) {
|
||||||
IntListNode current = list->head;
|
IntListNode current = list->head;
|
||||||
while (current != 0) {
|
while (i < index) {
|
||||||
if (i == index) {
|
|
||||||
return current->data;
|
|
||||||
}
|
|
||||||
current = current->next;
|
current = current->next;
|
||||||
i++;
|
i++;
|
||||||
}
|
}
|
||||||
|
return current->data;
|
||||||
|
}
|
||||||
|
// second half
|
||||||
|
else {
|
||||||
|
i = list->size - 1;
|
||||||
|
IntListNode current = list->tail;
|
||||||
|
while (i > index) {
|
||||||
|
current = current->prev;
|
||||||
|
i--;
|
||||||
|
}
|
||||||
|
return current->data;
|
||||||
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
@ -269,9 +281,10 @@ void list_insert(IntList list, int value) {
|
||||||
if (newNode != 0) {
|
if (newNode != 0) {
|
||||||
if (list_is_empty(list)) {
|
if (list_is_empty(list)) {
|
||||||
list->head = newNode;
|
list->head = newNode;
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
list->tail->next = newNode;
|
list->tail->next = newNode;
|
||||||
|
newNode->prev = list->tail;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
list->tail = newNode;
|
list->tail = newNode;
|
||||||
|
|
@ -289,36 +302,53 @@ void list_insert(IntList list, int value) {
|
||||||
* @param index The position index of the value to insert.
|
* @param index The position index of the value to insert.
|
||||||
* @param value The value to insert.
|
* @param value The value to insert.
|
||||||
*/
|
*/
|
||||||
void list_insert_at(IntList list, unsigned int index, int value) { // TODO: rewrite
|
void list_insert_at(IntList list, unsigned int index, int value) {
|
||||||
if (!list_is_valid(list)) {
|
if (!list_is_valid(list)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
IntListNode newNode = list_obtain_node(value);
|
IntListNode newNode = list_obtain_node(value);
|
||||||
|
if (newNode == 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (list_is_empty(list)) {
|
if (list_is_empty(list)) {
|
||||||
list->head = newNode;
|
list->head = newNode;
|
||||||
|
list->tail = newNode;
|
||||||
|
list->size++;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (index == 0) {
|
if (index == 0) {
|
||||||
newNode->next = list->head;
|
newNode->next = list->head;
|
||||||
|
list->head->prev = newNode;
|
||||||
list->head = newNode;
|
list->head = newNode;
|
||||||
|
list->size++;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned int i = 0;
|
unsigned int i = 0;
|
||||||
IntListNode current = list->head;
|
IntListNode current = list->head;
|
||||||
IntListNode previous = 0;
|
|
||||||
|
|
||||||
while (current != 0 && i < index) {
|
while (current != 0 && i < index) {
|
||||||
previous = current;
|
|
||||||
current = current->next;
|
current = current->next;
|
||||||
i++;
|
i++;
|
||||||
}
|
}
|
||||||
|
|
||||||
previous->next = newNode;
|
// if at the end, insert after current
|
||||||
|
if (current == 0) {
|
||||||
|
list->tail->next = newNode;
|
||||||
|
newNode->prev = list->tail;
|
||||||
|
list->tail = newNode;
|
||||||
|
} else {
|
||||||
|
// before current
|
||||||
newNode->next = current;
|
newNode->next = current;
|
||||||
|
newNode->prev = current->prev;
|
||||||
|
current->prev->next = newNode;
|
||||||
|
current->prev = newNode;
|
||||||
|
}
|
||||||
|
|
||||||
|
list->size++;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -330,22 +360,24 @@ void list_insert_at(IntList list, unsigned int index, int value) { // TODO: rewr
|
||||||
* @param list_to_append The list that is appended to `list`.
|
* @param list_to_append The list that is appended to `list`.
|
||||||
*/
|
*/
|
||||||
void list_append(IntList list, IntList list_to_append) {
|
void list_append(IntList list, IntList list_to_append) {
|
||||||
if (!list_is_valid(list) || !list_is_valid(list_to_append) || list_is_empty(list_to_append)) { // TODO: rewrite
|
if (!list_is_valid(list) || !list_is_valid(list_to_append) || list_is_empty(list_to_append)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (list_is_empty(list)) {
|
if (list_is_empty(list)) {
|
||||||
list->head = list_to_append->head;
|
list->head = list_to_append->head;
|
||||||
|
list->tail = list_to_append->tail;
|
||||||
|
list->size = list_to_append->size;
|
||||||
} else {
|
} else {
|
||||||
IntListNode current = list->head;
|
list->tail->next = list_to_append->head;
|
||||||
while (current->next != 0) {
|
list_to_append->head->prev = list->tail;
|
||||||
current = current->next;
|
list->tail = list_to_append->tail;
|
||||||
}
|
list->size += list_to_append->size;
|
||||||
|
|
||||||
current->next = list_to_append->head;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
list_to_append->head = 0;
|
list_to_append->head = 0;
|
||||||
|
list_to_append->tail = 0;
|
||||||
|
list_to_append->size = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -356,7 +388,7 @@ void list_append(IntList list, IntList list_to_append) {
|
||||||
* @param list The list from which the given value shall be removed.
|
* @param list The list from which the given value shall be removed.
|
||||||
* @param value The value to remove from the list.
|
* @param value The value to remove from the list.
|
||||||
*/
|
*/
|
||||||
void list_remove(IntList list, int value) { // TODO: rewrite
|
void list_remove(IntList list, int value) {
|
||||||
if (!list_is_valid(list) || list_is_empty(list)) {
|
if (!list_is_valid(list) || list_is_empty(list)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
@ -364,16 +396,33 @@ void list_remove(IntList list, int value) { // TODO: rewrite
|
||||||
if (list->head->data == value) {
|
if (list->head->data == value) {
|
||||||
IntListNode old_head = list->head;
|
IntListNode old_head = list->head;
|
||||||
list->head = list->head->next;
|
list->head = list->head->next;
|
||||||
|
|
||||||
|
if (list->head != 0) {
|
||||||
|
list->head->prev = 0;
|
||||||
|
} else {
|
||||||
|
list->tail = 0;
|
||||||
|
}
|
||||||
|
|
||||||
list_release_node(old_head);
|
list_release_node(old_head);
|
||||||
|
list->size--;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
IntListNode current = list->head;
|
IntListNode current = list->head->next;
|
||||||
while (current->next != 0) {
|
while (current != 0) {
|
||||||
if (current->next->data == value) {
|
if (current->data == value) {
|
||||||
IntListNode to_remove = current->next;
|
if (current->prev != 0) {
|
||||||
current->next = to_remove->next;
|
current->prev->next = current->next;
|
||||||
list_release_node(to_remove);
|
}
|
||||||
|
|
||||||
|
if (current->next != 0) {
|
||||||
|
current->next->prev = current->prev;
|
||||||
|
} else {
|
||||||
|
list->tail = current->prev;
|
||||||
|
}
|
||||||
|
|
||||||
|
list_release_node(current);
|
||||||
|
list->size--;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
current = current->next;
|
current = current->next;
|
||||||
|
|
@ -388,7 +437,7 @@ void list_remove(IntList list, int value) { // TODO: rewrite
|
||||||
* @param list The list from which all occurrances of `value` shall be removed.
|
* @param list The list from which all occurrances of `value` shall be removed.
|
||||||
* @param value The `value` to remove throughout the list.
|
* @param value The `value` to remove throughout the list.
|
||||||
*/
|
*/
|
||||||
void list_remove_all(IntList list, int value) { // TODO: rewrite
|
void list_remove_all(IntList list, int value) {
|
||||||
if (!list_is_valid(list) || list_is_empty(list)) {
|
if (!list_is_valid(list) || list_is_empty(list)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
@ -396,7 +445,15 @@ void list_remove_all(IntList list, int value) { // TODO: rewrite
|
||||||
while (list->head != 0 && list->head->data == value) {
|
while (list->head != 0 && list->head->data == value) {
|
||||||
IntListNode old_head = list->head;
|
IntListNode old_head = list->head;
|
||||||
list->head = list->head->next;
|
list->head = list->head->next;
|
||||||
|
|
||||||
|
if (list->head != 0) {
|
||||||
|
list->head->prev = 0;
|
||||||
|
} else {
|
||||||
|
list->tail = 0;
|
||||||
|
}
|
||||||
|
|
||||||
list_release_node(old_head);
|
list_release_node(old_head);
|
||||||
|
list->size--;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (list_is_empty(list)) {
|
if (list_is_empty(list)) {
|
||||||
|
|
@ -404,11 +461,19 @@ void list_remove_all(IntList list, int value) { // TODO: rewrite
|
||||||
}
|
}
|
||||||
|
|
||||||
IntListNode current = list->head;
|
IntListNode current = list->head;
|
||||||
while (current->next != 0) {
|
while (current != 0 && current->next != 0) {
|
||||||
if (current->next->data == value) {
|
if (current->next->data == value) {
|
||||||
IntListNode to_remove = current->next;
|
IntListNode to_remove = current->next;
|
||||||
current->next = to_remove->next;
|
current->next = to_remove->next;
|
||||||
|
|
||||||
|
if (to_remove->next != 0) {
|
||||||
|
to_remove->next->prev = current;
|
||||||
|
} else {
|
||||||
|
list->tail = current;
|
||||||
|
}
|
||||||
|
|
||||||
list_release_node(to_remove);
|
list_release_node(to_remove);
|
||||||
|
list->size--;
|
||||||
} else {
|
} else {
|
||||||
current = current->next;
|
current = current->next;
|
||||||
}
|
}
|
||||||
|
|
@ -424,36 +489,71 @@ void list_remove_all(IntList list, int value) { // TODO: rewrite
|
||||||
* @param index The zero-based index of the value to return.
|
* @param index The zero-based index of the value to return.
|
||||||
* @return The removed value or 0 in case of errors.
|
* @return The removed value or 0 in case of errors.
|
||||||
*/
|
*/
|
||||||
int list_remove_at(IntList list, unsigned int index) { // TODO: rewrite
|
int list_remove_at(IntList list, unsigned int index) {
|
||||||
if (!list_is_valid(list) || list_is_empty(list)) {
|
if (!list_is_valid(list) || list_is_empty(list) || index >= list->size) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int value;
|
||||||
|
|
||||||
if (index == 0) {
|
if (index == 0) {
|
||||||
int value = list->head->data;
|
value = list->head->data;
|
||||||
IntListNode old_head = list->head;
|
IntListNode old_head = list->head;
|
||||||
list->head = list->head->next;
|
list->head = list->head->next;
|
||||||
|
|
||||||
|
if (list->head != 0) {
|
||||||
|
list->head->prev = 0;
|
||||||
|
} else {
|
||||||
|
list->tail = 0;
|
||||||
|
}
|
||||||
|
|
||||||
list_release_node(old_head);
|
list_release_node(old_head);
|
||||||
|
list->size--;
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (index == list->size - 1) {
|
||||||
|
value = list->tail->data;
|
||||||
|
IntListNode old_tail = list->tail;
|
||||||
|
list->tail = list->tail->prev;
|
||||||
|
|
||||||
|
list->tail->next = 0;
|
||||||
|
|
||||||
|
list_release_node(old_tail);
|
||||||
|
list->size--;
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
|
|
||||||
unsigned int i = 0;
|
unsigned int i = 0;
|
||||||
IntListNode current = list->head;
|
IntListNode current = list->head;
|
||||||
IntListNode previous = 0;
|
|
||||||
|
|
||||||
while (current != 0 && i < index) {
|
// first half
|
||||||
previous = current;
|
if (index < list->size / 2) {
|
||||||
|
while (i < index) {
|
||||||
current = current->next;
|
current = current->next;
|
||||||
i++;
|
i++;
|
||||||
}
|
}
|
||||||
|
// second half
|
||||||
if (current == 0) {
|
} else {
|
||||||
return 0;
|
current = list->tail;
|
||||||
|
i = list->size - 1;
|
||||||
|
while (i > index) {
|
||||||
|
current = current->prev;
|
||||||
|
i--;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
value = current->data;
|
||||||
|
if (current->prev != 0) {
|
||||||
|
current->prev->next = current->next;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (current->next != 0) {
|
||||||
|
current->next->prev = current->prev;
|
||||||
}
|
}
|
||||||
|
|
||||||
int value = current->data;
|
|
||||||
previous->next = current->next;
|
|
||||||
list_release_node(current);
|
list_release_node(current);
|
||||||
|
list->size--;
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -462,7 +562,7 @@ int list_remove_at(IntList list, unsigned int index) { // TODO: rewrite
|
||||||
*
|
*
|
||||||
* @param list The list to clear.
|
* @param list The list to clear.
|
||||||
*/
|
*/
|
||||||
void list_clear(IntList list) { // TODO: rewrite?
|
void list_clear(IntList list) {
|
||||||
if (!list_is_valid(list) || list_is_empty(list)) {
|
if (!list_is_valid(list) || list_is_empty(list)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
@ -475,6 +575,8 @@ void list_clear(IntList list) { // TODO: rewrite?
|
||||||
}
|
}
|
||||||
|
|
||||||
list->head = 0;
|
list->head = 0;
|
||||||
|
list->tail = 0;
|
||||||
|
list->size = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* ===================================================================== */
|
/* ===================================================================== */
|
||||||
|
|
@ -515,8 +617,12 @@ IntListIterator list_it_obtain(IntList list) {
|
||||||
* is set to 0, if the list iterator was successfully released, otherwise it is left untouched.
|
* is set to 0, if the list iterator was successfully released, otherwise it is left untouched.
|
||||||
*/
|
*/
|
||||||
void list_it_release(IntListIterator* p_it) {
|
void list_it_release(IntListIterator* p_it) {
|
||||||
free_mem(p_it);
|
if (p_it == 0 || *p_it == 0) {
|
||||||
p_it = 0;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
free_mem(*p_it);
|
||||||
|
*p_it = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -526,7 +632,7 @@ void list_it_release(IntListIterator* p_it) {
|
||||||
* @return `True` if the list iterator is valid, false otherwise.
|
* @return `True` if the list iterator is valid, false otherwise.
|
||||||
*/
|
*/
|
||||||
bool list_it_is_valid(IntListIterator it) {
|
bool list_it_is_valid(IntListIterator it) {
|
||||||
return it != 0;
|
return it != 0 && it->cur != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -536,6 +642,10 @@ bool list_it_is_valid(IntListIterator it) {
|
||||||
* @return `True` if the list iterator could proceed to the next list node, `false` otherwise.
|
* @return `True` if the list iterator could proceed to the next list node, `false` otherwise.
|
||||||
*/
|
*/
|
||||||
bool list_it_next(IntListIterator it) {
|
bool list_it_next(IntListIterator it) {
|
||||||
|
if(!list_it_is_valid(it)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
if (it->cur->next == 0) {
|
if (it->cur->next == 0) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
@ -551,6 +661,10 @@ bool list_it_next(IntListIterator it) {
|
||||||
* @return `True` if the list iterator could proceed to the previous list node, `false` otherwise.
|
* @return `True` if the list iterator could proceed to the previous list node, `false` otherwise.
|
||||||
*/
|
*/
|
||||||
bool list_it_previous(IntListIterator it) {
|
bool list_it_previous(IntListIterator it) {
|
||||||
|
if(!list_it_is_valid(it)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
if (it->cur->prev == 0) {
|
if (it->cur->prev == 0) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue