rvalue参考vector :: push_back函数如何提高效率
Confused by how the rvalue reference vector::push_back function increases effciency
来自cppreference.com,我找到了一个简单的示例,以使用std ::移动:
std::string str = "Hello";
std::vector<std::string> v;
// uses the push_back(const T&) overload, which means
// we'll incur the cost of copying str
v.push_back(str); // First push_back
std::cout << "After copy, str is "" << str << ""n";
// uses the rvalue reference push_back(T&&) overload,
// which means no strings will be copied; instead, the contents
// of str will be moved into the vector. This is less
// expensive, but also means str might now be empty.
v.push_back(std::move(str)); // Second push_back
评论说避免了弦副本。
第一个push_back将致电: void push_back(const value_type& _Val)
第二个push_back将致电: void push_back(value_type&& _Val)
我检查了两个功能的实现代码:
void push_back(const value_type& _Val)
{ // insert element at end
if (_Inside(_STD addressof(_Val)))
{ // push back an element
size_type _Idx = _STD addressof(_Val) - _Unfancy(this->_Myfirst());
if (this->_Mylast() == this->_Myend())
_Reserve(1);
_Orphan_range(this->_Mylast(), this->_Mylast());
this->_Getal().construct(_Unfancy(this->_Mylast()),
this->_Myfirst()[_Idx]);
++this->_Mylast();
}
else
{ // push back a non-element
if (this->_Mylast() == this->_Myend())
_Reserve(1);
_Orphan_range(this->_Mylast(), this->_Mylast());
this->_Getal().construct(_Unfancy(this->_Mylast()),
_Val);
++this->_Mylast();
}
}
和
void push_back(value_type&& _Val)
{ // insert by moving into element at end
if (_Inside(_STD addressof(_Val)))
{ // push back an element
size_type _Idx = _STD addressof(_Val) - _Unfancy(this->_Myfirst());
if (this->_Mylast() == this->_Myend())
_Reserve(1);
_Orphan_range(this->_Mylast(), this->_Mylast());
this->_Getal().construct(_Unfancy(this->_Mylast()),
_STD forward<value_type>(this->_Myfirst()[_Idx]));
++this->_Mylast();
}
else
{ // push back a non-element
if (this->_Mylast() == this->_Myend())
_Reserve(1);
_Orphan_range(this->_Mylast(), this->_Mylast());
this->_Getal().construct(_Unfancy(this->_Mylast()),
_STD forward<value_type>(_Val));
++this->_Mylast();
}
}
因此,根据我的理解,第一个push_back( v.push_back(str);
(和第二个push_back( v.push_back(std::move(str));
(都会触发向量构造 std::string
类型变量并将其连接到向量。
因此,实际上在两个push_back呼叫中,字符串未复制。而且,对于两个push_back,费用都是相同的,因为两个调用基本上都做同样的事情,除了第二个push_back将使 str
输入为空。
至于效率,我能想到的唯一区别是第二个push_back不会调用delete [] cstring;在STD :: string的攻击函数中,这使第二个push_back调用效率更高。
不确定我的理解是否正确。非常感谢!
区别在这里:
this->_Getal().construct(_Unfancy(this->_Mylast()),
_STD forward<value_type>(_Val));
vs
this->_Getal().construct(_Unfancy(this->_Mylast()),
_Val);
现在forward<value_type>
实际上在std::string
上调用std::move
。
在一种情况下,我们在std::string const&
中构造std::string
,另一个情况下由std::string &&
。
,要看到差异,我们必须检查这两个不同的构造函数。
std::string
通常使用SBO(小缓冲区优化(实现。如果字符串很短(十二个左右的字符(,则将字符串存储在 std::string
。
如果它更长,而std::string
则存储一个指针。
如果您有SBO活动,则移动并复制字节上的复制。然后移动可能会清除源。
std::string(std::string const&)
在非SBO的情况下进行分配并复制包含字符的缓冲区。
std::string(std::string &&)
在非SBO的情况下,将指针移至目标对象,然后清空源对象。没有内存分配,并且复制了零字节。
这是push_back(&&)
超载提供的。
诸如"小字符串"之类的优化的缩写, std::basic_string
基本上包含了基本上是指向字符串中字符的动态分配区域的指针。避免了这一副本,因为移动可以窃取移动的指针而不是分配其数据并复制数据。
- 如何提高该函数的运行效率?
- 做对了一个类似竞争的问题,但需要帮助来提高效率
- 为什么内联函数的效率低于内置函数
- rvalue参考vector :: push_back函数如何提高效率
- LVALUE和RVALUE返回类型以提高效率
- 在opencv中,使用垫子类型计算马氏距离太慢了。如何提高效率?
- 多线程计算均值和std并不能提高效率
- 将密钥哈希存储在类中以提高效率
- 斯特劳斯特鲁普 第 4 章 练习 6:提高效率
- 使用 C++ dll 函数提高 C# 项目的性能
- C++压缩两个for循环以提高效率
- C++函数的效率
- 气泡---提高效率
- 提高了一个非常简单但用途广泛的函数(计算晶格中原子的邻居)的效率
- 通过引用传递基本类型而不是通过值返回,可以提高效率
- 使用友字提高效率
- 应该在返回语句中使用std::move来提高效率吗?
- 有人只使用引用变量来提高效率和减小大小吗?
- std::set构造函数有时效率很低
- 如何在涉及浮点运算的特定代码中优化和提高效率