00001 /* EGlib "Efficient General Library" provides some basic structures and 00002 * algorithms commons in many optimization algorithms. 00003 * 00004 * Copyright (C) 2005 Daniel Espinoza and Marcos Goycoolea. 00005 * 00006 * This library is free software; you can redistribute it and/or modify it 00007 * under the terms of the GNU Lesser General Public License as published by the 00008 * Free Software Foundation; either version 2.1 of the License, or (at your 00009 * option) any later version. 00010 * 00011 * This library is distributed in the hope that it will be useful, but 00012 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 00013 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public 00014 * License for more details. 00015 * 00016 * You should have received a copy of the GNU Lesser General Public License 00017 * along with this library; if not, write to the Free Software Foundation, 00018 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 00019 * */ 00020 /* ========================================================================= */ 00021 /** @defgroup EGgcIt Gray Code Iterator 00022 * 00023 * Here we define an implementation of knuth's looples gray code iterator for 00024 * binary strings as defined in ``The Art of Computer Programming, 00025 * Chapter 7.2.1.1''. 00026 * */ 00027 /** @file 00028 * @ingroup EGgcIt */ 00029 /** @addtogroup EGgcIt */ 00030 /** @{ */ 00031 /** @example eg_gcit.ex.c 00032 * This is a simple example of the usage of heaps using @ref EGeHeap */ 00033 /* ========================================================================= */ 00034 #ifndef __EG_GCIT__ 00035 #define __EG_GCIT__ 00036 #include <stdlib.h> 00037 #include <stdio.h> 00038 #include <string.h> 00039 #include <limits.h> 00040 #include <float.h> 00041 #include "eg_macros.h" 00042 #include "eg_mem.h" 00043 /* ========================================================================= */ 00044 /** @brief Debug level for the heap */ 00045 #define EG_GCIT_DBG 0 00046 00047 /* ========================================================================= */ 00048 /** @brief Structure to store the information relevant to the binary gray code 00049 * iterator. */ 00050 typedef struct EGgcIt_t 00051 { 00052 int sz; /**< @brief Number of bits in the code */ 00053 int changed_pos;/**< @brief position of the last bit changed */ 00054 int*tuple; /**< @brief Current binary tuple being visited */ 00055 int*focus; /**< @brief Internal information */ 00056 } 00057 EGgcIt_t; 00058 00059 /* ========================================================================= */ 00060 /** @brief Reset an initialized gray code iterator to the zero position. 00061 * @param __gc pointer to a gray-code iterator structure (#EGgcIt_t) 00062 * */ 00063 #define EGgcItReset(__gc) do{\ 00064 EGgcIt_t*const __EGgcit2 = (__gc);\ 00065 register int __EGgci = __EGgcit2->sz;\ 00066 __EGgcit2->focus[__EGgci]=__EGgci;\ 00067 while(__EGgci--){__EGgcit2->tuple[__EGgci] = 0;\ 00068 __EGgcit2->focus[__EGgci]=__EGgci;}\ 00069 __EGgcit2->changed_pos=0;}while(0) 00070 00071 /* ========================================================================= */ 00072 /** @brief Initialize a binary gray code iterator, and set the iterator to the 00073 * zero position. 00074 * @param __gc pointer to a gray-code iterator structure (#EGgcIt_t) 00075 * @param __sz number of bits to be used in the iterator. 00076 * */ 00077 #define EGgcItInit(__gc,__sz) do{\ 00078 EGgcIt_t*const __EGgcit = (__gc);\ 00079 const int __EGgcsz = __EGgcit->sz = ((int)(__sz));\ 00080 __EGgcit->tuple = EGsMalloc(int,__EGgcsz);\ 00081 __EGgcit->focus = EGsMalloc(int,__EGgcsz+1);\ 00082 EGgcItReset(__EGgcit);}while(0) 00083 00084 /* ========================================================================= */ 00085 /** @brief free all internally allocated memory for the given #EGgcIt_t 00086 * structure. 00087 * @param __gc pointer to a gray-code iterator structure (#EGgcIt_t) 00088 * */ 00089 #define EGgcItClear(__gc) do{\ 00090 EGgcIt_t*const __EGgcit = (__gc);\ 00091 EGfree(__EGgcit->tuple);\ 00092 EGfree(__EGgcit->focus);\ 00093 memset(__EGgcit,0,sizeof(EGgcIt_t));}while(0) 00094 00095 /* ========================================================================= */ 00096 /** @brief Return the number of bits for the given gray code iterator 00097 * @param __gc pointer to a gray-code iterator structure (#EGgcIt_t) 00098 * @return number of bits for the iterator 00099 * */ 00100 #define EGgcItGetSize(__gc) ((const int)((__gc)->sz)) 00101 00102 /* ========================================================================= */ 00103 /** @brief Return a constant pointer to the current tuple 00104 * @param __gc pointer to a gray-code iterator structure (#EGgcIt_t) 00105 * @return pointer to an array containing the current tuple */ 00106 #define EGgcItGetTuple(__gc) ((const int*const)((__gc)->tuple)) 00107 00108 /* ========================================================================= */ 00109 /** @brief return which position in the binary string changed in the last 00110 * iteration. 00111 * @param __gc pointer to a gray-code iterator structure (#EGgcIt_t) 00112 * */ 00113 #define EGgcItGetChange(__gc) ((const int)((__gc)->changed_pos)) 00114 00115 /* ========================================================================= */ 00116 /** @brief move to the next binary string, if no next string exists (i.e. we 00117 * finish the loop), return 0, otherwise return 1. 00118 * @param __gc pointer to a gray-code iterator structure (#EGgcIt_t) 00119 * @return zero if no next string exists, otherwise 1. 00120 * */ 00121 #define EGgcItNext(__gc) ({\ 00122 EGgcIt_t*const __EGgcit = (__gc);\ 00123 const int __EGgccp = __EGgcit->changed_pos = __EGgcit->focus[0];\ 00124 const int __EGgcrval=(__EGgccp!=__EGgcit->sz);\ 00125 if(__EGgcrval){\ 00126 __EGgcit->focus[0]=0;\ 00127 __EGgcit->focus[__EGgccp]=__EGgcit->focus[__EGgccp+1];\ 00128 __EGgcit->focus[__EGgccp+1]=__EGgccp+1;\ 00129 __EGgcit->tuple[__EGgccp] = 1-__EGgcit->tuple[__EGgccp];}\ 00130 __EGgcrval;}) 00131 00132 /* ========================================================================= */ 00133 /** @} */ 00134 /* end of eg_gcit.h */ 00135 #endif