//

//  priority_queue.cpp

//  笔记

//

//  Created by fam on 15/3/16.

//

//

//---------------------------15/03/16----------------------------

//priority_queue

{

/*

priority_queue概述:

同正常队列一样,队尾进,队首出,不过不是先进后出,

有权值的概念,所以会自动排序(并不是全部排序,只要保证队

首值最大即可,权值最高的最先出队列,这里用的是堆来保证队首

的值

*/

template<class T,
class Sequence = vector<T>,

class Compare = less<typename Sequence::value_type> >

class priority_queue

{

public:

typedef typename Sequence::value_type value_type;

typedef typename Sequence::size_type size_type;

typedef typename Sequence::reference reference;

typedef typename Sequence::const_reference const_reference;

protected:

Sequence c;

Compare comp;

public:

priority_queue() : c(){};

//explict
可以有效防止隐式转化

explicit priority_queue(const Compare& x) : c(), comp(x){}

//下面都是直接调用heap算法来直接实现堆的操作

template<class InputIterator>

priority_queue(InputIterator first, InputIterator last,
const Compare& x)

:c(first,last), comp(x){ make_heap(c.begin(), c.end(), comp);}

template< class InputIterator>

priority_queue(InputIterator first, InputIterator last)

: c(first, last) {make_heap(c.begin(), c.end(), comp);}

bool empty() const {return c.empty();}

size_type size()
const {return c.size();}

const_reference top()
const {return c.front();}

void push(const value_type& x)

{

__STL_TRY

{

c.push_back(x);

push_heap(c.begin(), c.end(), comp);

}

__STL_UNWIND(c.clear());

}

void pop()

{

__STL_TRY

{

pop_heap(c.begin(), c.end(), comp);

c.pop_back();

}

__STL_UNWIND(c.clear());

}

/*

总结:

同queue
不提供迭代器。

不同queue,底层实现是用vector实现的(queue底层是deque实现的)

原因:queue每次进队列都在队尾,出队列都在队首,频繁地对头尾进行操作,

deque比vector性能好很多

priority_queue虽然也是队尾进,队首出,但是不可避免的是每次都要调整位置,

所以采用堆加vector是很好的选择(deque的随机访问是要比vector慢的),采用

堆每次插入,取出,都只用log(n)的时间,所以很好.

*/

};

}

//slist

{

/*

slist概述:

list是双向链表(double linked list),slist是单向链表

slist的迭代器属于单向的ForwardIterator,所以功能被限制了很多

但是耗用的空间小,操作更快.(我们大部分人最先接触的链表数据结构就是单向链表)

slist不提供push_back(),

*/

//__slist_node

struct __slist_node_base

{

__slist_node_base* next;

};

template <class T>

struct __slist_node :
public __slist_node_base

{

T data;

};

//添加一个节点(new_node)到prev_node之后

inline __slist_node_base* __slist_make_link(

__slist_node_base* prev_node,

__slist_node_base* new_node)

{

new_node->next = prev_node->next;

prev_node->next = new_node;

return new_node;

}

//通过循环判断node节点之后(包括node节点)一共有多少节点

inline size_t __slist_size(__slist_node_base* node)

{

size_t result =
;

; node = node->next)

++result;

return result;

}

//__slist_iterator

struct __slist_iterator_base

{

typedef size_t size_type;

typedef ptrdiff_t difference_type;

typedef forward_iterator_tag iterator_category;

//这里用基类创建一个节点

__slist_node_base* node;

__slist_iterator_base(__slist_node_base* x) :node(x){}

//相当于++操作

void incr() { node = node->next; }

//迭代器是否相等取决于他们的节点是否相等

bool operator==(const __slist_iterator_base& x)
const

{

return node == x.node;

}

bool operator!=(const __slist_iterator_base& x)
const{

return node != x.node;

}

};

//T: class Ref class& Ptr  class*

template<class T,
class Ref, class Ptr>

struct __slist_iterator :
public __slist_iterator_base

{

typedef __slist_iterator<T, T&, T*>     iterator;

typedef __slist_iterator<T,
const T&, const T*>     const_iterator;

typedef __slist_iterator<T, Ref, Ptr>   self;

typedef T   value_type;

typedef Ptr pointer;

typedef Ref reference;

//节点类型

typedef __slist_node<T> list_node;

__slist_iterator(list_node* x) : __slist_iterator_base(x) {}

__slist_iterator() : __slist_iterator_base(){}

__slist_iterator(const iterator& x) : __slist_iterator_base(x.node) {}

//node是__slist_node_base类型
需要强制转化

reference
operator*() const {return ((list_node*) node)->data;}

pointer
operator->() const {return &(operator*());}

self&
operator++()

{

incr();

return *this;

}

self
operator++(int)

{

self temp = *this;

incr();

return temp;

}

//并没有operator--操作

};

//class slist

template< class T,
class Alloc = allic>

class slist

{

public:

typedef T value_type;

typedef value_type* pointer;

typedef const value_type* const_pointer;

typedef value_type& reference;

typedef const value_type& const_reference;

typedef size_t size_type;

typedef ptrdiff_t difference_type;

typedef __slist_iterator<T, T&, T*> iterator;

typedef __slist_iterator<T,
const T&, const T*> const_iterator;

private:

typedef __slist_node<T> list_node;

typedef __slist_node_base list_node_base;

typedef __slist_iterator_base iterator_base;

typedef simple_alloc<list_node, Alloc> list_node_allocator;

//申请内存并调用构造函数

static list_node* create_node(const value_type& x)

{

list_node* node = list_node_allocator::allocate();

__STL_TRY

{

construct(&node->data, x);

node->next=;

}

__STL_UNWIND(list_node_allocator::deallocate(node));

return node;

}

static void destroy_node(list_node* node)

{

destroy(&node->data);

list_node_allocator::deallocate(node);

}

private:

list_node_base head;

public:

slist() { head.next =
; }

//clear()是循环删除所有节点

~slist() {clear();}

iterator begin() {return iterator((list_node*)head.next);}

//强制转化一个0为iterator类型表示end

//最开始的时候,head.next等于0
表示末尾;

iterator end() {);}

