Chinaunix首页 | 论坛 | 博客
  • 博客访问: 192621
  • 博文数量: 27
  • 博客积分: 725
  • 博客等级: 上士
  • 技术积分: 347
  • 用 户 组: 普通用户
  • 注册时间: 2008-10-04 09:01
文章分类

全部博文(27)

文章存档

2012年(15)

2011年(12)

分类: LINUX

2011-11-10 12:20:09

在设计内存管理器时,经常需要根据内存的size找到对应的数组index,查表是个不错的解决办法。
 
假设有一个数组,数组中每个元素代表一个范围,任意给定一个数,要尽可能快得找到其对应的数组索引,有什么好的办法么?
 
例如,数组为
范围  [0,1) [1,2) [2,4) [4,8) [8,16) [16,32) [32,64) [64,128)
索引    0     1     2     3     4       5       6       7     
 
给定一个数37,那么由于在[32,64)范围内,故应返回索引6。
通过以下程序可生成一张索引表:
  1. #include <stdio.h>
  2. #include <stdlib.h>

  3. #define MIN_MASK 5
  4. #define MAX_MASK 12

  5. #define MIN_VALUE (1 << (MIN_MASK))
  6. #define MAX_VALUE (1 << (MAX_MASK))
  7. #define DIF_VAL   (1 << ((MAX_MASK) - (MIN_MASK)))

  8. #define ONELINE_MASK 4
  9. #define ONELINE   (1 << (ONELINE_MASK))

  10. int main(void)
  11. {
  12.     FILE *fp = fopen("c:\\data.txt", "w");
  13.     fprintf(fp, "static char index_table[] = {\n\t");
  14.     int idx = 0, idv = 1, lnc = 1, i;
  15.     for (i = 0; i < DIF_VAL; i++, lnc++) {
  16.         if (i >= idv) {
  17.             idx++;
  18.             idv <<= 1;
  19.         }
  20.         if (lnc > ONELINE) {
  21.             fprintf(fp, "\n\t");
  22.             lnc = 1;
  23.         }
  24.         fprintf(fp, "%d, ", idx);
  25.     }
  26.     fprintf(fp, "\n};");
  27.     fclose(fp);
  28.     return 0;
  29. }
生成如下查找表
  1. static char index_table[] = {
  2.     0, 1, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 4, 4, 4, 4,
  3.     5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5,
  4.     6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
  5.     6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6,
  6.     7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
  7.     7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
  8.     7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
  9.     7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
  10. };
则可通过size_to_index完成从size到index的转换
  1. static inline int size_to_index(unsigned int size)
  2. {
  3.     return index_table[size >> MIN_MASK];
  4. }
阅读(8386) | 评论(2) | 转发(1) |
给主人留下些什么吧!~~

keytounix2011-11-13 17:20:53

1. good idear
2.
#define N 32
int size_to_index(unsigned int size)

{

    int i=0;
for(i=1;i<N;i++)
{
if(unlikely(((1<<i)&size)==(1<<i)))
break;
}
return i;
}

守猪的幸福2011-11-11 01:08:42

Good idea!!