StrBlobPtr类——weak_ptr访问vector元素

#include <iostream>
#include <memory>
#include <string>
#include <initializer_list>
#include <vector>
#include <stdexcept>

using namespace std;

class StrBlobPtr;

class StrBlob {
    friend class StrBlobPtr;
public:
    using size_type = vector<string>::size_type;
    StrBlob();
    StrBlob(initializer_list<string> il);
    size_type size() const { return data->size(); }
    bool empty() const { return data->empty(); }
    void push_back(const string &s);
    void pop_back();
    //返回string的引用,是因为调用点会使用该string
    //如b.front() = "first";
    string& front();
    string& back();
    //只有const StrBlob对象才会调用以下函数
    const string& front() const;
    const string& back() const;
    StrBlobPtr begin();
    StrBlobPtr end();
private:
    shared_ptr<vector<string>> data;
    void check(size_type i, const string &msg) const;
}; 

StrBlob::StrBlob(): data(make_shared<vector<string>>())
{
}

StrBlob::StrBlob(initializer_list<string> il): data(make_shared<vector<string>>(il))
{
}

void StrBlob::check(size_type i, const string &msg) const
{
    if (i >= data->size())
        throw out_of_range(msg);
}

void StrBlob::push_back(const string &s)
{
    data->push_back(s);
}

void StrBlob::pop_back()
{
    check(0, "此StrBlob对象指向一个空vector!\n");
    data->pop_back();
}

string& StrBlob::front()
{
    check(0, "此StrBlob对象指向一个空vector!\n");
    return data->front();
}

string& StrBlob::back()
{
    check(0, "此StrBlob对象指向一个空vector!\n");
    return data->back();
}

const string& StrBlob::front() const
{
    check(0, "此StrBlob对象指向一个空vector!\n");
    cout << "调用对象为const StrBlob!\n";
    return data->front();
}

const string& StrBlob::back() const
{
    check(0, "此StrBlob对象指向一个空vector!\n");
    cout << "调用对象为const StrBlob!\n";
    return data->back();
}

class StrBlobPtr {
public:
    StrBlobPtr(): curr(0) {}
    StrBlobPtr(StrBlob &b, size_t sz = 0): wptr(b.data), curr(sz) {}
    string& deref() const;
    StrBlobPtr& incr();
private:
    weak_ptr<vector<string>> wptr;
    size_t curr;
    shared_ptr<vector<string>> check(size_t i, const string &msg) const;
};

shared_ptr<vector<string>> StrBlobPtr::check(size_t i, const string &msg) const
{
    auto ret = wptr.lock();
    if (!ret)
        throw runtime_error("要访问的vector<string>对象不存在!\n");
    if (i >= ret->size())
        throw out_of_range(msg);
    return ret;
}

string& StrBlobPtr::deref() const
{
    auto p = check(curr, "当前下标不合法!\n");
    return (*p)[curr];
}

StrBlobPtr& StrBlobPtr::incr()
{
    check(curr, "不能继续递增了\n");
    ++curr;
    return *this;
}

StrBlobPtr StrBlob::begin()
{
    return StrBlobPtr(*this);
}

StrBlobPtr StrBlob::end()
{
    return StrBlobPtr(*this, data->size());
}

int main()
{
    StrBlob b1{"mon", "tue", "wed", "thu", "fri"};
    StrBlobPtr p(b1, 3);
    cout << p.deref() << endl;            //访问p当前指向的元素
    cout << p.incr().deref() << endl;    //先递增p,再访问元素
    p = b1.begin();
    cout << p.deref() << endl;
    return 0;
}
时间: 2024-08-29 12:39:05

StrBlobPtr类——weak_ptr访问vector元素的相关文章

访问vector元素方法的效率比较(转)

vs2015中测试: 1 #include<iostream> 2 #include<vector> 3 #include<windows.h> 4 using namespace std; 5 6 7 8 int main() { 9 //建立4个vector,使用列表初始化,相当与调用拷贝构造函数 10 vector<int> v1; 11 int temp; 12 int i; 13 for (i = 0; i < 100000; ++i) {

