《Effective STL》读书笔记四:Item 6 - 9

来源:互联网 发布:淘宝手机助手官方版 编辑:程序博客网 时间:2024/05/22 09:42
Item 6:警惕C++中最令人恼怒的语法解析
Be alert for C++'s most vexing parse
  • 单独存在的括号意味着参数列表的存在,也意味着自身是一个函数指针。
  • 在形参外围加上括号是错误的语法,在实参外围加上括号是可以的。
  • list<int> data(istream_iterator<int>(dataFile), istream_iterator<int>()); 是一个函数的声明,所声明的函数的第二个参数是一个函数指针。
  • list<int> data((istream_iterator<int>(dataFile)), istream_iterator<int>()); 是正确的声明变量的形式。
Item 7:使用包含由new产生的指针容器时,切记在容器销毁前delete指针
When using containers of newed pointers, remember to delete the pointers before the container is destroyed
  • 在使用包含由new产生的指针容器时,为了避免内存泄露,必须使用智能指针来替代普通指针,或者在容器销毁之前手动delete每个指针。其中第一种方法是异常安全的。
Item 8:绝不使用包含auto_ptr的容器
Never create containers of auto_ptrs
  • Containers of auto_ptr(COAP)是被禁止的。有些编译平台不允许这样的语法,因此COAP是不具有好的可移植性的。
  • 当复制一个auto_ptr时,实际对象的所有权被转移到了被复制的目标auto_ptr中,原有的auto_ptr被设置成了NULL。
  • 由于stl中的sort算法常用快排来实现,而快排中会有对元素进行复制的操作,因而排序完之后有的指针会被置空,相应的元素会被删除。
Item 9:在删除选项中仔细选择
Choose carefully among erasing options
  • 删除容器中具有某个特定值的所有元素:当容器是vector, string或deque时,使用erase-remove;当容器是list时,使用list::remove;当容器是标准关联型容器时,使用erase成员函数。
  • 由于STL中的remove和remove_if算法在两个前向迭代器上进行操作,被remove的元素只是被移到了原有范围的尾端。当需要真正地删除这些元素时,需要使用容器的erase方法。
  • 删除容器中满足某个特定条件的所有元素:当容器是vector, string或deque时,使用erase-remove_if;当容器是list时,使用list::remove_if;当容器是标准关联型容器时,使用remove_copy_if和swap,或者写一个循环,如:
for (AssocContainer<int>::iterator i = c.begin();i != c.end();/*nothing*/ ){
  if (badValue(*I)) c.erase(i++);
    else ++i;
}
  • 除了删除元素之外,还需要在循环中做额外的事情:当容器是标准顺序型容器时,参考代码如下:
for (AssocContainer<int>::iterator i = c.begin();i != c.end();/*nothing*/ ){
  if (badValue(*I)) {
    logFile << "Erasing " << *i <<'\n';
    c.erase(i++);
  }
  else ++i;
}
当容器是标准关联型容器时,参考代码如下:
for (SeqContainer<int>::iterator i = c.beqin();i != c.end();){
  if (badValue(*i)){
    logFile << "Erasing " << *i << '\n';
    i = c.erase(i);
  }
  else ++i;
}


原创粉丝点击