算法代码(转)

动态内存分配算法 

  1. /* 工程名称: W32_Alloc */
  2. /* Alloc.h */
  3. #ifndef __ALLOC_H
  4. #define __ALLOC_H
  5. #include "Alloc.cpp"
  6. #endif
  7. /* Alloc.cpp */
  8. typedef unsigned int WORD;
  9. typedef enum { sUsed = 1, sFree = 0 } blk_state;
  10. typedef struct mcb {
  11. blk_state s; /* block state */
  12. WORD *pBegin; /* begining of allocated address */
  13. WORD *pEnd; /* ending of allocated address */
  14. size_t size; /* allocated size */
  15. struct mcb *next; 
  16. struct mcb *prev;
  17. } mcb_t; /* memory control block */
  18. typedef struct {
  19. mcb_t *blk_head; /* mcb linked-list head and tail */
  20. mcb_t *blk_tail;
  21. WORD *blk_free; /* free block ptr */
  22. WORD *ptos; /* pointer of stack top */
  23. size_t stack_size; /* stack size */
  24. size_t used_size; /* used size */
  25. } mcbc_t; /* memory control block container */
  26. mcbc_t *c; /* global container */
  27. inline mcbc_t *
  28. init_container( WORD *ptos, int stack_size ) {
  29. mcbc_t *ret = (mcbc_t *)malloc(sizeof(mcbc_t));
  30. assert(ret);
  31. ret->ptos = ptos;
  32. ret->blk_head = (mcb_t *)0;
  33. ret->blk_tail = (mcb_t *)0;
  34. ret->blk_free = ptos;
  35. ret->stack_size = stack_size;
  36. ret->used_size = (int)0;
  37. return ret;
  38. }
  39. inline void
  40. bind_container( mcbc_t *con ) {
  41. c = con;
  42. }
  43. inline void
  44. throw_container( void ) {
  45. mcb_t *p, *bak;
  46. if(c) {
  47. /* free linked-list */
  48. p = c->blk_head;
  49. while(p) {
  50. bak = p->next;
  51. free(p);
  52. p = bak;
  53. }
  54. /* free container */
  55. free(c);
  56. c = (mcbc_t *)0;
  57. }
  58. }
  59. inline void *
  60. allocate( size_t size ) {
  61. assert(c); /* ensure container has been binded */
  62. size_t reminder = c->stack_size - c->used_size; /* calc reminder */
  63. size_t split_size;
  64. size_t ss;
  65. mcb_t *p, *bak;
  66. void *ret;
  67. if(!size)
  68. return (void *)0;
  69. /* general size convert to stack offset */
  70. if(!(size % sizeof(WORD)))
  71. ss = size / sizeof(WORD);
  72. else
  73. ss = size / sizeof(WORD) + 1;
  74. if( reminder < ss )
  75. return (void *)0; /* not enough space for allocating */
  76. if(!c->blk_head) {
  77. /* no mcb in linked-list, create one */
  78. p = (mcb_t *)malloc(sizeof(mcb_t));
  79. assert(p);
  80. ret = (void *)c->ptos;
  81. c->blk_free += ss;
  82. c->used_size += ss;
  83. p->pBegin = c->ptos;
  84. p->pEnd = c->blk_free;
  85. p->s = sUsed;
  86. p->size = size;
  87. p->next = (mcb_t *)0;
  88. p->prev = (mcb_t *)0;
  89. c->blk_head = c->blk_tail = p;
  90. return ret;
  91. }
  92. else {
  93. /* find free block */
  94. p = c->blk_head;
  95. while(p) {
  96. if(p->size >= ss && p->s == sFree) {
  97. ret = (void *)p->pBegin;
  98. /* p->size > ss, split it! */
  99. if(p->size > ss) {
  100. split_size = p->size - ss;
  101. /* recalc end boundary */
  102. p->pEnd = (WORD *)(p->pBegin + ss);
  103. p->size = ss;
  104. p->s = sUsed;
  105. bak = (mcb_t *)malloc(sizeof(mcb_t));
  106. assert(bak);
  107. /* insert mcb */
  108. bak->prev = p;
  109. if(p->next) {
  110. p->next->prev = bak;
  111. bak->next = p->next;
  112. }
  113. else {
  114. bak->next = (mcb_t *)0;
  115. c->blk_tail = bak;
  116. }
  117. p->next = bak;
  118. /* constructing a splited control block */
  119. bak->pBegin = p->pEnd;
  120. bak->pEnd = (WORD *)(bak->pBegin + split_size);
  121. bak->size = split_size;
  122. bak->s = sFree;
  123. }
  124. else
  125. p->s = sUsed;
  126. c->used_size += ss;
  127. return ret;
  128. }
  129. p = p->next;
  130. }
  131. /* no matched block, create one at tail */
  132. ret = (void *)c->blk_free;
  133. c->blk_free += ss;
  134. c->used_size += ss;
  135. p = (mcb_t *)malloc(sizeof(mcb_t));
  136. assert(p);
  137. p->pBegin = (WORD *)ret;
  138. p->pEnd = c->blk_free;
  139. p->prev = c->blk_tail;
  140. p->next = (mcb_t *)0;
  141. p->size = ss;
  142. p->s = sUsed;
  143. c->blk_tail->next = p;
  144. c->blk_tail = p;
  145. return ret;
  146. }
  147. }
  148. inline int
  149. release( void *ptr ) {
  150. assert(c);
  151. mcb_t *p = (mcb_t *)0;
  152. mcb_t *pLeft = (mcb_t *)0;
  153. mcb_t *pRight = (mcb_t *)0;
  154. p = c->blk_head;
  155. while(p) {
  156. /* free matched block */
  157. if(p->pBegin == (WORD *)ptr) {
  158. p->s = sFree;
  159. c->used_size -= p->size;
  160. /* merge free neighbours */
  161. pLeft = p->prev;
  162. pRight = p->next;
  163. while( (pLeft && pLeft->s == sFree) || (pRight && pRight->s == sFree) ) {
  164. /* merge left neighbour */
  165. if(pLeft && pLeft->s == sFree) {
  166. p->pBegin = pLeft->pBegin;
  167. p->size += pLeft->size;
  168. /* destory left neighbour */
  169. p->prev = pLeft->prev;
  170. if(pLeft->prev)
  171. pLeft->prev->next = p;
  172. else
  173. c->blk_head = p;
  174. free(pLeft);
  175. }
  176. /* merge right neighbour */
  177. if(pRight && pRight->s == sFree) {
  178. p->pEnd = pRight->pEnd;
  179. p->size += pRight->size;
  180. /* destory right neighbour */
  181. p->next = pRight->next;
  182. if(pRight->next)
  183. pRight->next->prev = p;
  184. else
  185. c->blk_tail = p;
  186. free(pRight);
  187. }
  188. /* reload neighbours */
  189. pLeft = p->prev;
  190. pRight = p->next;
  191. }
  192. /* on success */
  193. return 0;
  194. }
  195. p = p->next;
  196. }
  197. /* no block matched */
  198. return 1;
  199. }
  200. /* main.cpp */
  201. #include <stdio.h>
  202. #include <stdlib.h>
  203. #include <string.h>
  204. #include <conio.h>
  205. #include <assert.h>
  206. #include "Alloc.h"
  207. WORD stk[8 * 1024]; /* 16Kbytes */
  208. int main() {
  209. char *s1,*s2,*s3;
  210. mcbc_t *con = init_container(stk, 8*1024);
  211. bind_container(con);
  212. s1 = (char *)allocate(12);
  213. s2 = (char *)allocate(4);
  214. s3 = (char *)allocate(5);
  215. strcpy(s1,"Hello,world");
  216. strcpy(s2,"ABC");
  217. strcpy(s3,"1234");
  218. printf("%s,%s,%s\n",s1,s2,s3);
  219. getch();
  220. release((void *)s1);
  221. release((void *)s2);
  222. s1 = (char *)allocate(16);
  223. strcpy(s1,"Hello,world,ABC");
  224. printf("%s %s %s\n",s1,s2,s3);
  225. getch();
  226. release((void *)s1);
  227. release((void *)s3);
  228. throw_container();
  229. return 0;
  230. }
复制代码



