侯捷老师C++ gp and STL笔记
Dec 2, 2013
侯捷老师是个很有意思的人,虽然我对他课的期待最初来自于一些风言风语,说他吉他弹的非常好,然后听了几节课下来发现,竟然还挺有意思。我猜我对C++的兴趣,就源自那里吧。
##第一节课##
- 函数名称就是函数地址
- 编译器检查符号重载(operator override)时,向左看类型
- typename后面加(),表示产生这个typename的临时对象
- 编译器会对fuction template进行实参推导,所以不用<>来指定类型
##第二节课##
- vector的iterator的类型为指针
- 32位机器上指针为4 Byte,所以sizeof(vector)是3个指针大小 (start,finish,end\ of_storage)
- 两个指针相加减,会根据类型自动算出元素的个数间隔而不是真正的地址相减
- operation ++() 为前++,但是为了区分前后++,另外还有一个operation ++ (T)的操作符重载,表示后++
- 关于 -> 操作符的重载,采取迭代措施,由编译器负责解决
- 容器的iterator需要而且一定要定义五个type,分别为:
- iterator_category
- value_type
- pointer
- reference
- difference_type
- operator new是一个函数,在这个函数中调用了malloc (operator delete同理)
- malloc分配区块大小时,会在区块的开头结尾加上cookie块,分别为4 Byte大小,保存了这个区块的大小信息。上面的cookie保存的信息可以用于free这个区块资源,下面的cookie用来合并区块
- GNU的c++ STL不用标准的Allocator,而是用其自己实现的Alloc,Alloc分配器可以实现去掉cookie的作用,获得nocookie block
- Alloc使用16个free list,大小从8 Byte到128 Byte递增,超过128 Byte的资源申请不使用Alloc来分配,直接用malloc(为何使用128这个数字,是开发人员考虑到浪费率的问题,认为128 Byte之后,cookie造成的浪费可以接受)
- 比如:Alloc得到获取32 Byte的资源申请,那么它向操作系统申请40倍的32 Byte大小的区块(区块指针借用每个区块的前4个Byte,叫做embeded pointer),对前20块进行切割,每块32 Byte,给出第一块到用户,链接第二块地址到#4,后面20块不切割,作为储备,如果此时有一个64 Byte大小的申请,则将储备切割成10块64 Byte,给出第一块给用户,链接第二块到#7
##第三节课##
本页第一行的三个模板参数的存在,是为了应对const型的iterator,更加灵活。
1self tmp = *this调用了其构造函数,所以并不是类型转换错误
- 如果malloc失败,则从最近的pool里面切一个出来应急
- 所以alloc的free list模型获取block先要查看pool,如果pool足够切出相应大小的块,则直接切;若不够,产生了碎片,则先将碎片挂载到对应的list下面,然后重新想操作系统申请
- GNU C++的alloc在进程死掉之前,不会将资源归还给操作系统,即未使用free函数,是一种霸占资源的方式
- deque,双向队列,分段连续,所以对于使用者来说,就是连续的;map里面最初有8根指针,如果不够,则双倍扩张map大小
- deque的insert操作将向元素少的那边推
- malloc分配之后,其区块有上下两cookie,两个cookie内容完全一致,保存了区块的大小,由于大小是16的倍数,所以长度的最后四个bit都是0,而cookie就用其最后一个字节表示该区块十分被归还,这样的话就可以判断是否能够被合并
- stack,queue都是用了Adapter设计模式复用了deque
##第四节课##
- hashtable: 元素超过篮子的个数时,就rehash
- _STL_TEMPLATE_NULL 在编译的时候会被转换成template<>,即模板的特化(template specialization)
- hash_set是一种退化,key就是value,value就是key