data_structures
array_merge_sort.c
Go to the documentation of this file.
1 /* ************************************************************************** */
3 /* */
4 /* ::: :::::::: */
5 /* array_merge_sort.c :+: :+: :+: */
6 /* +:+ +:+ +:+ */
7 /* By: unite <marvin@42.fr> +#+ +:+ +#+ */
8 /* +#+#+#+#+#+ +#+ */
9 /* Created: 2020/07/19 14:38:23 by unite #+# #+# */
10 /* Updated: 2020/09/07 21:50:50 by unite ### ########.fr */
11 /* */
12 /* ************************************************************************** */
13 
14 #include "array.h"
15 
16 static void array_copy_slice(t_array *array, t_array *aux, size_t lo, size_t hi)
17 {
18  size_t i;
19 
20  i = 0;
21  while (i < hi - lo)
22  {
23  array_set(array, lo + i, array_get(aux, i));
24  i++;
25  }
26 }
27 
28 static void array_merge(t_array *array, t_array *aux, size_t lo, size_t sz)
29 {
30  size_t mi;
31  size_t hi;
32  size_t i;
33  size_t j;
34  size_t k;
35 
36  mi = lo + sz;
37  hi = mi + sz > array->size ? array->size : mi + sz;
38  i = lo;
39  j = mi;
40  k = 0;
41  while (k < hi - lo)
42  {
43  if (!(j < hi))
44  array_set(aux, k++, array_get(array, i++));
45  else if (!(i < mi))
46  array_set(aux, k++, array_get(array, j++));
47  else if (array->type->cmp(array_get(array, i), array_get(array, j)) < 0)
48  array_set(aux, k++, array_get(array, i++));
49  else
50  array_set(aux, k++, array_get(array, j++));
51  }
52  array_copy_slice(array, aux, lo, hi);
53 }
54 
55 static void array_merge_sort_iter(t_array *array, t_array *aux)
56 {
57  size_t sz;
58  size_t lo;
59 
60  sz = 1;
61  while (sz < array->size)
62  {
63  lo = 1;
64  while (lo < array->size - sz)
65  {
66  array_merge(array, aux, lo, sz);
67  lo += sz;
68  }
69  sz *= 2;
70  }
71 }
72 
74 {
75  t_array *aux;
76 
77  if (array->type->cmp == NULL)
78  ds_exit_set(ENOTSUP);
79  if (array->size <= 7)
80  array_insertion_sort(array);
81  else
82  {
83  aux = array_zeros(array->type, array->size);
84  array_merge_sort_iter(array, aux);
85  array_delete(aux);
86  }
87 }
array_get
void * array_get(const t_array *array, size_t index)
Returns the item at the specified position in this list.
Definition: array_get.c:16
s_type::cmp
int(* cmp)(const void *, const void *)
(optional) A function ponter used to compare members of this data type
Definition: types.h:52
array_insertion_sort
void array_insertion_sort(t_array *array)
Sorts this array using insertion sort.
Definition: array_insertion_sort.c:28
array.h
array_merge_sort
void array_merge_sort(t_array *array)
Sorts this array using merge sort.
Definition: array_merge_sort.c:73
s_array::type
const t_type * type
The type of items in this array.
Definition: array.h:52
array_zeros
t_array * array_zeros(const t_type *type, size_t size)
Initializes a new array of the specified size, filled with zeros.
Definition: array_zeros.c:16
s_array
A resizable array.
Definition: array.h:47
array_delete
void array_delete(t_array *array)
Deletes this array and free all its items and the associated data.
Definition: array_delete.c:16
s_array::size
size_t size
The number of items in this array.
Definition: array.h:49
array_set
void array_set(t_array *array, size_t index, const void *content)
Replaces the element at the specified position in this array with a copy of the specified element.
Definition: array_set.c:16
ds_exit_set
void ds_exit_set(int err)
Set errno to the specified value, print the error message, and exit the process.
Definition: ds_exit_set.c:22