首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >标准库中隐藏着哪些贪婪的初始化程序列表示例?

标准库中隐藏着哪些贪婪的初始化程序列表示例?
EN

Stack Overflow用户
提问于 2013-11-07 22:25:55
回答 1查看 1.1K关注 0票数 14

从C++11开始,标准库容器和std::string就让构造函数接受初始化程序列表.此构造函数优先于其他构造函数(如@约翰内斯堡pointed litb在注释中指出的,甚至忽略了其他“最佳匹配”标准)。这将导致在将所有带括号的构造函数的()形式转换为其带括号的{}版本时出现一些众所周知的缺陷。

代码语言:javascript
运行
复制
#include <algorithm>
#include <iostream>
#include <iterator>
#include <vector>
#include <string>

void print(std::vector<int> const& v)
{
    std::copy(begin(v), end(v), std::ostream_iterator<int>(std::cout, ","));
    std::cout << "\n";
}

void print(std::string const& s)
{
    std::cout << s << "\n";
}

int main()
{
    // well-known 
    print(std::vector<int>{ 11, 22 });  // 11, 22, not 11 copies of 22
    print(std::vector<int>{ 11 });      // 11,     not 11 copies of 0

    // more surprising
    print(std::string{ 65, 'C' });      // AC,     not 65 copies of 'C'
}

我在这个站点上找不到第三个例子,在Lounge聊天中(在与@ count折叠、@Abyx和@JerryCoffin的讨论中),有点令人惊讶的是,将接受计数和字符的std::string构造函数转换为使用{}而不是()的字符,将其含义从字符的n副本更改为n-th字符(通常来自ASCII表),然后是其他字符。

这不是通常禁止缩小转换的大括号,因为65是一个常量表达式,可以表示为char,并在转换回int时保留其原始值(§8.5.4/7,项目4) (感谢@JerryCoffin)。

问题:在标准库中是否还有更多将()样式构造函数转换为{}样式的示例,是否有初始化-列表构造函数贪婪地匹配?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2013-11-07 22:43:24

我想,在std::vector<int>std::string的示例中,您还打算涵盖其他容器,例如std::list<int>std::deque<int>等,这些容器显然与std::vector<int>有相同的问题。同样,int并不是唯一的类型,因为它也适用于charshortlong及其unsigned版本(可能还有其他一些完整的类型)。

我认为也有std::valarray<T>,但我不确定是否允许T为整数类型。实际上,我认为它们有不同的语义:

代码语言:javascript
运行
复制
std::valarray<double>(0.0, 3);
std::valarray<double>{0.0, 3};

还有其他一些标准的C++类模板,它们都以std::initializer_list<T>作为参数,但我认为这些模板中没有一个具有重载的构造函数,在使用括号而不是大括号时将使用该构造函数。

票数 5
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/19847960

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档