A*算法

  1. /* 工程名称: W32_AStar */
  2. /* AStar.h */
  3. /* 设计者: yuki */
  4. #ifndef __ASTAR_H
  5. #define __ASTAR_H
  6. #define MAZE_WIDTH 10 /* 迷宫宽度 */
  7. #define MAZE_HEIGHT 10 /* 迷宫高度 */
  8. #define PATH_BLOCK 0 /* 障碍物 */
  9. #define PATH_WALKON 1 /* 可行走 */
  10. #define PATH_FOOTPRINT 2 /* 脚印 */
  11. #include "AStar.cpp"
  12. #endif
  13. /* AStar.cpp */
  14. /* 设计者: yuki */
  15. typedef unsigned char byte_t;
  16. typedef unsigned int uint_t;
  17. /* 路径节点 */
  18. typedef struct footprint {
  19. /* 存放在数组中的位置 */
  20. uint_t pos;
  21. /* 存放方向信号量 */
  22. byte_t direct;
  23. struct footprint *next;
  24. struct footprint *prev;
  25. } path_t;
  26. /*
  27. 方向信号量查询表
  28. 0x01(0000 0001) : 上
  29. 0x02(0000 0010) : 下
  30. 0x04(0000 0100) : 左
  31. 0x08(0000 1000) : 右
  32. */
  33. static byte_t d_signal[4] = {0x01, 0x02, 0x04, 0x08};
  34. /*
  35. 方向信号量使用表
  36. 如果指定方向已经走过,那么使用“与”运算去处该方向
  37. 0x0E(0000 1110) : 上
  38. 0x0D(0000 1101) : 下
  39. 0x0B(0000 1011) : 左
  40. 0x07(0000 0111) : 右
  41. */
  42. static byte_t d_spend[4] = {0x0E, 0x0D, 0x0B, 0x07};
  43. /* 指定方向移动偏量 */
  44. static int move[4][2] = { {0, -1}, {0, 1}, {-1, 0}, {1, 0} };
  45. /* 打印迷宫用的符号 */
  46. static byte_t symbolic[3] = {'#',0x20,'*'};
  47. /* 求两点间的距离 */
  48. inline uint_t
  49. distance( uint_t pos1X, uint_t pos1Y, uint_t pos2X, uint_t pos2Y ) {
  50. uint_t ret = 0;
  51. /* 距离公式 */
  52. ret = (uint_t)sqrt((pow((double)((int)pos1X - (int)pos2X),2) + pow((double)((int)pos1Y - (int)pos2Y),2)));
  53. return ret;
  54. }
  55. /* 压缩坐标 */
  56. inline uint_t
  57. create_pos( uint_t pX, uint_t pY ) {
  58. uint_t ret = 0;
  59. /* 将pX赋给ret,这样pX坐标在ret的低八位 */
  60. ret = pX;
  61. /* 将pX坐标移到高八位去,这样低位就能存放pY */
  62. ret <<= 8;
  63. /* 将pY存放放到ret的低八位,并保持高八位的数据不变 */
  64. ret |= pY;
  65. return ret;
  66. }
  67. /*
  68. == 估计函数 ===========================================
  69. -p : 当前移动到的节点指针
  70. -quit_x
  71. -quit_y : quit_x 和 quit_y表示迷宫出口坐标
  72. -maze : 迷宫矩阵
  73. =======================================================
  74. */
  75. inline path_t *
  76. evaluate( path_t *p, uint_t quit_x, uint_t quit_y, byte_t maze[MAZE_HEIGHT][MAZE_WIDTH] ) {
  77. uint_t pX, pY;
  78. /* 用于接收四个方向离开出口的距离,以便选择最近的方向移动 */
  79. int dis[4];
  80. int minDis = 32767;
  81. int minId = -1;
  82. path_t *pnode = (path_t *)0;
  83. register int i;
  84. /* 计算当前节点的坐标 */
  85. pX = p->pos >> 8;
  86. pY = p->pos & 0x00FF;
  87. memset(dis, (int)-1, sizeof(int)*4);
  88. /* 计算每个方向离开出口的距离,一次存放到dis数组,若没有i方向,则dis[i]任保留-1 */
  89. for( i = 0; i < 4; ++i ) {
  90. if( (p->direct & d_signal[i]) >> i == 0x01 )
  91. dis[i] =(int)distance(pX + move[i][0], pY + move[i][1], quit_x, quit_y);
  92. }
  93. /* 获得最短距离的方向 */
  94. for(i = 0; i < 4; ++i) {
  95. if(dis[i] != -1 && dis[i] < minDis) {
  96. minId = i;
  97. minDis = dis[i];
  98. }
  99. }
  100. /* 若没有可用的方向,则通知寻径函数折回 */
  101. if(minId == -1)
  102. return (path_t *)0;
  103. /* 用去最近距离方向的信号量 */
  104. p->direct &= d_spend[minId];
  105. /* 在移动到新位置之前,在旧位置处留下足迹 */
  106. maze[pY][pX] = (byte_t)PATH_FOOTPRINT;
  107. /* 构建新的路径节点 */
  108. pnode = (path_t *)malloc(sizeof(path_t));
  109. assert(pnode);
  110. /* 计算下一个位置的坐标 */
  111. pX += move[minId][0];
  112. pY += move[minId][1];
  113. pnode->pos = create_pos(pX, pY);
  114. pnode->prev = p;
  115. pnode->next = (path_t *)0;
  116. pnode->direct = 0;
  117. /* 在新位置处,计算下一个位置可用的移动方向 */
  118. for(i = 0; i < 4; ++i) {
  119. if(maze[pY + move[i][1]][pX + move[i][0]] != PATH_BLOCK && maze[pY + move[i][1]][pX + move[i][0]] != PATH_FOOTPRINT) {
  120. /* 若尝试的下一个位置不是障碍物或自己走过的足迹,则视为可用方向,获得该方向的信号量 */
  121. pnode->direct |= d_signal[i];
  122. }
  123. }
  124. return pnode;
  125. }
  126. /*
  127. == A*算法寻径函数 ===========================================
  128. -eX
  129. -eY :入口坐标
  130. -qX
  131. -qY :出口坐标
  132. -maze :迷宫矩阵
  133. =============================================================
  134. */
  135. inline path_t *
  136. AStar(uint_t eX, uint_t eY, uint_t qX, uint_t qY, byte_t maze[MAZE_HEIGHT][MAZE_WIDTH]) {
  137. register int i;
  138. /* 压缩坐标 */
  139. uint_t quit_pos = create_pos(qX, qY);
  140. /* 构建入口路径节点,视为路径链的头 */
  141. path_t *head = (path_t *)malloc(sizeof(path_t));
  142. path_t *p = (path_t *)0;
  143. path_t *back = (path_t *)0;
  144. assert(head);
  145. p = head;
  146. p->direct = 0;
  147. p->pos = create_pos(eX,eY);
  148. p->next = (path_t *)0;
  149. p->prev = (path_t *)0;
  150. /* 创建入口处的可用方向 */
  151. for(i = 0; i < 4; ++i) {
  152. if(maze[eY + move[i][1]][eX + move[i][0]] != PATH_BLOCK)
  153. /* 若无障碍物则获得该方向的信号量 */
  154. p->direct |= d_signal[i];
  155. }
  156. do {
  157. /* 获得下个路径的节点指针 */
  158. back = evaluate(p, qX, qY, maze);
  159. if(back) {
  160. p->next = back;
  161. p = p->next;
  162. }
  163. /* 无路可走则折回 */
  164. if(p->direct == 0 && p != head && p->pos != quit_pos) {
  165. back = p->prev;
  166. back->next = (path_t *)0;
  167. /* 清楚脚印 */
  168. maze[p->pos & 0x00FF][p->pos >> 8] = (byte_t)PATH_WALKON;
  169. free(p);
  170. p = back;
  171. }
  172. /* 若走不出迷宫,即折回到入口,且入口处的可用方向全部尝试过 */
  173. if(p == head && p->direct == 0) {
  174. free(head);
  175. return (path_t *)0;
  176. }
  177. } while( p->pos != quit_pos );
  178. /* 在出口处留下脚印,便于打印 */
  179. maze[p->pos & 0x00FF][p->pos >> 8] = (byte_t)PATH_FOOTPRINT;
  180. return head;
  181. }
  182. /* main.cpp */
  183. /* 设计者: yuki */
  184. #include <stdio.h>
  185. #include <stdlib.h>
  186. #include <string.h>
  187. #include <conio.h>
  188. #include <math.h>
  189. #include <assert.h>
  190. #include "AStar.h"
  191. static byte_t maze[MAZE_HEIGHT][MAZE_WIDTH] = { 
  192. 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
  193. 0, 1, 1, 0, 1, 1, 1, 0, 1, 0,
  194. 0, 1, 1, 0, 1, 1, 1, 0, 1, 0,
  195. 0, 1, 1, 1, 1, 0, 0, 0, 1, 0,
  196. 0, 1, 0, 0, 0, 1, 1, 0, 1, 0,
  197. 0, 1, 1, 1, 0, 1, 1, 0, 1, 0,
  198. 0, 1, 0, 1, 1, 1, 0, 1, 1, 0,
  199. 0, 1, 0, 0, 0, 1, 0, 0, 1, 0,
  200. 0, 0, 1, 1, 1, 1, 1, 1, 1, 0,
  201. 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
  202. };
  203. int main() {
  204. register int i,j;
  205. path_t *pHead = AStar((uint_t)1,(uint_t)1,(uint_t)2,(uint_t)8,maze);
  206. path_t *p = pHead;
  207. path_t *bak;
  208. if(p) {
  209. bak = p->next;
  210. printf("(%u,%u)",p->pos >> 8, p->pos & 0x00FF);
  211. free(p);
  212. p = bak;
  213. while(p) {
  214. bak = p->next;
  215. printf("->(%u,%u)",p->pos >> 8, p->pos & 0x00FF);
  216. free(p);
  217. p = bak;
  218. }
  219. printf("\n");
  220. }
  221. else
  222. printf("No path to get out of the maze\n");
  223. pHead = p = bak = (path_t *)0;
  224. /* 打印迷宫 */
  225. for(i = 0; i < MAZE_HEIGHT; ++i) {
  226. for(j = 0; j < MAZE_WIDTH; ++j)
  227. printf("%c",symbolic[maze[i][j]]);
  228. printf("\n");
  229. }
  230. getch();
  231. return 0;
  232. }
复制代码



