Algorithms_in_C  1.0.0
Set of algorithms implemented in C.
segment_tree.c File Reference

segment trees with only point updates More...

#include <assert.h>
#include <inttypes.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
Include dependency graph for segment_tree.c:

Data Structures

struct  segment_tree
 This structures holds all the data that is required by a segment tree. More...
 

Typedefs

typedef void(* combine_function) (const void *a, const void *b, void *result)
 Function that combines two data to generate a new one The name of function might be misleading actually combine here signifies the fact that in segment trees we take partial result from two ranges and using partial results we derive the result for joint range of those two ranges For Example: array(1,2,3,4,5,6) sum of range [0,2] = 6 and sum of range [3,5] = 15 the combined sum of two range is 6+15=21. More...
 
typedef struct segment_tree segment_tree
 This structures holds all the data that is required by a segment tree.
 

Functions

void segment_tree_build (segment_tree *tree)
 Builds a Segment tree It is assumed that leaves of tree already contains data. More...
 
void segment_tree_update (segment_tree *tree, size_t index, void *val)
 For point updates This function updates the element at given index and also updates segment tree accordingly. More...
 
void segment_tree_query (segment_tree *tree, long long l, long long r, void *res)
 Query the segment tree This function helps in range query of segment tree This function assumes that the given range is valid Performs the query in range [l,r]. More...
 
segment_treesegment_tree_init (void *arr, size_t elem_size, size_t len, void *identity, combine_function func)
 Initializes Segment Tree Accquires memory for segment tree and fill the leaves of segment tree with data from array. More...
 
void segment_tree_dispose (segment_tree *tree)
 Dispose Segment Tree Frees all heap memory accquired by segment tree. More...
 
void segment_tree_print_int (segment_tree *tree)
 Prints the data in segment tree The data should be of int type A utility to print segment tree with data type of int. More...
 
void minimum (const void *a, const void *b, void *c)
 Utility for test A function compare for minimum between two integers This function is used as combine_function for RMQ. More...
 
static void test ()
 Test RMQ Testing Segment tree using Range Minimum Queries. More...
 
int main ()
 Main Function. More...
 

Detailed Description

segment trees with only point updates

This code implements segment trees. Segment trees are general structures which allow range based queries in a given array in logN time. Segment tree with point updates allow update of single element in the array in logN time. Learn more about segment trees here

Author
Lakhan Nad

Typedef Documentation

◆ combine_function

typedef void(* combine_function) (const void *a, const void *b, void *result)

Function that combines two data to generate a new one The name of function might be misleading actually combine here signifies the fact that in segment trees we take partial result from two ranges and using partial results we derive the result for joint range of those two ranges For Example: array(1,2,3,4,5,6) sum of range [0,2] = 6 and sum of range [3,5] = 15 the combined sum of two range is 6+15=21.

Note
The function is same to binary function in Discrete Mathematics
Parameters
apointer to first data
bpointer to second data
resultpointer to memory location where result of combining a and b is to be stored

Function Documentation

◆ main()

int main ( void  )

Main Function.

Returns
0 on exit
232 {
233  test();
234  return 0;
235 }
static void test()
Test RMQ Testing Segment tree using Range Minimum Queries.
Definition: segment_tree.c:205
Here is the call graph for this function:

◆ minimum()

void minimum ( const void *  a,
const void *  b,
void *  c 
)

Utility for test A function compare for minimum between two integers This function is used as combine_function for RMQ.

Parameters
apointer to integer a
bpointer to integer b
cpointer where minimum of a and b is tored as result
195 {
196  *(int *)c = *(int *)a < *(int *)b ? *(int *)a : *(int *)b;
197 }

◆ segment_tree_build()

void segment_tree_build ( segment_tree tree)

Builds a Segment tree It is assumed that leaves of tree already contains data.

Parameters
treepointer to segment tree to be build
56 {
57  size_t elem_size = tree->elem_size;
58  int index = (tree->length - 2);
59  size_t b, l, r;
60  char *ptr = (char *)tree->root;
61  for (; index >= 0; index--)
62  {
63  b = index * elem_size;
64  l = (2 * index + 1) * elem_size;
65  r = (2 * index + 2) * elem_size;
66  tree->combine(ptr + l, ptr + r, ptr + b);
67  }
68 }
size_t length
total size of array which segment tree represents
Definition: segment_tree.c:43
combine_function combine
the function to be used to combine two node's data to form parent's data
Definition: segment_tree.c:47
void * root
the root of formed segment tree
Definition: segment_tree.c:40
size_t elem_size
size in bytes of each data element
Definition: segment_tree.c:42

◆ segment_tree_dispose()

void segment_tree_dispose ( segment_tree tree)

Dispose Segment Tree Frees all heap memory accquired by segment tree.

Parameters
treepointer to segment tree
163 {
164  free(tree->root);
165  free(tree->identity);
166 }
void * identity
identity element for combine function
Definition: segment_tree.c:41

◆ segment_tree_init()

segment_tree* segment_tree_init ( void *  arr,
size_t  elem_size,
size_t  len,
void *  identity,
combine_function  func 
)

Initializes Segment Tree Accquires memory for segment tree and fill the leaves of segment tree with data from array.