size_type size()
const {return __slist_size(head.next);}

bool empty() const {return head.next ==
;}

void swap(slist& L)

{

list_node_base* tmp =head.next;

head.next = L.head.next;

L.head.next = tmp;

}

public:

reference front() {return ((list_node*) head.next)->data;}

void push_front(const value_type& x)

{

__slist_make_link(&head, create_node(x));

}

void pop_front()

{

list_node* node = (list_node*) head.next;

head.next = node->next;

destroy_node(node);

}

};

/*

总结:

同deque一样,我还是不知道为什么在迭代器中会有self和iterator两个typedef

为什么要特地弄出两个基类?
这样的好处貌似是一个链表可以存放不同的数据类型,但是

并没有用啊。在使用slist<T>来声明定义变量时就确定了类型了。

别的没什么特别的技巧,就是一个很普通的list

*/

}

stl源码剖析 详细学习笔记priority_queue slist的更多相关文章

  1. stl源码剖析 详细学习笔记 hashtable

    //---------------------------15/03/24---------------------------- //hashtable { /* 概述: sgi采用的是开链法完成h ...

  2. stl源码剖析 详细学习笔记 set map

    // //  set map.cpp //  笔记 // //  Created by fam on 15/3/23. // // //---------------------------15/03 ...

  3. stl源码剖析 详细学习笔记 RB_tree (1)

    // //  RB_tree_STL.cpp //  笔记 // //  Created by fam on 15/3/21. // // #include "RB_tree_STL.h&q ...

  4. stl源码剖析 详细学习笔记heap

    // //  heap.cpp //  笔记 // //  Created by fam on 15/3/15. // // //---------------------------15/03/15 ...

  5. stl源码剖析 详细学习笔记 空间配置器

    //---------------------------15/04/05---------------------------- /* 空间配置器概述: 1:new操作包含两个阶段操作 1>调 ...

  6. stl源码剖析 详细学习笔记 算法(1)

    //---------------------------15/03/27---------------------------- //算法 { /* 质变算法:会改变操作对象之值 所有的stl算法都 ...

  7. stl源码剖析 详细学习笔记 算法总览

    //****************************基本算法***************************** /* stl算法总览,不在stl标准规格的sgi专属算法,都以 *加以标 ...

  8. stl源码剖析 详细学习笔记 RB_tree (2)

    //---------------------------15/03/22---------------------------- //一直好奇KeyOfValue是什么,查了下就是一个和仿函数差不多 ...

  9. stl源码剖析 详细学习笔记stack queue

    // //  stack.cpp //  笔记 // //  Created by fam on 15/3/15. // // //---------------------------15/03/1 ...

随机推荐

  1. 根据模板导出Excel报表并复制模板生成多个Sheet页

    因为最近用报表导出比较多,所有就提成了一个工具类,本工具类使用的场景为  根据提供的模板来导出Excel报表 并且可根据提供的模板Sheet页进行复制 从而实现多个Sheet页的需求, 使用本工具类时 ...

  2. 表迁移工具的选型-复制ibd的方法-传输表空间

    1.1. 场景 有的时候开放人员自己的库需要帮忙导一些数据,但是表的数据量又很大.虽然说使用mysqldump或mysqlpump也可以导.但是这耗时需要比较久. 记得之前建议开放人员可以直接使用na ...

  3. MySQL5.7多实例自动化部署脚本

    一.安装说明 ------------------------------------------------------ mysql5.7.10_onekey_install.sh自动化部署脚本支持 ...

  4. python的学习之路day3

    大纲 1.汉字编码 2.浅拷贝与深拷贝 3.函数 4.return 5.函数的基本参数 6.format 7.三元运算(三目运算) 8.python的内置函数 abs() all() any() bo ...

  5. 从PFX文件中获取私钥、公钥证书、公钥

    https://blog.csdn.net/ZuoYanYouYan/article/details/77868584 该类具体功能:根据pfx证书得到私钥.根据私钥字节数组获取私钥对象.根据公钥字节 ...

  6. 【存在问题,待修改】SSH 远程登陆

    0. 前提 设置 hosts 参考链接 Linux 配置 hosts SSH公钥登录原理 1. SSH 是什么 SSH ( Secure Shell ) 是一种协议标准,其目的是实现安全远程登录以及其 ...

  7. WCF 基于 WinForm 宿主 发布

    ServiceHost Host = new ServiceHost(typeof(ServiceHTTP)); //绑定 System.ServiceModel.Channels.Binding h ...

  8. myeclipse10无法weblogic10.3的问题解决方案

    在完成了myec与wl10的基本配置后,启动报如下错误 Parsing Failure in config.xml: java.lang.AssertionError: java.lang.Class ...

  9. NOIP模拟赛-2018.11.5

    NOIP模拟赛 好像最近每天都会有模拟赛了.今天从高二逃考试跑到高一机房,然而高一也要考试,这回好像没有拒绝的理由了. 今天的模拟赛好像很有技术含量的感觉. T1:xgy断句. 好诡异的题目,首先给出 ...

  10. ap、map值计算

    ap:所有图片某一个类 map:所有图片所有类的ap的平均 以一个score为阈值,大于score的所有框是假定正确输出的所有预测,将这些框和gt匹配(iou大于某一个阈值认为匹配成功),得到当前sc ...