表达式计算器

  1. /* 工程名称: W32_Expr */
  2. /* Expr.h */
  3. #ifndef __EXPR_H
  4. #define __EXPR_H
  5. #define TRUE 0x01
  6. #define FALSE 0x00
  7. #define OP_PRIOR_LESS_TO 0x00
  8. #define OP_PRIOR_GREATER_THAN 0x01
  9. #define OP_PRIOR_EQUAL_TO 0x02
  10. #define STACK_SIZE 64
  11. #define BUFFER_SIZE 16
  12. #include "Expr.cpp"
  13. #endif
  14. /* Expr.cpp */
  15. typedef unsigned char op_prior_t;
  16. typedef unsigned char bool_t;
  17. typedef int stack_t;
  18. /* is an operator ? */
  19. inline bool_t
  20. is_opr(char c) {
  21. switch(c) {
  22. case '+':
  23. case '-':
  24. case '*':
  25. case '/':
  26. case '(':
  27. case ')':
  28. return (bool_t)TRUE;
  29. default:
  30. return (bool_t)FALSE;
  31. }
  32. }
  33. /* calc two oprands */
  34. inline int
  35. calc_oprand(int opr1, int opr2, char op) {
  36. switch(op) {
  37. case '+':
  38. return opr1 + opr2;
  39. case '-':
  40. return opr1 - opr2;
  41. case '*':
  42. return opr1 * opr2;
  43. case '/':
  44. assert(opr2);
  45. return opr1 / opr2;
  46. default:
  47. return -1;
  48. }
  49. }
  50. /* get prior of operator */
  51. inline op_prior_t
  52. get_op_prior(char op) {
  53. switch(op) {
  54. case '+':
  55. case '-':
  56. return 0;
  57. case '*':
  58. case '/':
  59. return 1;
  60. default:
  61. return 0xFF;
  62. }
  63. }
  64. inline int
  65. cmp_op(char op1, char op2) {
  66. op_prior_t pop1 = get_op_prior(op1);
  67. op_prior_t pop2 = get_op_prior(op2);
  68. assert(pop1 != 0xFF);
  69. assert(pop2 != 0xFF);
  70. if(pop1 > pop2)
  71. return OP_PRIOR_GREATER_THAN;
  72. else if(pop1 < pop2)
  73. return OP_PRIOR_LESS_TO;
  74. else
  75. return OP_PRIOR_EQUAL_TO;
  76. }
  77. /* string length */
  78. inline int
  79. strl(char *str) {
  80. char *p = str;
  81. while(*p++);
  82. return (int)(p - str - 1);
  83. }
  84. /* 10^n */
  85. inline int
  86. pow_ten_n(int n) {
  87. int ret = 1;
  88. while(n > 0) {
  89. ret *= 10;
  90. --n;
  91. }
  92. return ret;
  93. }
  94. /* convert string to integer */
  95. inline int
  96. str_to_int(char *str) {
  97. int ret = 0;
  98. int i = 0;
  99. int len = strl(str);
  100. if(*str == '-' || *str == '+') {
  101. ++i;
  102. --len;
  103. }
  104. while(len > 0) {
  105. ret += (*(str + i) - '0') * pow_ten_n(len-1);
  106. ++i;
  107. --len;
  108. }
  109. if(*str == '-')
  110. return (-1) * ret;
  111. return ret;
  112. }
  113. inline int
  114. calc_expr(char *exp) {
  115. /* test express whether it is vaild */
  116. assert(exp);
  117. /* stack of oprands */
  118. stack_t stk_opr[STACK_SIZE];
  119. /* stack of operators */
  120. stack_t stk_op[STACK_SIZE];
  121. /* oprand1 & oprand2 */
  122. int opr1 = 0;
  123. int opr2 = 0;
  124. int cmp_ret;
  125. /* buffer */
  126. char buffer[BUFFER_SIZE];
  127. /* expression length */
  128. int len = strl(exp);
  129. /* counters */
  130. register int i,j;
  131. /* stack pointer */
  132. stack_t *pOpr = stk_opr;
  133. stack_t *pOp = stk_op;
  134. /* initialize buffer & stacks */
  135. memset(buffer, (char)0, sizeof(char) * BUFFER_SIZE);
  136. memset(stk_opr,(stack_t)0,sizeof(stack_t) * STACK_SIZE);
  137. memset(stk_op, (stack_t)0,sizeof(stack_t) * STACK_SIZE);
  138. /* get the first value */
  139. if(is_opr(*exp) && (*exp == '+' || *exp == '-')) {
  140. *buffer = *exp;
  141. i = 1;
  142. j = 1;
  143. }
  144. else {
  145. i = 0;
  146. j = 0;
  147. }
  148. while(!is_opr(exp[i]))
  149. buffer[j++] = exp[i++];
  150. if(i > 0) {
  151. /* push the first oprand to oprands stack */
  152. *pOpr = str_to_int(buffer);
  153. /* clean up buffer */
  154. memset(buffer, (char)0, sizeof(char) * BUFFER_SIZE);
  155. /* reset buffer pointer 'j' */
  156. j = 0;
  157. }
  158. /* push the first operator */
  159. if(exp[i] != '\0')
  160. *pOp = exp[i++];
  161. while(exp[i]) {
  162. /* if exp[i] is not an operator, than get the value */
  163. if(!is_opr(exp[i])) {
  164. while(!is_opr(exp[i]) && exp[i] != '\0')
  165. buffer[j++] = exp[i++];
  166. ++pOpr;
  167. *pOpr = str_to_int(buffer);
  168. memset(buffer, (char)0, sizeof(char) * BUFFER_SIZE);
  169. j = 0;
  170. }
  171. else {
  172. if(exp[i] == '(') {
  173. ++pOp;
  174. *pOp = exp[i++];
  175. }
  176. else if(exp[i] != ')') {
  177. if(*pOp != '(') {
  178. cmp_ret = cmp_op(*pOp,exp[i]);
  179. if(cmp_ret == OP_PRIOR_GREATER_THAN || cmp_ret == OP_PRIOR_EQUAL_TO) {
  180. /* pop two oprands to calc and than push the result to the stack */
  181. opr2 = *pOpr--;
  182. opr1 = *pOpr;
  183. *pOpr = calc_oprand(opr1,opr2,*pOp);
  184. /* push the low priority operator */
  185. *pOp = exp[i++];
  186. }
  187. else if(cmp_ret == OP_PRIOR_LESS_TO) {
  188. /* push the high priority operator */
  189. ++pOp;
  190. *pOp = exp[i++];
  191. }
  192. }
  193. else {
  194. ++pOp;
  195. *pOp = exp[i++];
  196. }
  197. }
  198. else {
  199. /* loop until a ')' matched with */
  200. while(*pOp != '(') {
  201. opr2 = *pOpr--;
  202. opr1 = *pOpr;
  203. *pOpr = calc_oprand(opr1,opr2,*pOp);
  204. /* pop the operator */
  205. *pOp-- = (char)0;
  206. if(pOp == stk_op && *pOp != '(') {
  207. printf("No '(' matched in expression!\n");
  208. getch();
  209. exit(1);
  210. }
  211. }
  212. /* pop the '(',and let the expression move on */
  213. if(pOp > stk_op)
  214. *pOp-- = (char)0;
  215. else
  216. *pOp = (char)0;
  217. ++i;
  218. }
  219. }
  220. }
  221. while(pOp >= stk_op) {
  222. opr2 = *pOpr--;
  223. opr1 = *pOpr;
  224. *pOpr = calc_oprand(opr1,opr2,*pOp);
  225. *pOp-- = (char)0;
  226. }
  227. return *stk_opr;
  228. }
  229. /* main.cpp */
  230. #include <stdio.h>
  231. #include <stdlib.h>
  232. #include <assert.h>
  233. #include <conio.h>
  234. #include <string.h>
  235. #include "Expr.h"
  236. int main() {
  237. char exp[80];
  238. printf("Input an expression\n");
  239. gets(exp);
  240. printf("= %d\n",calc_expr(exp));
  241. getch();
  242. return 0;
  243. }
复制代码



广义表的演示

  1. /* 工程名称: W32_GList */
  2. /* GList.h */
  3. #ifndef __GLIST_H
  4. #define __GLIST_H
  5. #include "Glist.cpp"
  6. #endif
  7. /* GList.cpp */
  8. #define NODE_ELEMENT 0x00
  9. #define NODE_LIST 0x01
  10. typedef unsigned char node_type_t;
  11. typedef unsigned int index_t;
  12. typedef struct {
  13. index_t id_x;
  14. index_t id_y;
  15. } locator_t; 
  16. typedef struct GList {
  17. node_type_t lst_type;
  18. char *menu;
  19. int item_count;
  20. union {
  21. locator_t loc;
  22. struct GList *sub_list;
  23. } data_item;
  24. struct Glist *next;
  25. } list_t;
  26. static char *description[3][2] = { "Black Eyes", "Blue Eyes" ,
  27. "Tall Body" , "Short Body" ,
  28. "Fat Body" , "Thin Body" 
  29. };
  30. static char *meu_list[] = {"== Describe yourself ==\n1. Eye\n2. Height\n3. Figure\n0. Exit\nMake your choice : ",
  31. "== Your eye color ==\n1. Black\n2. Blue\n0. Exit\nMake your choice : " ,
  32. "== Your height ==\n1. Tall\n2. Short\n0. Exit\nMake your choice : " ,
  33. "== Your figure ==\n1. Fat\n2. Thin\n0. Exit\nMake your choice : " 
  34. };
  35. list_t *dialog_sheet = (list_t *)0;
  36. list_t *static_dialog_sheet[4];
  37. char image[256] = "You have ";
  38. inline list_t *
  39. create_glist( void ) {
  40. register int i,j;
  41. list_t *ret = (list_t *)malloc(sizeof(list_t));
  42. list_t *p;
  43. list_t *q;
  44. /* create the first sheet */
  45. ret->lst_type = NODE_LIST;
  46. ret->menu = meu_list[0];
  47. ret->item_count = 4;
  48. ret->data_item.sub_list = (list_t *)0;
  49. p = ret;
  50. for(i = 1; i < 4; ++i) {
  51. p->next = (struct Glist *)malloc(sizeof(list_t));
  52. p = (list_t *)p->next;
  53. p->menu = meu_list[i];
  54. p->lst_type = NODE_LIST;
  55. p->item_count = 3;
  56. }
  57. p->next = (struct Glist *)0;
  58. p = (list_t *)ret->next;
  59. i = 0;
  60. j = 0;
  61. while(p) {
  62. p->data_item.sub_list = (list_t *)malloc(sizeof(list_t));
  63. q = p->data_item.sub_list;
  64. q->lst_type = NODE_ELEMENT;
  65. q->data_item.loc.id_x = (index_t)i;
  66. q->data_item.loc.id_y = (index_t)j++;
  67. q->next = (struct Glist *)malloc(sizeof(list_t));
  68. q = (list_t *)q->next;
  69. q->lst_type = NODE_ELEMENT;
  70. q->data_item.loc.id_x = (index_t)i++;
  71. q->data_item.loc.id_y = (index_t)j;
  72. q->next = (struct Glist *)0;
  73. j = 0;
  74. p = (list_t *)p->next;
  75. }
  76. return ret;
  77. }
  78. inline void
  79. destory_list(list_t *lst) {
  80. list_t *p = lst;
  81. list_t *q = (list_t *)0;
  82. while(p) {
  83. if(p->lst_type == NODE_LIST) {
  84. q = (list_t *)p->data_item.sub_list;
  85. if(q)
  86. destory_list(q);
  87. }
  88. q = (list_t *)p->next;
  89. free(p);
  90. p = q;
  91. }
  92. }
  93. inline void
  94. init_dialog_sheet() {
  95. list_t *p;
  96. register int i = 0;
  97. dialog_sheet = create_glist();
  98. p = dialog_sheet;
  99. while(p) {
  100. static_dialog_sheet[i++] = p;
  101. p = (list_t *)p->next;
  102. }
  103. }
  104. inline void
  105. debug() {
  106. list_t *p = (list_t *)dialog_sheet->next;
  107. list_t *q;
  108. while(p) {
  109. q = (list_t *)p->data_item.sub_list;
  110. printf("(%d,%d)",q->data_item.loc.id_x , q->data_item.loc.id_y);
  111. q = (list_t *)q->next;
  112. printf(",(%d,%d)\n",q->data_item.loc.id_x,q->data_item.loc.id_y);
  113. p = (list_t *)p->next ;
  114. }
  115. }
  116. inline void 
  117. main_menu() {
  118. int c;
  119. list_t *p = static_dialog_sheet[0];
  120. do {
  121. printf("%s",p->menu);
  122. scanf("%d",&c);
  123. if(c >= 1 && c <= 3 ) {
  124. p = static_dialog_sheet[c];
  125. do { /* sub menu */
  126. printf("%s",p->menu);
  127. scanf("%d",&c);
  128. if(c == 0) {
  129. c = 1;
  130. break;
  131. }
  132. else if(c == 1) {
  133. p = p->data_item.sub_list;
  134. strcat(image, description[p->data_item.loc.id_x][p->data_item.loc.id_y]);
  135. strcat(image, " ");
  136. p = static_dialog_sheet[0];
  137. break;
  138. }
  139. else if(c == 2) {
  140. p = (list_t *)p->data_item.sub_list->next;
  141. strcat(image, description[p->data_item.loc.id_x][p->data_item.loc.id_y]);
  142. strcat(image, " ");
  143. p = static_dialog_sheet[0];
  144. break;
  145. }
  146. } while( c != 0 );
  147. }
  148. } while( c != 0 );
  149. if(strlen(image) == 9)
  150. printf("You have nothing!\n");
  151. else
  152. printf("%s\n", image);
  153. }
  154. /* main.cpp */
  155. #include <stdio.h>
  156. #include <stdlib.h>
  157. #include <string.h>
  158. #include <dos.h>
  159. #include <conio.h>
  160. #include "Glist.h"
  161. int main() {
  162. init_dialog_sheet();
  163. main_menu();
  164. destory_list(dialog_sheet);
  165. getch();
  166. return 0;
  167. }
