Chinaunix首页 | 论坛 | 博客
  • 博客访问: 971036
  • 博文数量: 335
  • 博客积分: 10287
  • 博客等级: 上将
  • 技术积分: 3300
  • 用 户 组: 普通用户
  • 注册时间: 2005-08-08 15:29
文章分类

全部博文(335)

文章存档

2015年(4)

2014年(15)

2013年(17)

2012年(11)

2011年(12)

2010年(96)

2009年(27)

2008年(34)

2007年(43)

2006年(39)

2005年(37)

我的朋友

分类: C/C++

2010-03-11 18:06:55

 与大多数容器库一样,ACE允许你指定一个分配器类,它封装的是容器用于管理内存的内存分配例程.这使得你能够对该内存的管理方式进行细粒度的控制;
   你既可以构建自己的定制分配器,也可以使用ACE提供的某个分配器;所有的分配器都必须支持ACE_Allocator接口,而且,通常会在容器的构造器或是open()方法调用中提供给容器;在大多数情况下,使用open()方法调用更可取,而不是构造器,因为open()方法会返回出错代码,你可以在缺乏异常处理机制的情况下使用这些代码;
   ACE中的分配器的工作方式有两个明显的不同:
   A:分配器是在对象实例化的过程中传入的;而不是你在实例化模板时使用的一种类型;随后,一个指向你提供的分配器的引用会保存在容器中.容器使用这个引用来访问你的分配器对象.如果你想在共享内存中进行分配,这会造成问题;
   B:ACE分配器在原始的无类型内存上进行操作,其方式与C的malloc()相同;它们对类型没有意识;这与标准C++库的分配器尖锐对立,C++库中的分配器会在实例化的时候使用你提供的类型,并且对类型有意识.这个原则的一个例外是ACE_Cached_Allocator,它是强类型化的;

   所有ACE容器都要求分配器支持ACE_Allocator接口,它是一个真正的C++接口,所有的方法都是纯虚函数.ACE提供了若干分配器实现:

  (1)、ACE_New_Allocator:使用new操作符直接从堆中分配内存;
  (2)、ACE_Static_Allocator:预分配一个固定尺寸的内存池,然后以优化的方式从这个内存池中分配内存;内存永不释放;
  (3)、ACE_Cached_Allocator:固定尺寸的强类型化的分配器,它会分配一些强类型化的、尺寸固定的内存块,块的数量很明确,这些块在分配时返回给请求者,在释放时返回到自由列表中;
  (4)、ACE_Dynamic_Cached_Allocator:缓存分配器的一种版本,它允许你在运行时而不是在编译时指定缓存块的尺寸和数量.与ACE_Cached_Allocator不同,这些块不是强类型化的;

  分配器的通用接口ACE_Malloc:

  除了ACE_Allocator之外,ACE还有一个名为ACE_Malloc的通用接口.这个分配器的功能比ACE_Allocator强大得多,允许你使用像System V共享内存或内存映射文件这样的技术分配内存.如果你想要使用这些技术分配你的容器,你可以使用适配器ACE_Allocator_Adapter,把ACE_Malloc模板类适配为ACE_Allocator接口;

例子代码:

int TestContainers::testAllocator(void)
{
 ACE_DEBUG( (LM_INFO, ACE_TEXT("----------> use ACE_Allocator <----------\n")) );
 int nReturn = 0, i = 0;
 ACE_Allocator* allocator = NULL;
 size_t block_size = 0;

 //malloc a allocator
 block_size = sizeof(ACE_Node);
 ACE_NEW_RETURN(allocator, ACE_Dynamic_Cached_Allocator(10 + 1, block_size), -1);
 ACE_DEBUG( (LM_INFO, ACE_TEXT("Number of active objects: %d\n"), DataElement::numOfActiveObjects()) );

 ACE_Unbounded_Stack ustack(allocator);
 ACE_DEBUG( (LM_INFO, ACE_TEXT("push ten elements into ustack ...\n")) );
 for(i = 1; i <= 10; i++)
 {
  DataElement elem(i);
  nReturn = ustack.push(elem);
  if(nReturn == -1)
  {
   ACE_DEBUG( (LM_ERROR, ACE_TEXT("%p\n"), ACE_TEXT("push next element")) );
  }
  else
  {
   ACE_DEBUG( (LM_ERROR, ACE_TEXT("push %d ok[%d]\n"), elem.getData(), nReturn) );
  }
 }

 //malloc one block memory from allocator
 ACE_DEBUG( (LM_INFO, ACE_TEXT("malloc one block memory from allocator...\n")) );
 void* furtherMemory = NULL;
 furtherMemory = allocator->malloc(block_size);
 ACE_ASSERT( furtherMemory == NULL);
 ACE_DEBUG( (LM_ERROR, ACE_TEXT("---> %p\n"), ACE_TEXT("No Memory")) );

 //free some elements in the ustack
 ACE_DEBUG( (LM_INFO, ACE_TEXT("free some elements in the ustack ...\n")) );
 DataElement d;
 for(i = 1; i <= 3; i++)
 {
  ustack.pop(d);
 }

 ACE_DEBUG( (LM_INFO, ACE_TEXT("dddddddddddd\n")) );

 //malloc one block memory from allocator against
 furtherMemory = NULL;
 furtherMemory = allocator->malloc(block_size);
 ACE_ASSERT( furtherMemory != NULL);
 ACE_DEBUG( (LM_INFO, ACE_TEXT("malloc one block memory from allocator ok\n")) );
 return 0;
};
 

阅读(1140) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~