sglib.h
provides generic implementation of most
common algorithms for arrays, lists, sorted lists and red-black trees.
Implementation of double linked lists and hashed tables is envisaged.
Also suggestions for new useful functionalities are welcomed.
The library is generic and it does not define its own data
structures. Rather it acts on existing user defined data structures
via a generic interface. It also does not allocate or deallocate any
memory and does not depend on any particular memory management. In
case od several datatypes, sglib even does not impose its own data
representation. For example, sglib list routines can be applied to any
user defined structure containing a pointer to the same
structure as its field.
All algorithms are implemented in form of macros parametrized by the type of data structure and comparator function (or comparator macro). Several further generic parameters such as the name of 'next' field for linked lists may be required for some algorithms and data structures.
Sglib offers access to algorithms in two level user interface. A level - 0 interface is simply a collection of useful macros. If you do not like large macros or you afraid introduction of symbol clashes after macro expansions you can use a level - 1 interface. This interface generates legal C functions for each particular type. Those functions can be called from the main program without worrying about unwanted effects due to macro expansions.
You can always use level - 0 interface. You can use level - 1 interface only if your base type is named by a single identifier, or if you have defined a typedef for it. It is a question of taste whether you decide to use one of two interfaces. It seems that you get the most advantages by using both interfaces in the same time. You can do this without worrying about implementation clashes, the level - 1 inplementation are just wrappers to level - 0 interface. However, few functions using recursion (red-black trees for example) are implemented exclusively in level - 1 interface.
During the design and implementation of sglib we have followed following rules:
#define SGLIB_NUMERIC_COMPARATOR(x, y) ((int)((x) - (y)))is a comparator for integers numbers. By the way, the macro
SGLIB_NUMERIC_COMPARATOR
with this definition
is predefined in sglib
and you can use it withount need of your own redefinitions.
cmp
is a comparator and subcmp
is its subcomparator, then:
cmp(x,y) < 0
implies subcmp(x,y) <= 0
cmp(x,y) > 0
implies subcmp(x,y) >= 0
#define strsubcmp(x, y) (x[0] - y[0])Using this subcomparator we can iterate over all strings starting with the same letter.
#define SGLIB_ARRAY_ELEMENTS_EXCHANGER(type, a, i, j) {type tmp;tmp=a[i];a[i]=a[j];a[j]=tmp;}is an elem_exchanger usable by sglib. By the way, the macro
SGLIB_ARRAY_ELEMENTS_EXCHANGER
with this definition
is predefined in the sglib and you can use in implementations of your own
elem_exchangers.
An elem_exchanger can be used to parametrize sorting
algorithms. The motivation is that
in many projects, several arrays keep related informations.
Elemens of different arrays having the same index are related to each other
and they form a single record. For example, one can represent a phone annuary by
keeping person names in one array (say name) and corresponding phone
numbers in another array (say phoneNumbers). In this representation the person
name[i]
has the phone number phoneNumber[i]
.
If you decide to sort your annuary alphabetically by names,
you have to make corresponding reordering also on numbers.
Sglib modifies arrays exclusively by using an elem_exchanger. You can use your own elem_exchanger as parameter for sorting algorithms. Your implementation can simultaneously exchange elements in several arrays, and hence make sorting to act on multiple related arrays. For example, continuing the annuary example, we can define the following elem_exchanger:
#define ANNUARY_EXCHANGER(type, a, i, j) { SGLIB_ARRAY_ELEMENTS_EXCHANGER(char *, name, i, j); SGLIB_ARRAY_ELEMENTS_EXCHANGER(int, phoneNumber, i, j);}and use it as parameter of a sorting macro. For example we can sort the first 1000 elements of the annuary by the following command:
SGLIB_ARRAY_QUICK_SORT(char*, name, 1000, strcmp, ANNUARY_EXCHANGER);
struct myintlist { int value; struct myintlist *next; }; struct history { int order; struct historyelem *h; // ... any other records struct history *previous; }; // you can even consider special trees as linked lists struct mytreenode { int nodetype; union nodeinformations node; struct mytrenode **subtrees; }; |
next
, previous
and subtrees[1]
.
The difference between pointer and comparator equality remains the
difference between ==
and equals
operators in Java language (with
the difference that in sglib user has to implement its own comparator).
E
is a pointer equal member of a container if it is physically
part of the data structure, i.e. if the container contains the pointer to E
.
We say that an element E
is a comparator equal member, if the container contains
an element which is comparator equal to E
.
In other words, an element is a comparator equal member of a container
if the container contains an element with the same key. Note that if an element
is a pointer equal member then it is also a comparator equal member.
struct mydoublelinkedlist { int value; struct mydoublelinkedlist *previous, *next; }; struct history { int order; struct historyelem *h; // ... any other records struct history *up, *down; }; |
previous
and next
. For the second structure
those parameters will be up
and down
.
struct myTreeNode { int key; struct myTreeNode *left; struct myTreeNode *right; }; struct generalTree { struct nodeInfo onfo; struct generalTree **subtrees; }; // you can have a structure which is a tree and a list at the same time struct listAndTree { int key; struct listAndTree *left_ptr; struct listAndTree *right_ptr; struct listAndTree *next_ptr; }; |
left, right
then subtrees[0], subtrees[1]
and finally
left_ptr, right_ptr
.
struct myTreeNode { int key; char color; struct myTreeNode *left; struct myTreeNode *right; }; struct TreeWithOneColorBit { struct { unsigned key:31; unsigned blackLabel:1; } bits; struct TreeWithOneColorBit *left; struct TreeWithOneColorBit *right; }; |
color
and bits.blackLabel
.
By convention, names of all macros start by SGLIB_ prefix. Then goes the identification of the data structure on which the macro operates and finaly the action performed by the macro.
In the design of macros we tried to make macros as generic as
possible. This sometimes leads to parameters which may seems useless.
However, because macro expansion is done in compile time and the
number of macro parameters does not affect the efficiency of the code,
we thing that additional parameters do not matter.
SGLIB_ARRAY_SINGLE_QUICK_SORT
| macro |
SGLIB_ARRAY_SINGLE_QUICK_SORT(type, a, max, comparator)
sort a single array using quicksort.
|
SGLIB_ARRAY_SINGLE_HEAP_SORT
| macro |
SGLIB_ARRAY_SINGLE_HEAP_SORT(type, a, max, comparator)
sort a single array using heapsort.
|
SGLIB_ARRAY_QUICK_SORT
| macro |
SGLIB_ARRAY_QUICK_SORT(type, a, max, comparator, elem_exchanger)
sort possibly multiple arrays using quicksort.
|
SGLIB_ARRAY_HEAP_SORT
| macro |
SGLIB_ARRAY_HEAP_SORT(type, a, max, comparator, elem_exchanger)
sort possibly multiple arrays using heapsort.
|
SGLIB_ARRAY_BINARY_SEARCH
| macro |
SGLIB_ARRAY_BINARY_SEARCH(type, a, start_index, end_index, key, comparator, found, result_index)
find the key in a sorted array using binary search.
|
SGLIB_LIST_ADD
| macro |
SGLIB_LIST_ADD(type, list, elem, next)
add an element to a list.
|
SGLIB_LIST_ADD_IF_NOT_MEMBER
| macro |
SGLIB_LIST_ADD_IF_NOT_MEMBER(type, list, elem, comparator, next, member)
add an element to a list if there is no comparator equal element inside.
|
SGLIB_LIST_CONCAT
| macro |
SGLIB_LIST_CONCAT(type, first, second, next)
concatenate two lists by appending the second at the end of the first.
|
SGLIB_LIST_DELETE
| macro |
SGLIB_LIST_DELETE(type, list, elem, next)
delete an element from a list. The element must be a pointer equal member of the list.
|
SGLIB_LIST_DELETE_IF_MEMBER
| macro |
SGLIB_LIST_DELETE_IF_MEMBER(type, list, elem, comparator, next, member)
remove a comparator equal element from a list.
|
SGLIB_LIST_IS_MEMBER
| macro |
SGLIB_LIST_IS_MEMBER(type, list, elem, next, result)
determine whether an element is a pointer member of a list.
|
SGLIB_LIST_FIND_MEMBER
| macro |
SGLIB_LIST_FIND_MEMBER(type, list, elem, comparator, next, result)
determine whether there is a comparator equal element in a list.
|
SGLIB_LIST_LEN
| macro |
SGLIB_LIST_LEN(type, list, next, result)
compute the length of a list.
|
SGLIB_LIST_MAP_ON_ELEMENTS
| macro |
SGLIB_LIST_MAP_ON_ELEMENTS(type, list, var, next, command)
apply a command on all elements of a list.
|
SGLIB_LIST_REVERSE
| macro |
SGLIB_LIST_REVERSE(type, list, next)
reverse a list.
|
SGLIB_LIST_SORT
| macro |
SGLIB_LIST_SORT(type, list, comparator, next)
sort a list using mergesort.
|
SGLIB_SORTED_LIST_ADD
| macro |
SGLIB_SORTED_LIST_ADD(type, list, elem, comparator, next)
insert an element into a sorted list.
|
SGLIB_SORTED_LIST_ADD_IF_NOT_MEMBER
| macro |
SGLIB_SORTED_LIST_ADD_IF_NOT_MEMBER(type, list, elem, comparator, next, member)
insert an element into a sorted list if there is no comparator equal element inside.
|
SGLIB_SORTED_LIST_DELETE
| macro |
SGLIB_SORTED_LIST_DELETE(type, list, elem, next)
delete an element from a sorted list. The element must be a pointer equal member of the list.
|
SGLIB_SORTED_LIST_DELETE_IF_MEMBER
| macro |
SGLIB_SORTED_LIST_DELETE_IF_MEMBER(type, list, elem, comparator, next, member)
remove a comparator equal element from a sorted list.
|
SGLIB_SORTED_LIST_IS_MEMBER
| macro |
SGLIB_SORTED_LIST_IS_MEMBER(type, list, elem, comparator, next, result)
determine whether an element is a pointer member of a sorted list.
|
SGLIB_SORTED_LIST_FIND_MEMBER
| macro |
SGLIB_SORTED_LIST_FIND_MEMBER(type, list, elem, comparator, next, result)
determine whether an element is a comparator member of a sorted list.
|
SGLIB_SORTED_LIST_FIND_MEMBER_OR_PLACE
| macro |
SGLIB_SORTED_LIST_FIND_MEMBER_OR_PLACE(type, list, elem, comparator, next, comparator_result, member_ptr)
determine whether an element is a comparator member of a sorted list, if not, find the place where to insert it.
|
SGLIB_SORTED_LIST_LEN
| macro |
SGLIB_SORTED_LIST_LEN(type, list, next, result)
compute the length of a list.
|
SGLIB_SORTED_LIST_MAP_ON_ELEMENTS
| macro |
SGLIB_SORTED_LIST_MAP_ON_ELEMENTS(type, list, var, next, command)
apply a command on all elements of a list.
|
SGLIB_DL_LIST_ADD
| macro |
SGLIB_DL_LIST_ADD(type, list, elem, previous, next)
add an element to a list. |
SGLIB_DL_LIST_ADD_BEFORE
| macro |
SGLIB_DL_LIST_ADD_BEFORE(type, list, elem, previous, next)
add an element to a list. Elem will be inserted before the element pointed by list .
|
SGLIB_DL_LIST_ADD_AFTER
| macro |
SGLIB_DL_LIST_ADD_AFTER(type, list, elem, previous, next)
add an element to a list. Elem will be inserted after the element pointed by list .
|
SGLIB_DL_LIST_ADD_IF_NOT_MEMBER
| macro |
SGLIB_DL_LIST_ADD_IF_NOT_MEMBER(type, list, elem, comparator, previous, next, member)
add an element to a list if there is no comparator equal element inside.
|
SGLIB_DL_LIST_ADD_BEFORE_IF_NOT_MEMBER
| macro |
SGLIB_DL_LIST_ADD_BEFORE_IF_NOT_MEMBER(type, list, elem, comparator, previous, next, member)
add an element to a list if there is no comparator equal element inside. Elem will be inserted before the element pointed by list .
|
SGLIB_DL_LIST_ADD_AFTER_IF_NOT_MEMBER
| macro |
SGLIB_DL_LIST_ADD_AFTER_IF_NOT_MEMBER(type, list, elem, comparator, previous, next, member)
add an element to a list if there is no comparator equal element inside. Elem will be inserted after the element pointed by list .
|
SGLIB_DL_LIST_CONCAT
| macro |
SGLIB_DL_LIST_CONCAT(type, first, second, previous, next)
concatenate two lists by appending the second at the end of the first. |
SGLIB_DL_LIST_DELETE
| macro |
SGLIB_DL_LIST_DELETE(type, list, elem, previous, next)
delete an element from a list. The element must be a pointer equal member of the list. |
SGLIB_DL_LIST_DELETE_IF_MEMBER
| macro |
SGLIB_DL_LIST_DELETE_IF_MEMBER(type, list, elem, comparator, previous, next, member)
remove a comparator equal element from a list.
|
SGLIB_DL_LIST_IS_MEMBER
| macro |
SGLIB_DL_LIST_IS_MEMBER(type, list, elem, previous, next, result)
determine whether an element is a pointer member of a list.
|
SGLIB_DL_LIST_FIND_MEMBER
| macro |
SGLIB_DL_LIST_FIND_MEMBER(type, list, elem, comparator, previous, next, result)
determine whether there is a comparator equal element in a list.
|
SGLIB_DL_LIST_GET_FIRST
| macro |
SGLIB_DL_LIST_GET_FIRST(type, list, previous, next, result)
get the first element of a list. |
SGLIB_DL_LIST_GET_LAST
| macro |
SGLIB_DL_LIST_GET_LAST(type, list, previous, next, result)
get the last element of a list. |
SGLIB_DL_LIST_LEN
| macro |
SGLIB_DL_LIST_LEN(type, list, previous, next, result)
compute the length of a list. |
SGLIB_DL_LIST_MAP_ON_ELEMENTS
| macro |
SGLIB_DL_LIST_MAP_ON_ELEMENTS(type, list, var, previous, next, command)
apply a command on all elements of a list. Command will be repeatedly executed for each element of the list accessible via the previous field and then via the next field. The current element of the list is stored in the
variable var .
|
SGLIB_DL_LIST_REVERSE
| macro |
SGLIB_DL_LIST_REVERSE(type, list, previous, next)
reverse a list. |
SGLIB_DL_LIST_SORT
| macro |
SGLIB_DL_LIST_SORT(type, list, comparator, previous, next)
sort a list using mergesort. As a side effect the list is set to the first element of the list.
|
SGLIB_BIN_TREE_MAP_ON_ELEMENTS
| macro |
SGLIB_BIN_TREE_MAP_ON_ELEMENTS(type, tree, var, left, right, command)
traverse a binary tree and apply command on each element. This is non-recursive implementation of tree traversal. It maintains the path to the current node in the array _path_ , the _path_[0] contains the root of the tree. The _path_[_pathi_-1] contains the parent of the var . The maximal deep of the tree is limited by SGLIB_MAX_TREE_DEEP macro.
|
Functions generated by above macros:
|
sglib_type_array_quick_sort
| function |
sglib_type_array_quick_sort(type *a, int max)
sort an array using quicksort.
|
sglib_type_array_heap_sort
| function |
sglib_type_array_heap_sort(type *a, int max)
sort an array using heapsort.
|
Hashed containers are provided only in level-1 interface because they
require a uniform interface for operations applied on the base container.
Functions generated by above macros:
|
sglib_hashed_type_init
| function |
void sglib_hashed_type_init(type *table[dim])
set each cell in the table to NULL.
|
sglib_hashed_type_add
| function |
void sglib_hashed_type_add(type *table[dim], type *elem)
Add an element into the hashed container.
|
sglib_hashed_type_add_if_not_member
| function |
int sglib_hashed_type_add_if_not_member(type *table[dim], type *elem, type **member)
Add an element into the hashed container if there is no comparator equal element inside.
|
sglib_hashed_type_delete
| function |
void sglib_hashed_type_delete(type *table[dim], type *elem)
delete an element from a hashed container. The element must be a pointer equal member of the hashed container.
|
sglib_hashed_type_delete_if_member
| function |
int sglib_hashed_type_delete_if_member(type *table[dim], type *elem, type **member)
find a comparator equal element in the hashed container and remove it.
|
sglib_hashed_type_is_member
| function |
int sglib_hashed_type_is_member(type *table[dim], type *elem)
determine whether an element is inside a hashed container. The element is searched using pointer equality.
|
sglib_hashed_type_find_member
| function |
type *sglib_hashed_type_find_member(type *table[dim], type *elem)
find an element in the hashed container. The element is searched using comparator equality.
|
sglib_hashed_type_it_init
| function |
type *sglib_hashed_type_it_init(struct sglib_type_iterator *it, type *table[dim])
initialize an iterator it to run over elements of table .
|
sglib_hashed_type_it_init_on_equal
| function |
type *sglib_hashed_type_it_init_on_equal(struct sglib_type_iterator *it, type *table[dim], int (*subcomparator)(type *, type *), type *equalto)
initialize an iterator it to run over those elements of table which are
equal to equalto . The equality is considered with respect to the
subcomparator which must be a subcomparator
of the base container comparator.
|
sglib_hashed_type_it_next
| function |
type *sglib_hashed_type_it_next(struct sglib_type_iterator *it)
get the next element from the iterator it .
|
Functions generated by above macros:
|
sglib_type_add
| function |
void sglib_type_add(type **list, type *elem)
insert an element into a list.
|
sglib_type_add_if_not_member
| function |
int sglib_type_add_if_not_member(type **list, type *elem, type **member)
insert an element if there is no comparator equal element in the list.
|
sglib_type_concat
| function |
void sglib_type_concat(type **first, type *second)
concatenate two lists by appending second at the end of the first.
|
sglib_type_delete
| function |
void sglib_type_delete(type **list, type *elem)
delete an element. The element must be a member of the list, it is looked using the pointer equality, not equality generated by comparator.
|
sglib_type_delete_if_member
| function |
int sglib_type_delete_if_member(type **list, type *elem, type **result)
find a comparator equal element in the list and remove it.
|
sglib_type_is_member
| function |
int sglib_type_is_member(type *list, type *elem)
determine whether an element is inside a list. The element is searched using pointer equality.
|
sglib_type_find_member
| function |
type *sglib_type_find_member(type **list, type *elem)
find an element in the list. The element is searched using comparator equality.
|
sglib_type_len
| function |
int sglib_type_len(type *list)
compute the length of a list.
|
sglib_type_sort
| function |
void sglib_type_sort(type **list)
sort the list according to comparator.
|
sglib_type_reverse
| function |
void sglib_type_reverse(type **list)
reverse the list.
|
sglib_type_it_init
| function |
type *sglib_type_it_init(struct sglib_type_iterator *it, type *list)
initialize an iterator it to run over elements of list .
|
sglib_type_it_init_on_equal
| function |
type *sglib_type_it_init_on_equal(struct sglib_type_iterator *it, type *list, int (*subcomparator)(type *, type *), type *equalto)
initialize an iterator it to run over those elements of list which are
equal to equalto . The equality is considered with respect to the
subcomparator which must be a subcomparator
of the comparator.
|
sglib_type_it_next
| function |
type *sglib_type_it_next(struct sglib_type_iterator *it)
get the next element from the iterator it .
|
Functions generated by above macros:
|
sglib_type_add
| function |
void sglib_type_add(type **list, type *elem)
insert an element into a list.
|
sglib_type_add_if_not_member
| function |
int sglib_type_add_if_not_member(type **list, type *elem, type **member)
insert an element if there is no comparator equal element in the list.
|
sglib_type_delete
| function |
void sglib_type_delete(type **list, type *elem)
delete an element. The element must be a member of the list, it is looked using the pointer equality, not equality generated by comparator.
|
sglib_type_delete_if_member
| function |
int sglib_type_delete_if_member(type **list, type *elem, type **result)
find a comparator equal element in the list and remove it.
|
sglib_type_is_member
| function |
int sglib_type_is_member(type *list, type *elem)
determine whether an element is inside a list. The element is searched using pointer equality.
|
sglib_type_find_member
| function |
type *sglib_type_find_member(type **list, type *elem)
find an element in the list. The element is searched using comparator equality.
|
sglib_type_len
| function |
int sglib_type_len(type *list)
compute the length of a list.
|
sglib_type_sort
| function |
void sglib_type_sort(type **list)
sort the list according to comparator. This function does not logically belong to this datatype as it is supposed that lists are kept sorted. However, it can be used to initial sorting, when the list was created by other than sglib functions.
|
sglib_type_it_init
| function |
type *sglib_type_it_init(struct sglib_type_iterator *it, type *list)
initialize an iterator it to run over elements of list .
|
sglib_type_it_init_on_equal
| function |
type *sglib_type_it_init_on_equal(struct sglib_type_iterator *it, type *list, int (*subcomparator)(type *, type *), type *equalto)
initialize an iterator it to run over those elements of list which are
equal to equalto . The equality is considered with respect to the
subcomparator which must be a subcomparator
of the comparator.
|
sglib_type_it_next
| function |
type *sglib_type_it_next(struct sglib_type_iterator *it)
get the next element from the iterator it .
|
Functions generated by above macros:
|
sglib_type_add
| function |
void sglib_type_add(type **list, type *elem)
insert an element into a list.
|
sglib_type_add_before
| function |
void sglib_type_add_before(type **list, type *elem)
insert an element into a list. Elem will be inserted before the element pointed by *list .
|
sglib_type_add_after
| function |
void sglib_type_add_after(type **list, type *elem)
insert an element into a list. Elem will be inserted after the element pointed by *list .
|
sglib_type_add_if_not_member
| function |
int sglib_type_add_if_not_member(type **list, type *elem, type **member)
insert an element if there is no comparator equal element in the list.
|
sglib_type_add_before_if_not_member
| function |
int sglib_type_add_before_if_not_member(type **list, type *elem)
insert an element if there is no comparator equal element in the list. Elem will be inserted before the element pointed by *list .
|
sglib_type_add_after_if_not_member
| function |
int sglib_type_add_after_if_not_member(type **list, type *elem)
insert an element if there is no comparator equal element in the list. Elem will be inserted before the element pointed by *list .
|
sglib_type_concat
| function |
void sglib_type_concat(type **first, type *second)
concatenate two lists by appending second at the end of the first.
|
sglib_type_delete
| function |
void sglib_type_delete(type **list, type *elem)
delete an element. The element must be a pointer equal member of the list.
|
sglib_type_delete_if_member
| function |
int sglib_type_delete_if_member(type **list, type *elem, type **result)
find a comparator equal element in the list and remove it.
|
sglib_type_is_member
| function |
int sglib_type_is_member(type *list, type *elem)
determine whether an element is inside a list. The element is searched using pointer equality.
|
sglib_type_find_member
| function |
type *sglib_type_find_member(type **list, type *elem)
find an element in the list. The element is searched using comparator equality.
|
sglib_type_get_first
| function |
type *sglib_type_get_first(type *list)
get the first element of a list.
|
sglib_type_get_last
| function |
type *sglib_type_get_last(type *list)
get the last element of a list.
|
sglib_type_len
| function |
int sglib_type_len(type *list)
compute the length of a list.
|
sglib_type_sort
| function |
void sglib_type_sort(type **list)
sort the list according to comparator. After the sorting *list will point to the first element of the list.
|
sglib_type_reverse
| function |
void sglib_type_reverse(type **list)
reverse the list.
|
sglib_type_it_init
| function |
type *sglib_type_it_init(struct sglib_type_iterator *it, type *list)
initialize an iterator it to run over elements of list .
|
sglib_type_it_init_on_equal
| function |
type *sglib_type_it_init_on_equal(struct sglib_type_iterator *it, type *list, int (*subcomparator)(type *, type *), type *equalto)
initialize an iterator it to run over those elements of list which are
equal to equalto . The equality is considered with respect to the
subcomparator which must be a subcomparator
of the comparator.
|
sglib_type_it_next
| function |
type *sglib_type_it_next(struct sglib_type_iterator *it)
get the next element from the iterator it .
|
Functions generated by above macros:
|
sglib_type_add
| function |
void sglib_type_add(type **tree, type *elem)
insert an element into a tree.
|
sglib_type_add_if_not_member
| function |
int sglib_type_add_if_not_member(type **tree, type *elem, type **member)
insert an element if there is no comparator equal element in the tree.
|
sglib_type_delete
| function |
void sglib_type_delete(type **tree, type *elem)
delete an element. The element must be a member of the tree, it is looked using the pointer equality, not equality generated by comparator.
|
sglib_type_delete_if_member
| function |
int sglib_type_delete_if_member(type **tree, type *elem, type **result)
find a comparator equal element in the tree and remove it.
|
sglib_type_is_member
| function |
int sglib_type_is_member(type *tree, type *elem)
determine whether an element is inside a tree. The element is searched using pointer equality.
|
sglib_type_find_member
| function |
type *sglib_type_find_member(type **tree, type *elem)
find an element in the tree. The element is searched using comparator equality.
|
sglib_type_len
| function |
int sglib_type_len(type *tree)
compute the length of a tree, i.e. compute how many elements is inside.
|
sglib_type_it_init
| function |
type *sglib_type_it_init(struct sglib_type_iterator *it, type *tree)
initialize an iterator it to run over elements of tree .
|
sglib_type_it_init_on_equal
| function |
type *sglib_type_it_init_on_equal(struct sglib_type_iterator *it, type *tree, int (*subcomparator)(type *, type *), type *equalto)
initialize an iterator it to run over those elements of the tree which are
equal to equalto . The equality is considered with respect to the
subcomparator which must be a subcomparator
of the comparator.
|
sglib_type_it_next
| function |
type *sglib_type_it_next(struct sglib_type_iterator *it)
get the next element from the iterator it .
|
// This program sorts its parameters using // array sort level 0 interface. // For example: // a.out 6 7 3 4 1 5 // writes // 1 3 4 5 6 7 #include <stdio.h> #include <stdlib.h> #include "sglib.h" #define MAX_ELEMS 1000 int main(int argc, char **argv) { int i,size; int a[MAX_ELEMS]; size = argc-1; for (i=0; i<size; i++) { sscanf(argv[i+1],"%d", &a[i]); } SGLIB_ARRAY_SINGLE_QUICK_SORT(int, a, size, SGLIB_NUMERIC_COMPARATOR); for (i=0; i<size; i++) { printf("%d ", a[i]); } printf("\n"); return(0); } |
// This program sorts its parameters using // array sort level 1 interface. // For example: // a.out 6 7 3 4 1 5 // writes // 1 3 4 5 6 7 #include <stdio.h> #include <stdlib.h> #include "sglib.h" #define MAX_ELEMS 1000 SGLIB_DEFINE_ARRAY_SORTING_FUNCTIONS(int, SGLIB_NUMERIC_COMPARATOR) int main(int argc, char **argv) { int i,size; int a[MAX_ELEMS]; size = argc-1; for (i=0; i<size; i++) { sscanf(argv[i+1],"%d", &a[i]); } sglib_int_array_heap_sort(a, size); for (i=0; i<size; i++) { printf("%d ", a[i]); } printf("\n"); return(0); } |
// This program sorts its parameters using // binary search to implement insert sort. // For example: // a.out 6 7 3 4 1 5 // writes // 1 3 4 5 6 7 #include <stdio.h> #include <stdlib.h> #include <string.h> #include "sglib.h" #define MAX_ELEMS 1000 int main(int argc, char **argv) { int i, size, found, index, tmp; int a[MAX_ELEMS]; size = argc-1; for (i=0; i<size; i++) { sscanf(argv[i+1],"%d", &a[i]); } for(i=1; i<size; i++) { tmp = a[i]; SGLIB_ARRAY_BINARY_SEARCH(int, a, 0, i, tmp, SGLIB_NUMERIC_COMPARATOR, found, index); memmove(a+index+1, a+index, (i-index)*sizeof(int)); a[index]=tmp; } for (i=0; i<size; i++) { printf("%d ", a[i]); } printf("\n"); return(0); } |
// This program sorts its parameters using // list sort (level 0 interface). // For example: // a.out 6 7 3 4 1 5 // writes // 1 3 4 5 6 7 #include <stdio.h> #include <stdlib.h> #include <malloc.h> #include "sglib.h" struct ilist { int i; struct ilist *next_ptr; }; #define ILIST_COMPARATOR(e1, e2) (e1->i - e2->i) int main(int argc, char **argv) { int i,a; struct ilist *l, *the_list, *ll; the_list = NULL; for (i=1; i<argc; i++) { sscanf(argv[i],"%d", &a); l = malloc(sizeof(struct ilist)); l->i = a; SGLIB_LIST_ADD(struct ilist, the_list, l, next_ptr); } // it is useless, but anyway, get parameters in the right order SGLIB_LIST_REVERSE(struct ilist, the_list, next_ptr); // now sort them SGLIB_LIST_SORT(struct ilist, the_list, ILIST_COMPARATOR, next_ptr); // print the list SGLIB_LIST_MAP_ON_ELEMENTS(struct ilist, the_list, ll, next_ptr, { printf("%d ", ll->i); }); printf("\n"); // free all SGLIB_LIST_MAP_ON_ELEMENTS(struct ilist, the_list, ll, next_ptr, { free(ll); }); return(0); } |
// This program sorts its parameters using // insertion into sorted list (level 0 interface). // For example: // a.out 6 7 3 4 1 5 // writes // 1 3 4 5 6 7 #include <stdio.h> #include <stdlib.h> #include <malloc.h> #include "sglib.h" struct ilist { int i; struct ilist *next_ptr; }; #define ILIST_COMPARATOR(e1, e2) (e1->i - e2->i) int main(int argc, char **argv) { int i,a; struct ilist *l, *the_list, *ll; the_list = NULL; for (i=1; i<argc; i++) { sscanf(argv[i],"%d", &a); l = malloc(sizeof(struct ilist)); l->i = a; // insert the new element into the list while keeping it sorted SGLIB_SORTED_LIST_ADD(struct ilist, the_list, l, ILIST_COMPARATOR, next_ptr); } SGLIB_LIST_MAP_ON_ELEMENTS(struct ilist, the_list, ll, next_ptr, { printf("%d ", ll->i); }); printf("\n"); SGLIB_LIST_MAP_ON_ELEMENTS(struct ilist, the_list, ll, next_ptr, { free(ll); }); return(0); } |
// This program sorts its parameters using // insertion into sorted list (level 1 interface). // For example: // a.out 6 7 3 4 1 5 // writes // 1 3 4 5 6 7 #include <stdio.h> #include <stdlib.h> #include <malloc.h> #include "sglib.h" typedef struct ilist { int i; struct ilist *next_ptr; } iListType; #define ILIST_COMPARATOR(e1, e2) (e1->i - e2->i) SGLIB_DEFINE_SORTED_LIST_PROTOTYPES(iListType, ILIST_COMPARATOR, next_ptr) SGLIB_DEFINE_SORTED_LIST_FUNCTIONS(iListType, ILIST_COMPARATOR, next_ptr) int main(int argc, char **argv) { int i,a; struct ilist *l, *the_list; struct sglib_iListType_iterator it; the_list = NULL; for (i=1; i<argc; i++) { sscanf(argv[i],"%d", &a); l = malloc(sizeof(struct ilist)); l->i = a; // insert the new element into the list while keeping it sorted sglib_iListType_add(&the_list, l); } // print the list for (l=the_list; l!=NULL; l=l->next_ptr) { printf("%d ", l->i); } printf("\n"); // free all for(l=sglib_iListType_it_init(&it,the_list); l!=NULL; l=sglib_iListType_it_next(&it)) { free(l); } return(0); } |
// This program reads parameters, sorts them // and write them in both directions. // The program is using level 1 interface. // For example: // a.out 6 7 3 4 1 5 // writes // 1 3 4 5 6 7 // 7 6 5 4 3 1 #include <stdio.h> #include <stdlib.h> #include <malloc.h> #include "sglib.h" typedef struct dllist { int i; struct dllist *ptr_to_next; struct dllist *ptr_to_previous; } dllist; #define DLLIST_COMPARATOR(e1, e2) (e1->i - e2->i) SGLIB_DEFINE_DL_LIST_PROTOTYPES(dllist, DLLIST_COMPARATOR, ptr_to_previous, ptr_to_next); SGLIB_DEFINE_DL_LIST_FUNCTIONS(dllist, DLLIST_COMPARATOR, ptr_to_previous, ptr_to_next); int main(int argc, char **argv) { int i,a; dllist *l, *the_list; struct sglib_dllist_iterator it; the_list = NULL; for (i=1; i<argc; i++) { sscanf(argv[i],"%d", &a); l = malloc(sizeof(dllist)); l->i = a; sglib_dllist_add(&the_list, l); } // sort the list sglib_dllist_sort(&the_list); // print the list for(l=sglib_dllist_get_first(the_list); l!=NULL; l=l->ptr_to_next) printf("%d ", l->i); printf("\n"); // print the list in reversed direction for(l=sglib_dllist_get_last(the_list); l!=NULL; l=l->ptr_to_previous) printf("%d ", l->i); printf("\n"); // free the list for(l=sglib_dllist_it_init(&it,the_list); l!=NULL; l=sglib_dllist_it_next(&it)) { free(l); } return(0); } |
// This program uses hash table containing lists // to remove multiple occurences of its parameters // For example: // a.out 1 3 1 5 2 3 1 7 11 33 11 // writes: // 11 1 2 33 3 5 7 #include <stdio.h> #include <stdlib.h> #include <malloc.h> #include "sglib.h" #define HASH_TAB_SIZE 10 typedef struct ilist { int i; struct ilist *next; } ilist; ilist *htab[HASH_TAB_SIZE]; #define ILIST_COMPARATOR(e1, e2) (e1->i - e2->i) unsigned int ilist_hash_function(ilist *e) { return(e->i); } SGLIB_DEFINE_LIST_PROTOTYPES(ilist, ILIST_COMPARATOR, next) SGLIB_DEFINE_LIST_FUNCTIONS(ilist, ILIST_COMPARATOR, next) SGLIB_DEFINE_HASHED_CONTAINER_PROTOTYPES(ilist, HASH_TAB_SIZE, ilist_hash_function) SGLIB_DEFINE_HASHED_CONTAINER_FUNCTIONS(ilist, HASH_TAB_SIZE, ilist_hash_function) int main(int argc, char **argv) { int i, ai,aj, n; struct ilist ii, *nn, *ll; struct sglib_hashed_ilist_iterator it; sglib_hashed_ilist_init(htab); for (i=1; i<argc; i++) { sscanf(argv[i],"%d", &n); ii.i = n; if (sglib_hashed_ilist_find_member(htab, &ii) == NULL) { nn = malloc(sizeof(struct ilist)); nn->i = n; sglib_hashed_ilist_add(htab, nn); } } for(ll=sglib_hashed_ilist_it_init(&it,htab); ll!=NULL; ll=sglib_hashed_ilist_it_next(&it)) { printf("%d ", ll->i); } printf("\n"); for(ll=sglib_hashed_ilist_it_init(&it,htab); ll!=NULL; ll=sglib_hashed_ilist_it_next(&it)) { free(ll); } return(0); } |
// This program uses red-black tree to // remove multiple occurences of the same // value from its paramaters. // For example: // a.out 6 7 3 4 1 4 1 3 5 // writes: // 1 3 4 5 6 7 #include <stdio.h> #include <stdlib.h> #include "sglib.h" typedef struct rbtree { int n; char color_field; struct rbtree *left; struct rbtree *right; } rbtree; #define CMPARATOR(x,y) ((x->n)-(y->n)) SGLIB_DEFINE_RBTREE_PROTOTYPES(rbtree, left, right, color_field, CMPARATOR); SGLIB_DEFINE_RBTREE_FUNCTIONS(rbtree, left, right, color_field, CMPARATOR); int main(int argc, char **argv) { int i,a; struct rbtree e, *t, *the_tree, *te; struct sglib_rbtree_iterator it; the_tree = NULL; for (i=1; i<argc; i++) { sscanf(argv[i],"%d", &a); e.n = a; if (sglib_rbtree_find_member(the_tree, &e)==NULL) { t = malloc(sizeof(struct rbtree)); t->n = a; sglib_rbtree_add(&the_tree, t); } } for(te=sglib_rbtree_it_init_inorder(&it,the_tree); te!=NULL; te=sglib_rbtree_it_next(&it)) { printf("%d ", te->n); } printf("\n"); for(te=sglib_rbtree_it_init(&it,the_tree); te!=NULL; te=sglib_rbtree_it_next(&it)) { free(te); } return(0); } |