Parameters
arrthe array data upon which segment tree is build
elem_sizesize of each element in segment tree
lentotal no of elements in array
identitythe identity element for combine_function
functhe combine_function used to build segment tree
Returns
pointer to sgement tree build
142 {
143  segment_tree *tree = malloc(sizeof(segment_tree));
144  tree->elem_size = elem_size;
145  tree->length = len;
146  tree->combine = func;
147  tree->root = malloc(sizeof(char) * elem_size * (2 * len - 1));
148  tree->identity = malloc(sizeof(char) * elem_size);
149  char *ptr = (char *)tree->root;
150  memset(ptr, 0, (len - 1) * elem_size); // Initializing memory
151  ptr = ptr + (len - 1) * elem_size;
152  memcpy(ptr, arr, elem_size * len); // copy the leaf nodes i.e. array data
153  memcpy(tree->identity, identity, elem_size); // copy identity element
154  return tree;
155 }
void func(int sockfd)
Continuous loop to send and receive over the socket.
Definition: client.c:37
This structures holds all the data that is required by a segment tree.
Definition: segment_tree.c:39
Here is the call graph for this function:

◆ segment_tree_print_int()

void segment_tree_print_int ( segment_tree tree)

Prints the data in segment tree The data should be of int type A utility to print segment tree with data type of int.

Parameters
treepointer to segment tree
176 {
177  char *base = (char *)tree->root;
178  size_t i = 0;
179  for (; i < 2 * tree->length - 1; i++)
180  {
181  printf("%d ", *(int *)(base + i * tree->elem_size));
182  }
183  printf("\n");
184 }

◆ segment_tree_query()

void segment_tree_query ( segment_tree tree,
long long  l,
long long  r,
void *  res 
)

Query the segment tree This function helps in range query of segment tree This function assumes that the given range is valid Performs the query in range [l,r].

Parameters
treepointer to segment tree
lthe start of range
rthe end of range
resthe pointer to memory where result of query is stored
106 {
107  size_t elem_size = tree->elem_size;
108  memcpy(res, tree->identity, elem_size);
109  elem_size = tree->elem_size;
110  char *root = (char *)tree->root;
111  l += tree->length - 1;
112  r += tree->length - 1;
113  while (l <= r)
114  {
115  if (!(l & 1))
116  {
117  tree->combine(res, root + l * elem_size, res);
118  }
119  if (r & 1)
120  {
121  tree->combine(res, root + r * elem_size, res);
122  }
123  r = (r >> 1) - 1;
124  l = (l >> 1);
125  }
126 }

◆ segment_tree_update()

void segment_tree_update ( segment_tree tree,
size_t  index,
void *  val 
)

For point updates This function updates the element at given index and also updates segment tree accordingly.

Parameters
treepointer to segment tree
indexthe index whose element is to be updated (0 based indexing used)
valpointer to value that is to be replaced at given index
80 {
81  size_t elem_size = tree->elem_size;
82  index = index + tree->length - 1;
83  char *base = (char *)tree->root;
84  char *t = base + index * elem_size;
85  memcpy(t, val, elem_size);
86  while (index > 0)
87  {
88  index = ((index - 1) >> 1);
89  tree->combine(base + (2 * index + 1) * elem_size,
90  base + (2 * index + 2) * elem_size,
91  base + index * elem_size);
92  }
93 }

◆ test()

static void test ( void  )
static

Test RMQ Testing Segment tree using Range Minimum Queries.

Returns
void
206 {
207  int32_t arr[10] = {1, 0, 3, 5, 7, 2, 11, 6, -2, 8};
208  int32_t identity = __INT32_MAX__;
209  segment_tree *tree =
210  segment_tree_init(arr, sizeof(*arr), 10, &identity, minimum);
211  segment_tree_build(tree);
212  int32_t result;
213  segment_tree_query(tree, 3, 6, &result);
214  assert(result == 2);
215  segment_tree_query(tree, 8, 9, &result);
216  assert(result == -2);
217  result = 12;
218  segment_tree_update(tree, 5, &result);
219  segment_tree_update(tree, 8, &result);
220  segment_tree_query(tree, 0, 3, &result);
221  assert(result == 0);
222  segment_tree_query(tree, 8, 9, &result);
223  assert(result == 8);
224  segment_tree_dispose(tree);
225 }
void segment_tree_update(segment_tree *tree, size_t index, void *val)
For point updates This function updates the element at given index and also updates segment tree acco...
Definition: segment_tree.c:79
void minimum(const void *a, const void *b, void *c)
Utility for test A function compare for minimum between two integers This function is used as combine...
Definition: segment_tree.c:194
void segment_tree_build(segment_tree *tree)
Builds a Segment tree It is assumed that leaves of tree already contains data.
Definition: segment_tree.c:55
segment_tree * segment_tree_init(void *arr, size_t elem_size, size_t len, void *identity, combine_function func)
Initializes Segment Tree Accquires memory for segment tree and fill the leaves of segment tree with d...
Definition: segment_tree.c:140
void segment_tree_dispose(segment_tree *tree)
Dispose Segment Tree Frees all heap memory accquired by segment tree.
Definition: segment_tree.c:162
void segment_tree_query(segment_tree *tree, long long l, long long r, void *res)
Query the segment tree This function helps in range query of segment tree This function assumes that ...
Definition: segment_tree.c:105
Here is the call graph for this function: