Audacious  $Id:Doxyfile42802007-03-2104:39:00Znenolod$
index.c
Go to the documentation of this file.
1 /*
2  * index.c
3  * Copyright 2009-2011 John Lindgren
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  * 1. Redistributions of source code must retain the above copyright notice,
9  * this list of conditions, and the following disclaimer.
10  *
11  * 2. Redistributions in binary form must reproduce the above copyright notice,
12  * this list of conditions, and the following disclaimer in the documentation
13  * provided with the distribution.
14  *
15  * This software is provided "as is" and without any warranty, express or
16  * implied. In no event shall the authors be liable for any damages arising from
17  * the use of this software.
18  */
19 
20 #include <stdlib.h>
21 #include <string.h>
22 
23 #include <glib.h>
24 
25 #include "index.h"
26 
27 struct _Index {
28  void * * data;
29  int count, size;
30 };
31 
32 typedef struct {
33  int (* compare) (const void * a, const void * b);
35 
36 typedef struct {
37  int (* compare) (const void * a, const void * b, void * data);
38  void * data;
40 
41 EXPORT Index * index_new (void)
42 {
43  Index * index = g_slice_new (Index);
44 
45  index->data = NULL;
46  index->count = 0;
47  index->size = 0;
48 
49  return index;
50 }
51 
52 EXPORT void index_free (Index * index)
53 {
54  g_free (index->data);
55  g_slice_free (Index, index);
56 }
57 
58 EXPORT int index_count (Index * index)
59 {
60  return index->count;
61 }
62 
63 EXPORT void index_allocate (Index * index, int size)
64 {
65  if (size <= index->size)
66  return;
67 
68  if (! index->size)
69  index->size = 64;
70 
71  while (size > index->size)
72  index->size <<= 1;
73 
74  index->data = g_realloc (index->data, sizeof (void *) * index->size);
75 }
76 
77 EXPORT void index_set (Index * index, int at, void * value)
78 {
79  index->data[at] = value;
80 }
81 
82 EXPORT void * index_get (Index * index, int at)
83 {
84  return index->data[at];
85 }
86 
87 static void make_room (Index * index, int at, int count)
88 {
89  index_allocate (index, index->count + count);
90 
91  if (at < index->count)
92  memmove (index->data + at + count, index->data + at, sizeof (void *) *
93  (index->count - at));
94 
95  index->count += count;
96 }
97 
98 EXPORT void index_insert (Index * index, int at, void * value)
99 {
100  make_room (index, at, 1);
101  index->data[at] = value;
102 }
103 
104 EXPORT void index_append (Index * index, void * value)
105 {
106  index_insert (index, index->count, value);
107 }
108 
109 EXPORT void index_copy_set (Index * source, int from, Index * target,
110  int to, int count)
111 {
112  memcpy (target->data + to, source->data + from, sizeof (void *) * count);
113 }
114 
115 EXPORT void index_copy_insert (Index * source, int from, Index * target,
116  int to, int count)
117 {
118  make_room (target, to, count);
119  memcpy (target->data + to, source->data + from, sizeof (void *) * count);
120 }
121 
122 EXPORT void index_copy_append (Index * source, int from, Index * target,
123  int count)
124 {
125  index_copy_insert (source, from, target, target->count, count);
126 }
127 
128 EXPORT void index_merge_insert (Index * first, int at, Index * second)
129 {
130  index_copy_insert (second, 0, first, at, second->count);
131 }
132 
133 EXPORT void index_merge_append (Index * first, Index * second)
134 {
135  index_copy_insert (second, 0, first, first->count, second->count);
136 }
137 
138 EXPORT void index_move (Index * index, int from, int to, int count)
139 {
140  memmove (index->data + to, index->data + from, sizeof (void *) * count);
141 }
142 
143 EXPORT void index_delete (Index * index, int at, int count)
144 {
145  index->count -= count;
146  memmove (index->data + at, index->data + at + count, sizeof (void *) *
147  (index->count - at));
148 }
149 
150 static int index_compare (const void * ap, const void * bp, void * _wrapper)
151 {
152  CompareWrapper * wrapper = _wrapper;
153  return wrapper->compare (* (const void * *) ap, * (const void * *) bp);
154 }
155 
156 EXPORT void index_sort (Index * index, int (* compare) (const void *, const void *))
157 {
158  CompareWrapper wrapper = {compare};
159  g_qsort_with_data (index->data, index->count, sizeof (void *),
160  index_compare, & wrapper);
161 }
162 
163 static int index_compare2 (const void * ap, const void * bp, void * _wrapper)
164 {
165  CompareWrapper2 * wrapper = _wrapper;
166  return wrapper->compare (* (const void * *) ap, * (const void * *) bp, wrapper->data);
167 }
168 
169 EXPORT void index_sort_with_data (Index * index, int (* compare)
170  (const void * a, const void * b, void * data), void * data)
171 {
172  CompareWrapper2 wrapper = {compare, data};
173  g_qsort_with_data (index->data, index->count, sizeof (void *),
174  index_compare2, & wrapper);
175 }