auto_ptr为什么不能做为vector的元素
昨天看effectve c++的时候,发现了auto_ptr这个东西。由于我待过的公司都是用的老版c++,代码里智能指针什么的完全没有出现过,都是直接操作的原始指针。虽说我很少出错,但是总归还是不太安全。言归正传,说回auto_ptr,这个东西一开始我也见过,但是当时在赶项目也就没有怎么上心,这回正好看到了,就详细了解下。
在effiectev c++中我了解到,这是老版c++里的智能指针(之前我只知道c++11里的share_ptr和unique_ptr),同一个对象从始至终只会有一个auto_ptr指向它,也就是说当指向某个对象的auto_ptr被拷贝时(拷贝构造或者是赋值),原auto_ptr会被置为NULL。当指向对象的auto_ptr离开作用域后,会自动调用析构函数,从而达到防止资源泄露的目的。
很自然的,我想将我最近的新项目由操作裸指针改为智能指针,因为在项目中用到了STL标准容器,所以打算先用vector测试下auto_ptr。测试代码如下:
#include<iostream>
#include<vector>
#include<memory> class Test{
public:
Test() {
std::cout << "init" << std::endl;
} ~Test() {
std::cout << "del" << std::endl;
}
}; int main()
{
std::auto_ptr<Test> ap(new Test()); std::vector<std::auto_ptr<Test> > vec;
vec.push_back(ap); std::cout << ap.get() << std::endl;
return ;
}
编译时,提示auto_ptr过时的警告就不提了,报错如下:
/usr/include/c++//ext/new_allocator.h::: error: no matching function for call to ‘std::auto_ptr<Test>::auto_ptr(const std::auto_ptr<Test>&)’
{ ::new((void *)__p) _Up(std::forward<_Args>(__args)...); }
当时可能警告加报错信息太长,我没有看到这个const。。。然后想了很久想不通为什么不行,我当时的理解是vector将auto_ptr拷贝进去,原auto_ptr将变为0。然后怀疑自己将vector的push_back操作记错了,打开stl源码解析,找到vector加入元素时构造的函数:
template <class T1, class T2>
inline void construct(T1* p, const T2& value)
{
new (p) T1(value);
}
嗯?我没记错啊,为什么不能呢?然后我去网上搜了下,知道真相的我眼泪掉了下来。很简单:
因为将auto_ptr拷贝时需要对原auto_ptr进行修改,也就是将原auto_ptr置为NULL,所以不能支持以const的方式进行拷贝构造!
也就是说,auto_ptr是不能做为STL标准容器的元素的。
对于这个疑问的出现,我想一方面是自己不够细心,没有仔细看报错的含义;另一方面是自己的思维还有点欠缺,明明知识点都知道,但是没联想到。
auto_ptr为什么不能做为vector的元素的更多相关文章
- 3205: 数组做函数参数--数组元素求和1--C语言
3205: 数组做函数参数--数组元素求和1--C语言 时间限制: 1 Sec 内存限制: 128 MB提交: 178 解决: 139[提交][状态][讨论版][命题人:smallgyy] 题目描 ...
- PAT 甲级 1053 Path of Equal Weight (30 分)(dfs,vector内元素排序,有一小坑点)
1053 Path of Equal Weight (30 分) Given a non-empty tree with root R, and with weight Wi assigne ...
- 【C++】Vector判断元素是否存在,去重,求交集,求并集
1 #include <iostream> 2 #include <vector> 3 #include <algorithm> //sort函数.交并补函数 4 ...
- vector查找元素
转自:http://hi.baidu.com/chain2008/blog/item/821744585e12c5c89c8204e8.html 今天又忘了怎么在vector中查找某一个值..唉..每 ...
- vector删除元素与清除内存空洞
问题:stl中的vector容器经常造成删除假象,这对于c++程序猿来说是极其讨厌的,<effective stl>大师已经将之列为第17条,使用交换技巧来修整过剩容量. 内存空洞这个名词 ...
- C++ vector清空元素的三种方法
#include <iostream> #include <vector> using namespace std; //STL vector的几种清空容器(删除)办法 voi ...
- vector删除元素浅析
<<effectSTL>>书中提到erase-remove方法 即c.rease(remove(c.begin(),c.end(),1963),c.end()) 关于remo ...
- C++之vector中元素删除
今天在删除vector中的元素中遇到一个问题,这里记录下来以便以后查阅. 预备知识:用到了erase()函数,对于一个容器c来说,假设迭代器为p,那么执行: c.erase(p)之后就删除了容器c中p ...
- C++中标准容器Vector,元素操作.insert()小结
insert() 函数有以下三种用法: iterator insert( iterator loc, const TYPE &val ); //在指定位置loc前插入值为val的元素,返回指 ...
随机推荐
- php array function
说明:不特殊说明都支持php4,5,7 参考:https://www.php.net/manual/zh/ref.array.php is_array ( mixed $var ) : bool ...
- Android共享元素场景切换动画的实现
安卓5.0系统引入了共享元素,能做出非常炫酷的场景切换效果,这让人非常兴奋同时非常蛋疼,因为低版本没法使用啊,所以今天就跟大家分享一下自己写的一个库,其实只有2个文件而已就可以兼容安卓5.0以下的版本 ...
- ControlTemplate in WPF ——ScrollBar
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" x ...
- OpenFlow/SDN 的缘起与发展
目录 文章目录 目录 从虚拟机动态迁移对大二层网络的需求说起 OpenFlow 起源 从 OpenFlow 扩展为 SDN OpenFlow 的应用场景 网络虚拟化 – FlowVisor 负载均衡 ...
- LeetCode.1030-曼哈顿距离排序矩阵单元格(Matrix Cells in Distance Order)
这是小川的第384次更新,第412篇原创 01 看题和准备 今天介绍的是LeetCode算法题中Easy级别的第246题(顺位题号是1030).我们给出一个矩阵,其中R行和C列具有整数坐标(r,c)的 ...
- javase程序设计上机作业2
package javaxgp.teacher.test; import java.util.Scanner; public class Demo3 { public static void main ...
- python_面试题_DB相关问题
1.mysql部分 问题 问题1:mysql的存储引擎 问题2:mysql的索引机制 问题3:mysql的事务以及事务隔离级别 问题4:mvcc/GAP lock是做什么的 问题5:mysql的悲观锁 ...
- TCP中三次挥手四次握手
1.TCP连接 手机能够使用联网功能是因为手机底层实现了TCP/IP协议,可以使手机终端通过无线网络建立TCP连接.TCP协议可以对上层网络提供接口,使上层网络数据的传输建立在“无差别”的网络之上. ...
- 【Qt开发】QTableWidget设置根据内容调整列宽和行高
QTableWidget要调整表格行宽主要涉及以下一个函数 1.resizeColumnsToContents(); 根据内容调整列宽 ...
- mybati代码生成器 mybatis-generator
Mybatis代码生成器,用于快速生成代码 代码 https://github.com/wangxinforme/mybatis-generator