Struts2学习之路(五)—— 访问web元素

以下是Action类中访问web元素的示例,共有四种方法.其中第一种和第三种依赖容器,第二种和第四种利用IOC思想.前面两种取得Map类型的request.session.application:后面两种是真实类型HttpServletRequest.HttpServletSession.ServletContext的引用. 1.第一种方法: 1 package com.user.action; 2 3 import java.util.Map; 4 5 import com.opensymph

C++ 安全并发访问容器元素

C++ 安全并发访问容器元素 2014-9-24 flyfish 标准库STL的vector, deque, list等等不是线程安全的 例如 线程1正在使用迭代器(iterator)读vector 线程2正在对该vector进行插入操作,使vector重新分配内存,这样就造成线程1中的迭代器失效 STL的容器 多个线程读是安全的,在读的过程中,不能对容器有任何写入操作 多个线程可以同时对不同的容器做写入操作. 不能指望任何STL实现来解决线程难题,必须手动做同步控制. 方案1 对vector进

deque双端队列容器(对象创建,数组、迭代器方式访问,元素的赋值、插入、删除等)

deque与vector非常相似,不仅可以在尾部插入和删除元素,还可以在头部插入和删除.不过当考虑到容器元素的内存分配策略和操作性能时,deque相对vector较为有优势. 头文件 #include<deque> 创建deque对象 1)deque();//创建一个没有任何元素的deque对象. deque<int> d 2)deque(size_typen);//创建一个具有n个元素的deque对象,每个元素采用它的类型下的默认值. deque<int> d(10)

Struts2中访问web元素

有很多时候我们都需要访问web元素,比如说用户管理系统,用户登录成功了需要往session中放置一个值,然后要在前台拿到这个值,常用的web元素包括request.session和application等. Struts2中有四种方式可以访问到web元素: 1.通过ActionContext来访问Map类型的request.session.application对象. 2.通过实现RequestAware.SessionAware.ApplicationAware接口来访问Map类型的reque

c++ vector(向量)使用方法详解(顺序访问vector的多种方式)

来源:http://www.jb51.net/article/44231.htm 作者: 字体:[增加 减小] 类型:转载 时间:2013-12-08我要评论 vector是向量类型,它可以容纳许多类型的数据,如若干个整数,所以称其为容器,本文介绍一下使用方法 vector 是向量类型,它可以容纳许多类型的数据,如若干个整数,所以称其为容器.vector 是C++ STL的一个重要成员,使用它时需要包含头文件: 复制代码 代码如下: #include<vector>; 一.vector 的初始

Struts2访问web元素

一.为什么Action要访问web元素? 在使用struts2框架进行开发的时候, 页面与Action类进行交互, 由于Action中无法取得前端request.session.application.HttpServletRequest.HttpSession.ServletApplication,但是当有用户登录的时候, 需要在程序中为该用户创建session以标识该用户的登录状态及其他信息, 如何才能使得Action能够访问web元素,并把相应数据放到session.application

css3中伪类选择器和伪元素介绍

利用html5和css3开发出炫酷的网页,那么对于一个web前端开发者,css3也是必须要掌握的,下面和大家讨论一下css3中伪类选择器和伪元素. 类选择器 在css中可以使用类选择器把相同的元素定义成不同的样式.比如:p.left{text-align: left}p.rigth{text-align: right} 伪类选择器 类选择器和伪类选择器的区别在于,类选择器我们可以随意起名,而伪类选择器是CSS中已经定义好的选择器,不可以随意起名. 最常见的伪类选择器 a:link{ color:

java类的访问权限

1.解析 Java有四种访问权限, 其中三种有访问权限修饰符,分别为private,public和protected,还有一种不带任何修饰符. private: Java语言中对访问权限限制的最窄的修饰符,一般称之为“私有的”.被其修饰的类.属性以及方法只能被该类的对象访问,其子类不能访问,更不能允许跨包访问. default:即不加任何访问修饰符,通常称为“默认访问模式“.该模式下,只允许在同一个包中进行访问. protect: 介于public 和 private 之间的一种访问修饰符,一般