Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Add xbt_dynar_getlast_as and xbt_dynar_getfirst_as helping macros
[simgrid.git] / include / xbt / dynar.h
1 /* $Id$ */
2
3 /* dynar - a generic dynamic array                                          */
4
5 /* Copyright (c) 2003, 2004 Martin Quinson. All rights reserved.            */
6
7 /* This program is free software; you can redistribute it and/or modify it
8  * under the terms of the license (GNU LGPL) which comes with this package. */
9
10 #ifndef _XBT_DYNAR_H
11 #define _XBT_DYNAR_H
12
13 #include "xbt/misc.h" /* SG_BEGIN_DECL */
14
15 SG_BEGIN_DECL()
16
17 /** @addtogroup XBT_dynar
18   * @brief DynArr are dynamically sized vector which may contain any type of variables.
19   *
20   * <center><table><tr><td><b>Up </b>    <td> [\ref index]::[\ref XBT_API]
21   *                <tr><td><b>Prev</b>   <td> [\ref XBT_config]
22   *                <tr><td><b>Next</b>   <td> [\ref XBT_dict]
23   *                <tr><td><b>Down</b>   <td> \ref XBT_dynar_cons\n\ref XBT_dynar_array\n\ref XBT_dynar_perl\n\ref XBT_dynar_ctn\n\ref XBT_dynar_speed\n\ref XBT_dynar_cursor 
24   * </table></center>
25   *
26   * These are the SimGrid version of the dynamically size arrays, which all C programmer recode one day or another.
27   *  
28   * For performance concerns, the content of DynArr must be homogeneous (in
29   * contrary to dictionnaries -- see the \ref XBT_dict section). You thus
30   * have to provide the function which will be used to free the content at
31   * structure creation (of type void_f_ppvoid_t or void_f_pvoid_t).
32   *
33   * \section XBT_dynar_exscal Example with scalar
34   * \dontinclude dynar_int.c
35   *
36   * \skip Vars_decl
37   * \skip dyn
38   * \until iptr
39   * \skip Populate_ints
40   * \skip dyn
41   * \until end_of_traversal
42   * \skip shifting
43   * \skip val
44   * \until xbt_dynar_free
45   *
46   * \section XBT_dynar_exptr Example with pointed data
47   * \dontinclude dynar_string.c
48   * 
49   * \skip doxygen_first_cruft
50   * \skip f
51   * \until xbt_init
52   * \skip Populate_str
53   * \skip dyn
54   * \until }
55   * \skip macro
56   * \until dynar_free
57   * \skip xbt_exit
58   * \until }
59   *
60   */
61
62 /** @defgroup XBT_dynar_cons Dynar constructor and destructor
63  *  @ingroup XBT_dynar
64  *
65  * <center><table><tr><td><b>Up </b>       <td> [\ref index]::[\ref XBT_API]::[\ref XBT_dynar]
66  *                <tr><td><b>Jump to</b><td> --\>\ref XBT_dynar_cons\<--\n\ref XBT_dynar_array\n\ref XBT_dynar_perl\n\ref XBT_dynar_ctn\n\ref XBT_dynar_speed\n\ref XBT_dynar_cursor
67  * </table></center>
68  *
69  *  @{
70  */
71    /** \brief Dynar data type (opaque type) */
72    typedef struct xbt_dynar_s *xbt_dynar_t;
73
74
75   xbt_dynar_t   xbt_dynar_new(unsigned long elm_size, 
76                              void_f_pvoid_t *free_func);
77   void          xbt_dynar_free(xbt_dynar_t *dynar);
78   void          xbt_dynar_free_container(xbt_dynar_t *dynar);
79
80   unsigned long xbt_dynar_length(const xbt_dynar_t dynar);
81   void          xbt_dynar_reset(xbt_dynar_t dynar);
82
83   void          xbt_dynar_dump(xbt_dynar_t dynar);
84
85 /** @} */
86 /** @defgroup XBT_dynar_array Dynar as a regular array
87  *  @ingroup XBT_dynar
88  *
89  * <center><table><tr><td><b>Up </b>    <td> [\ref index]::[\ref XBT_API]::[\ref XBT_dynar]
90  *                <tr><td><b>Jump to</b><td> \ref XBT_dynar_cons\n--\>\ref XBT_dynar_array\<--\n\ref XBT_dynar_perl\n\ref XBT_dynar_ctn\n\ref XBT_dynar_speed\n\ref XBT_dynar_cursor
91  * </table></center>
92  *
93  *  @{
94  */
95
96   void xbt_dynar_get_cpy(const xbt_dynar_t dynar, int idx, void * const dst);
97   
98   void xbt_dynar_set(xbt_dynar_t dynar, int idx, const void *src);
99   void xbt_dynar_replace(xbt_dynar_t dynar, int idx, const void *object);
100
101   void xbt_dynar_insert_at(xbt_dynar_t dynar, int  idx, const void *src);
102   void xbt_dynar_remove_at(xbt_dynar_t dynar, int  idx, void * const dst);
103
104 /** @} */
105 /** @defgroup XBT_dynar_perl Perl-like use of dynars
106  *  @ingroup XBT_dynar
107  *
108  * <center><table><tr><td><b>Up </b>    <td> [\ref index]::[\ref XBT_API]::[\ref XBT_dynar]
109  *                <tr><td><b>Jump to</b><td> \ref XBT_dynar_cons\n\ref XBT_dynar_array\n--\>\ref XBT_dynar_perl\<--\n\ref XBT_dynar_ctn\n\ref XBT_dynar_speed\n\ref XBT_dynar_cursor
110  * </table></center>
111  *
112  *  @{
113  */
114
115   void xbt_dynar_push    (xbt_dynar_t dynar, const void *src);
116   void xbt_dynar_pop     (xbt_dynar_t dynar, void *const dst);
117   void xbt_dynar_unshift (xbt_dynar_t dynar, const void *src);
118   void xbt_dynar_shift   (xbt_dynar_t dynar, void *const dst);
119   void xbt_dynar_map     (const xbt_dynar_t dynar, void_f_pvoid_t *op);
120
121 /** @} */
122 /** @defgroup XBT_dynar_ctn Direct manipulation to the dynars content
123  *  @ingroup XBT_dynar
124  *
125  * <center><table><tr><td><b>Up </b>    <td> [\ref index]::[\ref XBT_API]::[\ref XBT_dynar]
126  *                <tr><td><b>Jump to</b><td> \ref XBT_dynar_cons\n\ref XBT_dynar_array\n\ref XBT_dynar_perl\n--\>\ref XBT_dynar_ctn\<--\n\ref XBT_dynar_speed\n\ref XBT_dynar_cursor
127  * </table></center>
128  *
129  *  Those functions do not retrive the content, but only their address.
130  *
131  *  @{
132  */
133
134   void *xbt_dynar_get_ptr(const xbt_dynar_t dynar, const int idx);
135   void *xbt_dynar_insert_at_ptr(xbt_dynar_t const dynar, const int idx);
136   void *xbt_dynar_push_ptr(xbt_dynar_t dynar);
137   void *xbt_dynar_pop_ptr(xbt_dynar_t dynar);
138
139 /** @} */
140 /** @defgroup XBT_dynar_speed Speed optimized access to dynars of scalars
141  *  @ingroup XBT_dynar
142  *
143  * <center><table><tr><td><b>Up </b>    <td> [\ref index]::[\ref XBT_API]::[\ref XBT_dynar]
144  *                <tr><td><b>Jump to</b><td> \ref XBT_dynar_cons\n\ref XBT_dynar_array\n\ref XBT_dynar_perl\n\ref XBT_dynar_ctn\n--\>\ref XBT_dynar_speed\<--\n\ref XBT_dynar_cursor
145  * </table></center>
146  *
147  *  While the other functions use a memcpy to retrive the content into the
148  *  user provided area, those ones use a regular affectation. It only works
149  *  for scalar values, but should be a little faster.
150  *
151  *  @{
152  */
153
154   /** @brief Quick retrieval of scalar content 
155    *  @hideinitializer */
156 #  define xbt_dynar_get_as(dynar,idx,type) \
157           (*(type*)xbt_dynar_get_ptr((dynar),(idx)))
158   /** @brief Quick retrieval of scalar content 
159    *  @hideinitializer */
160 #  define xbt_dynar_getlast_as(dynar,type) \
161           (*(type*)xbt_dynar_get_ptr((dynar),xbt_dynar_length(dynar)-1))
162   /** @brief Quick retrieval of scalar content 
163    *  @hideinitializer */
164 #  define xbt_dynar_getfirst_as(dynar,type) \
165           (*(type*)xbt_dynar_get_ptr((dynar),0))
166   /** @brief Quick insertion of scalar content 
167    *  @hideinitializer */
168 #  define xbt_dynar_insert_at_as(dynar,idx,type,value) \
169           *(type*)xbt_dynar_insert_at_ptr(dynar,idx)=value
170   /** @brief Quick insertion of scalar content 
171    *  @hideinitializer */
172 #  define xbt_dynar_push_as(dynar,type,value) \
173           *(type*)xbt_dynar_push_ptr(dynar)=value
174   /** @brief Quick insertion of scalar content 
175    *  @hideinitializer */
176 #  define xbt_dynar_pop_as(dynar,type) \
177            (*(type*)xbt_dynar_pop_ptr(dynar))
178
179 /** @} */
180 /** @defgroup XBT_dynar_cursor Cursors on dynar
181  *  @ingroup XBT_dynar
182  *
183  * <center><table><tr><td><b>Up </b>    <td> [\ref index]::[\ref XBT_API]::[\ref XBT_dynar]
184  *                <tr><td><b>Jump to</b><td> \ref XBT_dynar_cons\n\ref XBT_dynar_array\n\ref XBT_dynar_perl\n\ref XBT_dynar_ctn\n\ref XBT_dynar_speed\n--\>\ref XBT_dynar_cursor\<--
185  * </table></center>
186  *
187  * Cursors are used to iterate over the structure. Never add elements to the 
188  * DynArr during the traversal. To remove elements, use the
189  * xbt_dynar_cursor_rm() function
190  *
191  *  @{
192  */
193
194   void xbt_dynar_cursor_first (const xbt_dynar_t dynar, int *cursor);
195   void xbt_dynar_cursor_step  (const xbt_dynar_t dynar, int *cursor);
196   int  xbt_dynar_cursor_get   (const xbt_dynar_t dynar, int *cursor, 
197                                void *whereto);
198   void xbt_dynar_cursor_rm(xbt_dynar_t dynar,
199                            int          *const cursor);
200
201
202 /** @brief Iterates over the whole dynar. 
203  * 
204  *  @param _dynar what to iterate over
205  *  @param _cursor an integer used as cursor
206  *  @param _data
207  *  @hideinitializer
208  *
209  * \note An example of usage:
210  * \code
211 xbt_dynar_t dyn;
212 int cpt;
213 string *str;
214 xbt_dynar_foreach (dyn,cpt,str) {
215   printf("Seen %s\n",str);
216 }
217 \endcode
218  */
219 #define xbt_dynar_foreach(_dynar,_cursor,_data) \
220        for (xbt_dynar_cursor_first(_dynar,&(_cursor))      ; \
221             xbt_dynar_cursor_get(_dynar,&(_cursor),&_data) ; \
222             xbt_dynar_cursor_step(_dynar,&(_cursor))         )
223
224 /** @} */
225
226 SG_END_DECL()
227
228 #endif /* _XBT_DYNAR_H */