复制代码


赫夫曼自动编码

  1. /* 工程名称: W32_Huffman */
  2. /* Huffman.h */
  3. #ifndef __HUFFMAN_H
  4. #define __HUFFMAN_H
  5. #include "huffman.cpp"
  6. #endif
  7. /* Huffman.cpp */
  8. typedef unsigned int uint_t;
  9. typedef struct huffman {
  10. uint_t weight; /* 权值 */
  11. struct huffman *lchild;
  12. struct huffman *rchild;
  13. } HuffmanTreeNode, *PHuffmanNode;
  14. typedef struct lnklst {
  15. PHuffmanNode HNode; /* 赫夫曼树 */
  16. struct lnklst *next;
  17. struct lnklst *prev;
  18. } LnkListNode, *PLnkListNode;
  19. typedef struct {
  20. uint_t count; /* 树的棵数 */
  21. PLnkListNode head; /* 链表结构,表示一行赫夫曼树 */
  22. PLnkListNode tail;
  23. } LnkList;
  24. /* ===================================================================================================================== */
  25. inline PHuffmanNode
  26. create_huffman_node( uint_t weight ) {
  27. PHuffmanNode node = (PHuffmanNode)malloc(sizeof(HuffmanTreeNode));
  28. assert(node);
  29. /* 确保权值有效 */
  30. assert(weight > (uint_t)0);
  31. /* 使用传入的权值初始化赫夫曼结点 */
  32. node->weight = weight;
  33. node->lchild = (PHuffmanNode)0;
  34. node->rchild = (PHuffmanNode)0;
  35. return node;
  36. }
  37. inline PLnkListNode
  38. create_lnklst_node( PHuffmanNode node ) {
  39. PLnkListNode lstNode = (PLnkListNode)malloc(sizeof(LnkListNode));
  40. assert(lstNode);
  41. /* 初始化链表结点 */
  42. lstNode->HNode = node;
  43. lstNode->next = (PLnkListNode)0;
  44. lstNode->prev = (PLnkListNode)0;
  45. return lstNode;
  46. }
  47. inline void
  48. add_to_lnklist( LnkList *lst, PLnkListNode lstNode ) {
  49. /* 却保lstNode有效 */
  50. assert(lstNode); 
  51. /* 第一次添加结点 */
  52. if(!lst->head) {
  53. lst->head = lstNode;
  54. lst->tail = lstNode;
  55. lst->count = (uint_t)1;
  56. }
  57. else {
  58. lst->tail->next = lstNode;
  59. lstNode->prev = lst->tail;
  60. lst->tail = lstNode;
  61. ++lst->count;
  62. }
  63. }
  64. inline void
  65. remove_from_lnklist( LnkList *lst, PLnkListNode lstNode ) {
  66. /* 辅助结点 */
  67. PLnkListNode pnode = (PLnkListNode)0;
  68. assert(lstNode);
  69. /* 如果结点为链表头 */
  70. if(lstNode == lst->head) {
  71. pnode = lstNode->next;
  72. pnode->prev = (PLnkListNode)0;
  73. lst->head = pnode;
  74. --lst->count;
  75. free(lstNode);
  76. }
  77. /* 如果是两表尾部 */
  78. else if(lstNode == lst->tail) {
  79. pnode = lstNode->prev;
  80. pnode->next = (PLnkListNode)0;
  81. lst->tail = pnode;
  82. --lst->count;
  83. free(lstNode);
  84. }
  85. else {
  86. pnode = lstNode->next;
  87. pnode->prev = lstNode->prev;
  88. lstNode->prev->next = pnode;
  89. --lst->count;
  90. free(lstNode);
  91. }
  92. inline void
  93. find_and_insert( LnkList *lst, PLnkListNode plst ) {
  94. /* 根据赫夫曼树的节点权值,插入链表的适当位置 */
  95. PLnkListNode pcur = (PLnkListNode)0;
  96. if(!lst->head) 
  97. add_to_lnklist(lst,plst);
  98. else {
  99. pcur = lst->head;
  100. while(pcur) {
  101. if(plst->HNode->weight >= pcur->HNode->weight) {
  102. if(pcur->next && plst->HNode->weight <= pcur->next->HNode->weight) {
  103. plst->prev = pcur;
  104. plst->next = pcur->next;
  105. pcur->next->prev = plst;
  106. pcur->next = plst;
  107. ++lst->count;
  108. break;
  109. }
  110. else if(!pcur->next) {
  111. add_to_lnklist(lst, plst);
  112. break;
  113. }
  114. }
  115. pcur = pcur->next;
  116. }
  117. }
  118. }
  119. /* ===================================================================================================================== */
  120. inline void
  121. swap_lnklst_node( PLnkListNode lstNode1, PLnkListNode lstNode2 ) {
  122. PHuffmanNode pnode = (PHuffmanNode)0;
  123. assert(lstNode1 && lstNode2);
  124. /* 交换链表内容 */
  125. pnode = lstNode1->HNode;
  126. lstNode1->HNode = lstNode2->HNode;
  127. lstNode2->HNode = pnode;
  128. }
  129. inline void
  130. select_sort( LnkList *lst ) {
  131. /* 根据权值做一个从小到大的选择排序 */
  132. PLnkListNode cmp_node = lst->head;
  133. PLnkListNode p;
  134. assert(cmp_node);
  135. while(cmp_node) {
  136. p = cmp_node->next;
  137. while(p) {
  138. /* 如果目标位置权值比比较位置的权值小,则将它们交换 */
  139. if(p->HNode->weight < cmp_node->HNode->weight)
  140. swap_lnklst_node(cmp_node,p);
  141. p = p->next;
  142. }
  143. cmp_node = cmp_node->next;
  144. }
  145. }
  146. /* ===================================================================================================================== */
  147. inline PHuffmanNode 
  148. merge_tree( PHuffmanNode root1, PHuffmanNode root2 ) {
  149. /* 合并两棵赫夫曼树,并返回合并后新树根的指针 */
  150. PHuffmanNode retRoot = (PHuffmanNode)0;
  151. assert(root1 && root2);
  152. /* 创建一棵合并后的赫夫曼树 */
  153. retRoot = create_huffman_node(root1->weight + root2->weight);
  154. retRoot->lchild = root1;
  155. retRoot->rchild = root2;
  156. return retRoot;
  157. }
  158. inline void
  159. destory_tree( PHuffmanNode root ) {
  160. /* 销毁一棵树 */
  161. PHuffmanNode plchild, prchild;
  162. if(root) {
  163. plchild = root->lchild;
  164. prchild = root->rchild;
  165. free(root);
  166. root = (PHuffmanNode)0;
  167. destory_tree(plchild);
  168. destory_tree(prchild);
  169. }
  170. }
  171. /* ===================================================================================================================== */
  172. inline void
  173. convert_to_lnklst( LnkList *lst, uint_t Wi[], uint_t size ) {
  174. /* 将权值数组转换成赫夫曼树并添加到链表 */
  175. PLnkListNode plstnode = (PLnkListNode)0;
  176. PHuffmanNode phufnode = (PHuffmanNode)0;
  177. register uint_t i;
  178. for(i = 0; i < size; ++i) {
  179. phufnode = create_huffman_node(Wi[i]);
  180. plstnode = create_lnklst_node(phufnode);
  181. add_to_lnklist(lst,plstnode);
  182. }
  183. /* 排序链表 */
  184. select_sort(lst);
  185. }
  186. inline PHuffmanNode
  187. Huffman_code( uint_t Wi[], uint_t size) {
  188. /* 根据权值数组进行赫夫曼编码,并返回赫夫曼树的树根 */
  189. LnkList lst;
  190. PLnkListNode p1,p2,pnode;
  191. PHuffmanNode phnode;
  192. /* 初始化链表 */
  193. lst.count = (uint_t)0;
  194. lst.head = (PLnkListNode)0;
  195. lst.tail = (PLnkListNode)0;
  196. /* 转换链表 */
  197. convert_to_lnklst(&lst, Wi, size);
  198. /* 开始合并树 */
  199. while(lst.count > 1) {
  200. /* 取两棵根权值最小的树进行合并,并将合并结果写入链表 */
  201. p1 = lst.head;
  202. p2 = lst.head->next;
  203. /* 合并两树 */
  204. phnode = merge_tree(p1->HNode, p2->HNode);
  205. /* 为该树创建一个链表节点 */
  206. pnode = create_lnklst_node(phnode);
  207. /* 将新树添加入链表 */
  208. find_and_insert(&lst,pnode);
  209. /* 删除旧树的两个链表节点 */
  210. remove_from_lnklist(&lst,p1);
  211. remove_from_lnklist(&lst,p2);
  212. }
  213. /* 工作完成删除链表 */
  214. /* 首先获取创建的赫夫曼树的根便于返回 */
  215. phnode = lst.head->HNode;
  216. pnode = lst.head;
  217. while(pnode) {
  218. p1 = pnode->next;
  219. free(pnode);
  220. pnode = p1;
  221. }
  222. lst.head = lst.tail = (PLnkListNode)0;
  223. return phnode;
  224. }
  225. inline void
  226. PreOrderTraverse( PHuffmanNode root, uint_t pos, char code[]) {
  227. if(root) {
  228. if(!root->lchild && !root->rchild)
  229. printf("%u is coded to %s\n",root->weight, code);
  230. code[pos] = '0';
  231. PreOrderTraverse(root->lchild, pos+1, code);
  232. code[pos] = '1';
  233. PreOrderTraverse(root->rchild, pos+1, code); 
  234. }
  235. }
  236. /* main.cpp */
  237. #include <stdio.h>
  238. #include <stdlib.h>
  239. #include <string.h>
  240. #include <assert.h>
  241. #include <conio.h>
  242. #include "huffman.h"
  243. int main() {
  244. uint_t n = 0;
  245. uint_t *Wi = (uint_t *)0;
  246. register uint_t i;
  247. char buf[80];
  248. PHuffmanNode HuffmanTree;
  249. memset(buf,(char)0,80 * sizeof(char));
  250. printf("How many weight you wanna import ( 1...65535 ) ? ");
  251. scanf("%u",&n);
  252. Wi = (uint_t *)malloc(n * sizeof(uint_t));
  253. assert(Wi);
  254. printf("Input weights in turn \n");
  255. for(i = 0; i < n; ++i)
  256. scanf("%u",&Wi[i]);
  257. HuffmanTree = Huffman_code(Wi, n);
  258. PreOrderTraverse(HuffmanTree,0,buf);
  259. getch();
  260. destory_tree(HuffmanTree);
  261. free(Wi);
  262. return 0;
  263. }
复制代码


KMP模式匹配算法(不用next函数)

  1. /* 工程名称: W32_KMP */
  2. /* main.cpp */
  3. #include <stdio.h>
  4. #include <conio.h>
  5. inline int KMP(char *s,char *p);
  6. int main() {
  7. char *s1 = "abacabcdabbab";
  8. char *s2 = "abc";
  9. printf("index = %d\n",KMP(s1,s2));
  10. getch();
  11. return 0;
  12. }
  13. /************************************************
  14. *
  15. * 函数名: KMP
  16. *
  17. * 参数表: s - 主串的指针; p - 模式串的指针
  18. *
  19. * 功能介绍: 比较p是否为s的子串,若是则返回在
  20. * s中起始的索引号。
  21. *
  22. ************************************************/
  23. inline int 
  24. KMP(char *s, char *p) {
  25. char *ptr_s = s; /* 映射字符串指针s */
  26. char *ptr_p = p; /* 映射字符串指针p */
  27. char *ptr_bak = s; /* 用于定位在*ptr_s与*p内容相同的位置 */
  28. int addr_delta; /* 计算相匹配的内容长度,调整ptr_p对比起始位置 */
  29. while(*ptr_s && *ptr_p) {
  30. if(*ptr_s == *ptr_p) {
  31. /* 如果匹配字符与对比串的首字符相等,则备份该指针 */
  32. if(*ptr_s == *p)
  33. ptr_bak = ptr_s;
  34. ++ptr_s;
  35. ++ptr_p;
  36. }
  37. else {
  38. /* 计算新位置与备份指针的差,这便是以匹配的字符数,从而使p+addr_delta获得开始匹配的起始位置 */
  39. addr_delta = (int)(ptr_s - ptr_bak);
  40. /* 若备份位置与当前位置相同,则将当前位置一下下一个位置,从头开始比较 */
  41. if(!addr_delta) {
  42. ++ptr_s;
  43. ptr_bak = ptr_s;
  44. ptr_p = p;
  45. }
  46. else {
  47. ptr_p = p + addr_delta;
  48. /* 若备份位置与模式串的首位置都不匹配当前位置的字符串,则继续向后比较,重设备份位置和匹配位置 */
  49. if(*ptr_p != *ptr_s && *p != *ptr_s) {
  50. ++ptr_s;
  51. ptr_bak = ptr_s;
  52. ptr_p = p;
  53. }
  54. else {
  55. /* 若备份位置与当前位置字符不匹但与模式串首字符相匹,则重设匹配位置和备份位置 */
  56. if(*p == *ptr_s) {
  57. ptr_p = p;
  58. ptr_bak = ptr_s;
  59. }
  60. }
  61. }
  62. }
  63. }
  64. if(*ptr_p)
  65. return -1;
  66. else
  67. /* 计算索引 */
  68. return (int)((ptr_s - s) - (ptr_p - p));
  69. }
复制代码


一元多项式加减乘

  1. /* 工程名称: W32_Polynomial */
  2. /* Polynomial.h */
  3. #ifndef __POLYNOMIAL_H
  4. #define __POLYNOMIAL_H
  5. #define TRUE 0x01
  6. #define FALSE 0x00
  7. /* 错误代码 */
  8. #define ERR_ON_SUCCESS 0x00 /* 没有错误 */
  9. #define ERR_STACK_OVERRUN 0x01 /* 堆栈溢出 */
  10. #define ERR_ITEM_EXIST 0x02 /* 欲添加项已存在 */
  11. #define ERR_PTR_INVAILD 0x04 /* 无效的指针传入 */
  12. #define ERR_LNKLST_INVAILD 0x08 /* 无效的链表 */
  13. #define ERR_ACTCODE_INVAILD 0x10 /* 无效的操作码 */
  14. #define ERR_ADD_IMPOSSIBLE 0x20 /* 无法做加运算 */
  15. #define ERR_SUB_IMPOSSIBLE 0x40 /* 无法做减运算 */
  16. #define ERR_EMPTY_POLY 0x80 /* 多项式链表为空 */
  17. #define ERR_UNKNOWN 0xff /* 位置错误 */
  18. /* 操作码 */
  19. #define ACT_ADD 0x01 /* 多项式加 */
  20. #define ACT_SUB 0x02 /* 多项式减 */
  21. #define ACT_MUP 0x03 /* 多项式乘 */
  22. /* 嵌入式功能配置常数 */
  23. #define AUTO_DESTORY_EXIST FALSE /* 欲插入的项已存在时,自动删除创建的项 */
  24. #define CHK_PARAMETER_PTR TRUE /* 检查作为参数传入的指针是否有效 */
  25. #define RAISE_ERR TRUE /* 错误报告函数 */
  26. #define CRITICAL_ABORT TRUE /* 错误异常中断 */
  27. #define COPY_LNKLST TRUE /* 链表复制函数 */
  28. #define SIMPLE_OUTPUT TRUE /* 简单的多项式输出函数 */
  29. #define SIMPLE_INPUT TRUE /* 简单的多项式输入函数 */
  30. #define EPSILON 1E-6 /* 极小值定义,用于浮点数趋近比较 */
  31. #include "Polynomial.cpp"
  32. #endif
  33. /* Polynomial.cpp */
  34. typedef struct Polynomial { 
  35. float p; 
  36. int e; 
  37. struct Polynomial *next; 
  38. struct Polynomial *prev; 
  39. } poly;
  40. typedef struct {
  41. poly *head; 
  42. poly *tail; 
  43. int length;
  44. } poly_lnklst;
  45. typedef unsigned int uint;
  46. #if RAISE_ERR == TRUE
  47. inline void
  48. raise_err(uint err) {
  49. switch(err) {
  50. case ERR_STACK_OVERRUN:
  51. printf("Error %#x : Stack overrun\n", err);
  52. break;
  53. case ERR_ITEM_EXIST:
  54. printf("Error %#x : Item is already exist\n",err);
  55. break;
  56. case ERR_PTR_INVAILD:
  57. printf("Error %#x : Invaild pointer\n",err);
  58. break;
  59. case ERR_LNKLST_INVAILD:
  60. printf("Error %#x : Invaild Linked-List\n",err);
  61. break;
  62. case ERR_ACTCODE_INVAILD:
  63. printf("Error %#x : Invaild Action Code\n",err);
  64. break;
  65. case ERR_ADD_IMPOSSIBLE:
  66. printf("Error %#x : Item cannot be added\n",err);
  67. break;
  68. case ERR_SUB_IMPOSSIBLE:
  69. printf("Error %#x : Item cannot be subtracted\n",err);
  70. break;
  71. case ERR_EMPTY_POLY:
  72. printf("Error %#x : Polynomial grows empty!\n",err);
  73. break;
  74. case ERR_UNKNOWN:
  75. printf("Error %#x : Unknown error\n",err);
  76. break;
  77. }
  78. }
  79. #endif
  80. inline uint
  81. destory_polynomial(poly_lnklst *plst) {
  82. poly *p = (poly *)0;
  83. poly *tmp = (poly *)0;
  84. #if CHK_PARAMETER_PTR == TRUE
  85. if(!plst)
  86. return ERR_LNKLST_INVAILD;
  87. #endif
  88. p = plst->head;
  89. /* 逐一释放链表项目 */
  90. while(p) {
  91. tmp = p->next;
  92. free(p);
  93. p = tmp;
  94. }
  95. /* 释放两表容器 */
  96. free(plst);
  97. plst = (poly_lnklst *)0;
  98. return ERR_ON_SUCCESS;
  99. }
  100. inline uint
  101. init_poly_lnklst(poly_lnklst *plst) {
  102. #if CHK_PARAMETER_PTR == TRUE
  103. if(!plst)
  104. return ERR_LNKLST_INVAILD;
  105. #endif
  106. plst->head = (poly *)0;
  107. plst->tail = (poly *)0;
  108. plst->length = (int)0;
  109. return ERR_ON_SUCCESS;
  110. }
  111. inline poly *
  112. create_poly_item(float p, int e, uint *err) {
  113. poly *item =
  114. (poly *)malloc(sizeof(poly));
  115. if(!item) {
  116. *err = ERR_STACK_OVERRUN;
  117. return (poly *)0;
  118. }
  119. item->p = p;
  120. item->e = e;
  121. item->next = (poly *)0;
  122. item->prev = (poly *)0;
  123. *err = ERR_ON_SUCCESS;
  124. return item;
  125. }
  126. #if COPY_LNKLST == TRUE
  127. inline poly_lnklst *
  128. copy_polynomial(poly_lnklst *plstSrc,uint *err) { 
  129. poly *pSrc = (poly *)0;
  130. poly *pDes = (poly *)0;
  131. poly *tmp = (poly *)0;
  132. poly_lnklst *plstDes = (poly_lnklst *)0;
  133. #if CHK_PARAMETER_PTR == TRUE
  134. if(!plstSrc) {
  135. *err = ERR_LNKLST_INVAILD;
  136. return (poly_lnklst *)0;
  137. }
  138. #endif
  139. plstDes = (poly_lnklst *)malloc(sizeof(poly_lnklst));
  140. if(!plstDes) {
  141. *err = ERR_STACK_OVERRUN;
  142. #if RAISE_ERR == TRUE
  143. raise_err(*err);
  144. #endif
  145. #if CRITICAL_ABORT == TRUE
  146. exit(1);
  147. #else
  148. return (poly_lnklst *)0;
  149. #endif
  150. }
  151. /* 复制表首 */
  152. pSrc = plstSrc->head;
  153. if(!pSrc) {
  154. free(plstDes);
  155. *err = ERR_EMPTY_POLY;
  156. return (poly_lnklst *)0;
  157. }
  158. pDes = create_poly_item(pSrc->p,pSrc->e,err);
  159. if(*err != ERR_ON_SUCCESS) {
  160. #if RAISE_ERR == TRUE
  161. raise_err(*err);
  162. #endif
  163. #if CRITICAL_ABORT == TRUE
  164. exit(1);
  165. #else
  166. return (poly_lnklst *)0;
  167. #endif
  168. }
  169. plstDes->head = plstDes->tail = pDes;
  170. plstDes->length = plstSrc->length;
  171. /* 逐一复制余下的项目 */
  172. pSrc = pSrc->next;
  173. while(pSrc) {
  174. tmp = create_poly_item(pSrc->p,pSrc->e,err);
  175. if(*err != ERR_ON_SUCCESS) {
  176. #if RAISE_ERR == TRUE
  177. raise_err(*err);
  178. #endif
  179. #if CRITICAL_ABORT == TRUE
  180. exit(1);
  181. #else
  182. return (poly_lnklst *)0;
  183. #endif
  184. }
  185. /* 创建链表的节点连接 */
  186. pDes->next = tmp;
  187. tmp->prev = pDes;
  188. pDes = tmp;
  189. plstDes->tail = tmp;
  190. pSrc = pSrc->next;
  191. }
  192. return plstDes;
  193. }
  194. #endif
  195. inline uint
  196. connect_to_lst(poly_lnklst *plst, poly *item) {
  197. poly *p = (poly *)0,
  198. *tmp = (poly *)0;
  199. #if CHK_PARAMETER_PTR == TRUE
  200. if(!plst)
  201. return ERR_LNKLST_INVAILD;
  202. if(!item)
  203. return ERR_PTR_INVAILD;
  204. #endif
  205. if(!plst->head) {
  206. plst->head = plst->tail = item;
  207. item->next = item->prev = (poly *)0;
  208. plst->length = (int)1;
  209. }
  210. else {
  211. p = plst->head;
  212. while(p) {
  213. tmp = p->next;
  214. #if AUTO_DESTORY_EXIST == TRUE
  215. if(p->e == item->e) {
  216. free(item);
  217. item = (poly *)0;
  218. return ERR_ITEM_EXIST;
  219. }
  220. #else
  221. if(p->e == item->e)
  222. return ERR_ITEM_EXIST;
  223. #endif
  224. if(tmp) {
  225. if((p->e < item->e) && (tmp->e > item->e)) {
  226. item->prev = p;
  227. item->next = tmp;
  228. p->next = item;
  229. tmp->prev = item;
  230. ++plst->length;
  231. break;
  232. }
  233. }
  234. else {
  235. if(p->e > item->e && !p->prev) {
  236. item->prev = (poly *)0;
  237. item->next = p;
  238. p->prev = item;
  239. plst->head = item;
  240. ++plst->length;
  241. break;
  242. }
  243. else {
  244. item->prev = p;
  245. item->next = (poly *)0;
  246. p->next = item;
  247. plst->tail = item;
  248. ++plst->length;
  249. break;
  250. }
  251. }
  252. p = tmp;
  253. }
  254. }
  255. return ERR_ON_SUCCESS;
  256. }
  257. inline uint
  258. remove_item(poly_lnklst *plst, poly *item) {
  259. poly *tmp_prev = (poly *)0;
  260. poly *tmp_next = (poly *)0;
  261. #if CHK_PARAMETER_PTR == TRUE
  262. if(!plst)
  263. return ERR_LNKLST_INVAILD;
  264. if(!plst->head || !item)
  265. return ERR_PTR_INVAILD;
  266. #endif
  267. tmp_prev = item->prev;
  268. tmp_next = item->next;
  269. if(tmp_prev) {
  270. tmp_prev->next = tmp_next;
  271. if(tmp_next)
  272. tmp_next->prev = tmp_prev;
  273. else
  274. plst->tail = tmp_prev;
  275. }
  276. else {
  277. plst->head = tmp_next;
  278. if(!tmp_next)
  279. return ERR_EMPTY_POLY;
  280. if(!tmp_next->next)
  281. plst->tail = tmp_next;
  282. tmp_next->prev = (poly *)0;
  283. }
  284. --plst->length;
  285. free(item);
  286. item = (poly *)0;
  287. return ERR_ON_SUCCESS;
  288. }
  289. inline uint
  290. merge_item(poly *des, poly *src, uint code) {
  291. poly *tmp = (poly *)0;
  292. poly *tmp_prev = (poly *)0;
  293. poly *tmp_next = (poly *)0;
  294. #if CHK_PARAMETER_PTR == TRUE
  295. if(!des || !src)
  296. return ERR_PTR_INVAILD;
  297. #endif
  298. switch(code) {
  299. case ACT_ADD:
  300. if(des->e == src->e) {
  301. des->p += src->p;
  302. return ERR_ON_SUCCESS;
  303. }
  304. else
  305. return ERR_ADD_IMPOSSIBLE;
  306. case ACT_SUB:
  307. if(des->e == src->e) {
  308. des->p -= src->p;
  309. return ERR_ON_SUCCESS;
  310. }
  311. else
  312. return ERR_SUB_IMPOSSIBLE;
  313. case ACT_MUP:
  314. des->p *= src->p;
  315. des->e += src->e;
  316. return ERR_ON_SUCCESS;
  317. default:
  318. return ERR_ACTCODE_INVAILD;
  319. }
  320. }
  321. inline uint
  322. find_and_merge(poly_lnklst *plst) {
  323. poly *tmp = (poly *)0;
  324. poly *tmp_next = (poly *)0;
  325. poly *tmp_prev = (poly *)0;
  326. poly **container = (poly **)0;
  327. register int i = 0;
  328. register int j;
  329. uint err;
  330. #if CHK_PARAMETER_PTR == TRUE
  331. if(!plst)
  332. return ERR_LNKLST_INVAILD;
  333. if(!plst->head)
  334. return ERR_PTR_INVAILD;
  335. #endif
  336. tmp = plst->head;
  337. container = (poly **)malloc(sizeof(poly *) * plst->length);
  338. container[0] = tmp;
  339. tmp = tmp->next;
  340. while(tmp) {
  341. for(j = i; j >=0; --j) {
  342. if(!container[j]) 
  343. continue;
  344. if(container[j]->e == tmp->e) {
  345. err = merge_item(tmp,container[j],ACT_ADD);
  346. if(err != ERR_ON_SUCCESS) {
  347. #if RAISE_ERR == TRUE
  348. raise_err(err);
  349. #endif
  350. #if CRITICAL_ABORT == TRUE
  351. exit(1);
  352. #else
  353. return err;
  354. #endif
  355. }
  356. err = remove_item(plst,container[j]);
  357. if(err != ERR_ON_SUCCESS) {
  358. #if RAISE_ERR == TRUE
  359. raise_err(err);
  360. #endif
  361. #if CRITICAL_ABORT == TRUE
  362. exit(1);
  363. #else
  364. return err;
  365. #endif
  366. }
  367. /* 如果系数为0 */
  368. if(tmp->p <= EPSILON) {
  369. tmp_next = tmp->next;
  370. err = remove_item(plst,tmp);
  371. if(err != ERR_ON_SUCCESS) {
  372. #if RAISE_ERR == TRUE
  373. raise_err(err);
  374. #endif
  375. #if CRITICAL_ABORT == TRUE
  376. exit(1);
  377. #else
  378. return err;
  379. #endif
  380. }
  381. tmp = tmp_next;
  382. }
  383. else
  384. tmp = tmp->next;
  385. break;
  386. }
  387. }
  388. /* 如果没有合并,则存入容器 */
  389. if(j < 0) {
  390. container[++i] = tmp;
  391. tmp = tmp->next;
  392. }
  393. }
  394. free(container);
  395. return ERR_ON_SUCCESS;
  396. }
  397. inline uint
  398. polynomial_opr(poly_lnklst *plstDes, poly_lnklst *plstSrc, uint oprcode) {
  399. poly *pSrc = (poly *)0;
  400. poly *pDes = (poly *)0;
  401. poly *tmp = (poly *)0;
  402. poly_lnklst *plstOpr = (poly_lnklst *)0;
  403. poly_lnklst *plstRet = (poly_lnklst *)0;
  404. uint err;
  405. #if CHK_PARAMETER_PTR == TRUE
  406. if(!plstDes || !plstSrc)
  407. return ERR_LNKLST_INVAILD;
  408. if(!plstDes->head || !plstSrc->head)
  409. return ERR_PTR_INVAILD;
  410. #endif
  411. pSrc = plstSrc->head;
  412. switch(oprcode) {
  413. case ACT_ADD:
  414. case ACT_SUB:
  415. while(pSrc) {
  416. pDes = plstDes->head;
  417. while(pDes) {
  418. if(pSrc->e == pDes->e) {
  419. err = merge_item(pDes,pSrc,oprcode);
  420. if(err != ERR_ON_SUCCESS) {
  421. #if RAISE_ERR == TRUE
  422. raise_err(err);
  423. #endif
  424. #if CRITICAL_ABORT == TRUE
  425. exit(1);
  426. #else
  427. return err;
  428. #endif
  429. }
  430. /* 如果相加后的系数为0,则删除此项 */
  431. if(pDes->p <= EPSILON) {
  432. tmp = pDes->next;
  433. err = remove_item(plstDes,pDes);
  434. if(err != ERR_ON_SUCCESS) {
  435. #if RAISE_ERR == TRUE
  436. raise_err(err);
  437. #endif
  438. #if CRITICAL_ABORT == TRUE
  439. exit(1);
  440. #else
  441. return err;
  442. #endif
  443. }
  444. pDes = tmp;
  445. }
  446. break;
  447. }
  448. else {
  449. if(pDes->next) {
  450. if((pSrc->e > pDes->e) && (pSrc->e < pDes->next->e)) {
  451. tmp = create_poly_item(pSrc->p,pSrc->e,&err);
  452. if(err != ERR_ON_SUCCESS) {
  453. #if RAISE_ERR == TRUE
  454. raise_err(err);
  455. #endif
  456. #if CRITICAL_ABORT == TRUE
  457. exit(1);
  458. #else
  459. return err;
  460. #endif
  461. }
  462. tmp->prev = pDes;
  463. tmp->next = pDes->next;
  464. pDes->next->prev = tmp;
  465. pDes->next = tmp;
  466. ++plstDes->length;
  467. break;
  468. }
  469. }
  470. else {
  471. tmp = create_poly_item(pSrc->p,pSrc->e,&err);
  472. if(err != ERR_ON_SUCCESS) {
  473. #if RAISE_ERR == TRUE
  474. raise_err(err);
  475. #endif
  476. #if CRITICAL_ABORT == TRUE
  477. exit(1);
  478. #else
  479. return err;
  480. #endif
  481. }
  482. if(pDes->e > tmp->e && !pDes->prev) {
  483. tmp->prev = (poly *)0;
  484. tmp->next = pDes;
  485. pDes->prev = tmp;
  486. plstDes->head = tmp;
  487. ++plstDes->length;
  488. break;
  489. }
  490. else {
  491. plstDes->tail->next = tmp;
  492. tmp->prev = plstDes->tail;
  493. tmp->next = (poly *)0;
  494. plstDes->tail = tmp;
  495. ++plstDes->length;
  496. break;
  497. }
  498. }
  499. }
  500. pDes = pDes->next;
  501. }
  502. pSrc = pSrc->next;
  503. }
  504. return ERR_ON_SUCCESS;
  505. case ACT_MUP:
  506. /* 复制旧链表 */
  507. plstOpr = copy_polynomial(plstDes,&err);
  508. if(err != ERR_ON_SUCCESS) {
  509. #if RAISE_ERR == TRUE
  510. raise_err(err);
  511. #endif
  512. #if CRITICAL_ABORT == TRUE
  513. exit(1);
  514. #else
  515. return err;
  516. #endif
  517. }
  518. /* 首先计算第一项,保存到返回链表 */
  519. pDes = plstOpr->head;
  520. while(pDes) {
  521. err = merge_item(pDes,pSrc,ACT_MUP);
  522. pDes = pDes->next;
  523. }
  524. plstRet = copy_polynomial(plstOpr,&err);
  525. if(err != ERR_ON_SUCCESS) {
  526. #if RAISE_ERR == TRUE
  527. raise_err(err);
  528. #endif
  529. #if CRITICAL_ABORT == TRUE
  530. exit(1);
  531. #else
  532. return err;
  533. #endif
  534. }
  535. /* 删除plstOpr */
  536. err = destory_polynomial(plstOpr);
  537. if(err != ERR_ON_SUCCESS) {
  538. #if RAISE_ERR == TRUE
  539. raise_err(err);
  540. #endif
  541. #if CRITICAL_ABORT == TRUE
  542. exit(1);
  543. #else
  544. return err;
  545. #endif
  546. }
  547. /* 计算其余项 */
  548. pSrc = pSrc->next;
  549. while(pSrc) {
  550. plstOpr = copy_polynomial(plstDes,&err);
  551. if(err != ERR_ON_SUCCESS) {
  552. #if RAISE_ERR == TRUE
  553. raise_err(err);
  554. #endif
  555. #if CRITICAL_ABORT == TRUE
  556. exit(1);
  557. #else
  558. return err;
  559. #endif
  560. }
  561. pDes = plstOpr->head;
  562. while(pDes) {
  563. err = merge_item(pDes,pSrc,ACT_MUP);
  564. pDes = pDes->next;
  565. }
  566. /* 两链表相加 */
  567. err = polynomial_opr(plstRet,plstOpr,ACT_ADD);
  568. if(err != ERR_ON_SUCCESS) {
  569. #if RAISE_ERR == TRUE
  570. raise_err(err);
  571. #endif
  572. #if CRITICAL_ABORT == TRUE
  573. exit(1);
  574. #else
  575. return err;
  576. #endif
  577. }
  578. /* 删除plstOpr */
  579. err = destory_polynomial(plstOpr);
  580. if(err != ERR_ON_SUCCESS) {
  581. #if RAISE_ERR == TRUE
  582. raise_err(err);
  583. #endif
  584. #if CRITICAL_ABORT == TRUE
  585. exit(1);
  586. #else
  587. return err;
  588. #endif
  589. }
  590. /* 计算下一项 */
  591. pSrc = pSrc->next;
  592. }
  593. /* 清除原表达式 */
  594. pDes = plstDes->head;
  595. while(pDes) {
  596. pSrc = pDes->next;
  597. free(pDes);
  598. pDes = pSrc;
  599. }
  600. plstDes->head = plstRet->head;
  601. plstDes->tail = plstRet->tail;
  602. plstDes->length = plstRet->length;
  603. free(plstRet);
  604. return ERR_ON_SUCCESS;
  605. default:
  606. return ERR_ACTCODE_INVAILD;
  607. }
  608. #if SIMPLE_OUTPUT == TRUE
  609. inline void
  610. print_polynomial(poly_lnklst *plst) {
  611. poly *p = plst->head;
  612. printf("P = %c%.1fx^%d",p->p > 0 ? '\0' : '-',p->p,p->e);
  613. p = p->next;
  614. while(p) {
  615. printf("%c%.1fx^%d",p->p > 0 ? '+' : '-',p->p,p->e);
  616. p = p->next;
  617. }
  618. printf("\n");
  619. }
  620. #endif
  621. #if SIMPLE_INPUT == TRUE
  622. inline poly_lnklst *
  623. input_polynomial(uint *err) {
  624. poly *item = (poly *)0;
  625. poly_lnklst *plst = (poly_lnklst *)malloc(sizeof(poly_lnklst));
  626. int item_count = 0;
  627. int i = 0;
  628. *err = init_poly_lnklst(plst);
  629. if(*err != ERR_ON_SUCCESS) {
  630. #if RAISE_ERR == TRUE
  631. raise_err(*err);
  632. #endif
  633. #if CRITICAL_ABORT == TRUE
  634. exit(1);
  635. #else
  636. return (poly_lnklst *)0;
  637. #endif
  638. }
  639. printf("Input how many items do you want to constructure a polynomial? ");
  640. scanf("%d",&item_count);
  641. while(item_count > 0) {
  642. item = (poly *)malloc(sizeof(poly));
  643. if(!item) {
  644. *err = ERR_STACK_OVERRUN;
  645. #if RAISE_ERR == TRUE
  646. raise_err(*err);
  647. #endif
  648. #if CRITICAL_ABORT == TRUE
  649. exit(1);
  650. #else
  651. free(plst);
  652. return (poly_lnklst *)0;
  653. #endif
  654. }
  655. printf("(p,e) ? ");
  656. scanf("%f,%d",&item->p,&item->e);
  657. *err = connect_to_lst(plst,item);
  658. if(*err != ERR_ON_SUCCESS) {
  659. #if RAISE_ERR == TRUE
  660. raise_err(*err);
  661. #endif
  662. #if AUTO_DESTORY_EXIST == FALSE
  663. free(item);
  664. #endif
  665. continue;
  666. }
  667. --item_count;
  668. }
  669. *err = ERR_ON_SUCCESS;
  670. return plst;
  671. }
  672. #endif
  673. /* main.cpp */
  674. #include <stdio.h>
  675. #include <stdlib.h>
  676. #include <conio.h>
  677. #include "Polynomial.h"
  678. int main() {
  679. poly_lnklst *plstA, *plstB;
  680. uint err;
  681. /* inputs */
  682. printf("Input polynomial A\n");
  683. plstA = input_polynomial(&err);
  684. printf("Input polynomial B\n");
  685. plstB = input_polynomial(&err);
  686. /* mutiply */
  687. err = polynomial_opr(plstA,plstB,ACT_MUP);
  688. print_polynomial(plstA);
  689. getch();
  690. err = destory_polynomial(plstA);
  691. err = destory_polynomial(plstB);
  692. return 0;
  693. }
复制代码



迷宫算法(用栈实现)

  1. /* 工程名称: W32_Maze */
  2. /* Maze.h */
  3. #ifndef __MAZE_H
  4. #define __MAZE_H
  5. #define TRUE 0x01
  6. #define FALSE 0x00
  7. #define DEFAULT_MAZE TRUE
  8. #define PATH_BLOCK 0x00
  9. #define PATH_WALK_ON 0x01
  10. #define PATH_FOOT_PRINT 0x02
  11. #define MAX_COL 10
  12. #include "Maze.cpp"
  13. #endif
  14. /* Maze.cpp */
  15. /* 无符号整型 */
  16. typedef unsigned int uint_t;
  17. /* 地图数据 */
  18. typedef int map_t;
  19. typedef struct track {
  20. /* 在迷宫矩阵中的位置 */
  21. uint_t x;
  22. uint_t y;
  23. /* 可用方向 */
  24. uint_t direct;
  25. struct track *next;
  26. struct track *prev;
  27. } maze_track;
  28. typedef struct {
  29. /* 路径 */
  30. maze_track *track_ptr;
  31. /* 迷宫出口的位置 */
  32. uint_t endx;
  33. uint_t endy;
  34. /* 当前栈的长度 */
  35. int size;
  36. } maze_path;
  37. int count = 0;
  38. /* 方向查询表 */
  39. uint_t directInqTbl[4] = {0x01, 0x02, 0x04, 0x08};
  40. /* 方向使用表 */
  41. uint_t directUseTbl[4] = {0xE, 0xD, 0xB, 0x7};
  42. /* 方向算数常数 */
  43. int directTbl[4][2] = {{0,-1},{0,1},{-1,0},{1,0}};
  44. /* 墙、路和足迹的符号集 */
  45. unsigned char symbolic[3] = { '#', 0x20, '*' };
  46. //unsigned char symbolic[3] = {0x2A, 0x20, '#'};
  47. #if DEFAULT_MAZE == TRUE
  48. static map_t def_maze[10][10] = { 
  49. 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
  50. 0, 1, 1, 0, 1, 1, 1, 0, 1, 0,
  51. 0, 1, 1, 0, 1, 1, 1, 0, 1, 0,
  52. 0, 1, 1, 1, 1, 0, 0, 0, 1, 0,
  53. 0, 1, 0, 0, 0, 1, 1, 0, 1, 0,
  54. 0, 1, 1, 1, 0, 1, 1, 0, 1, 0,
  55. 0, 1, 0, 1, 1, 1, 0, 1, 1, 0,
  56. 0, 1, 0, 0, 0, 1, 0, 0, 1, 0,
  57. 0, 0, 1, 1, 1, 1, 1, 1, 1, 0,
  58. 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
  59. };
  60. #endif
  61. inline maze_path *
  62. create_path(void) {
  63. maze_path *path = (maze_path *)malloc(sizeof(maze_path));
  64. assert(path);
  65. path->track_ptr = (maze_track *)0;
  66. path->size = (int)0;
  67. return path;
  68. }
  69. inline void
  70. generate_enterance(maze_path *path,uint_t x, uint_t y) {
  71. if(path && !path->size) {
  72. path->track_ptr = (maze_track *)malloc(sizeof(maze_track));
  73. assert(path->track_ptr);
  74. path->track_ptr->direct = (uint_t)0;
  75. path->track_ptr->x = x;
  76. path->track_ptr->y = y;
  77. path->track_ptr->next = (maze_track *)0;
  78. path->track_ptr->prev = (maze_track *)0;
  79. ++path->size;
  80. }
  81. }
  82. inline void
  83. designate_exit(maze_path *path, uint_t x, uint_t y) {
  84. if(path) {
  85. path->endx = x;
  86. path->endy = y;
  87. }
  88. }
  89. inline void
  90. print_maze(map_t maze[][MAX_COL], uint_t row, uint_t col) {
  91. register uint_t i,j;
  92. for(i = 0; i < row; ++i) {
  93. for(j = 0; j < col; ++j)
  94. printf("%c",*(symbolic + maze[i][j]));
  95. printf("\n");
  96. }
  97. }
  98. inline uint_t
  99. find_my_way(map_t maze[][MAX_COL], uint_t row, uint_t col, maze_path *path) {
  100. register int i,j;
  101. uint_t x;
  102. uint_t y;
  103. uint_t ex;
  104. uint_t ey;
  105. maze_track *ptrack = (maze_track *)0;
  106. maze_track *ptmp = (maze_track *)0;
  107. if(path) {
  108. /* 设置入口方向量 */
  109. assert(path->track_ptr);
  110. for(i = 0; i < 4; ++i) {
  111. x = path->track_ptr->x + directTbl[i][0];
  112. y = path->track_ptr->y + directTbl[i][1];
  113. if( (x < 0 || x >= col) || (y < 0 || y >= row))
  114. continue;
  115. if(maze[y][x] == PATH_WALK_ON)
  116. path->track_ptr->direct |= directInqTbl[i];
  117. }
  118. ptrack = path->track_ptr;
  119. ex = path->endx;
  120. ey = path->endy;
  121. while(ptrack->x != ex || ptrack->y != ey) {
  122. /* 获取行进方向 */
  123. for(i = 0; i < 4; ++i) {
  124. /* 方向有效,则该方向被使用 */
  125. if( ((ptrack->direct & directInqTbl[i]) >> i) == 0x01 ) {
  126. ptrack->direct &= directUseTbl[i];
  127. break;
  128. }
  129. }
  130. /* 当入口方向量用完,则宣告无解 */
  131. if(i == 4) {
  132. if(!ptrack->prev) {
  133. printf("No way to solve!\n");
  134. return FALSE;
  135. }
  136. /* 当最后个路径节点用完方向量,则折回 */
  137. else {
  138. /* 清除足迹 */
  139. maze[ptrack->y][ptrack->x] = PATH_WALK_ON;
  140. ptmp = ptrack->prev;
  141. ptmp->next = (maze_track *)0;
  142. free(ptrack);
  143. ptrack = ptmp;
  144. --path->size;
  145. ++count;
  146. continue;
  147. }
  148. }
  149. ptmp = (maze_track *)malloc(sizeof(maze_track));
  150. assert(ptmp);
  151. ptrack->next = ptmp;
  152. ++path->size;
  153. /* 创建链表结构,在旧位置处留下足迹 */
  154. maze[ptrack->y][ptrack->x] = PATH_FOOT_PRINT;
  155. /* 设置新位置 */
  156. ptmp->x = ptrack->x + directTbl[i][0];
  157. ptmp->y = ptrack->y + directTbl[i][1];
  158. ptmp->direct = (uint_t)0;
  159. ptmp->prev = ptrack;
  160. ptrack = ptmp;
  161. ptmp->next = (maze_track *)0;
  162. /* 为下一个路径节点获取方向信号 */
  163. for(j = 0; j < 4; ++j) {
  164. x = ptrack->x + directTbl[j][0];
  165. y = ptrack->y + directTbl[j][1];
  166. if( (x < 0 || x >= col) || (y < 0 || y >= row))
  167. continue;
  168. if(maze[y][x] == PATH_WALK_ON && maze[y][x] != PATH_FOOT_PRINT)
  169. ptrack->direct |= directInqTbl[j];
  170. }
  171. }
  172. maze[ey][ex] = PATH_FOOT_PRINT;
  173. return TRUE;
  174. }
  175. return FALSE;
  176. }
  177. inline void
  178. destory_path(maze_path *path) {
  179. assert(path);
  180. maze_track *track = path->track_ptr;
  181. maze_track *tmp = (maze_track *)0;
  182. while(track) {
  183. tmp = track->next;
  184. free(track);
  185. track = tmp;
  186. }
  187. free(path);
  188. path = (maze_path *)0;
  189. }
  190. /* main.cpp */
  191. #include <stdio.h>
  192. #include <stdlib.h>
  193. #include <conio.h>
  194. #include <assert.h>
  195. #include "Maze.h"
  196. int main() {
  197. uint_t ret;
  198. /* 创建路径链 */
  199. maze_path *path = create_path();
  200. maze_track *p;
  201. /* 初始化入口 */
  202. generate_enterance(path,1,1);
  203. /* 初始化终点 */
  204. designate_exit(path,8,8);
  205. printf("Before explorer\n");
  206. print_maze(def_maze,10,10);
  207. /* 开始探索 */
  208. ret = find_my_way(def_maze,10,10,path);
  209. if(ret == TRUE) {
  210. p = path->track_ptr;
  211. printf("(%u,%u)",p->x, p->y);
  212. p = p->next;
  213. while(p) {
  214. printf("->(%u,%u)",p->x, p->y);
  215. p = p->next;
  216. }
  217. printf("\n");
  218. printf("\nAfter explorer\n");
  219. print_maze(def_maze,10,10);
  220. }
  221. printf("\nReturn count = %d\n",count);
  222. getch();
  223. destory_path(path);
  224. return 0;
  225. }
复制代码
posted @ 2012-08-15 15:07  山路水桥  阅读(503)  评论(0编辑  收藏  举报