首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >C++结构初始化

C++结构初始化
EN

Stack Overflow用户
提问于 2017-01-04 23:44:19
回答 2查看 105关注 0票数 1

我在soecode.h中有以下结构声明:

代码语言:javascript
复制
    struct MySt
    {
        MySt( const char * m, const char * gm ):
            firstSen(m),
            secondSen(gm)
        {
        }

        std::string firstSen;
        std::string secondSen;
    };

以下是somecode.cpp中的代码:

代码语言:javascript
复制
        std::vector<MySt> dataSen;

        char * cp = trim(buff);
        std::vector<std::string> tokens;

        getTokens( cp, tokens );

        if(tokens.size() == 2 )
        {

            dataSen.push_back( MySt(tokens[0].c_str(), tokens[1].c_str() ));
        }

这段代码可以工作。我的问题是:这种类型的MySt初始化是堆栈还是堆,是动态分配的还是静态分配的?Thnx。

EN

回答 2

Stack Overflow用户

发布于 2017-01-04 23:53:09

这里发生了很多事情。

dataSen是一个向量,这意味着它在堆栈上有少量的空间来存储指向其存储的指针以及一些开销(如大小等),但它存储的所有内容都是通过它管理的分配在堆上的。

dataSen存储的类型std::string实际上有少量数据存储在您的向量中(也是在堆中),然后为它的数据创建一个自己的堆分配。

因此,您将数据读入一个标记向量,该向量将数据存储为字符串。字符串的存储在堆上(通过向量的堆分配),字符串中实际字符的存储也在堆上(通过字符串管理的堆分配)。

然后使用c_str()从每个字符串中获取const char*引用以创建临时MySt (它创建了两个新字符串,由const char*初始化),然后将此临时字符串复制到向量中,这意味着它存储在向量管理的堆中,每个字符串的数据通过字符串管理的不同分配存储在堆中。

现在..。

巧合的是,如果您使用emplace_back(const char*, const char*)而不是push_back(MySt(...)),您将在适当的位置构建它,而不是创建临时的和移动的。

此外,如果您为MySt添加了一个接受std:: string &&值的构造函数,那么您可以将已经创建的字符串移动到MySt中,以避免转换为const char*,然后从该字符串创建另一个字符串。

编辑您的评论:

代码语言:javascript
复制
struct MySt
{
    // existing constructor, creating strings from const char*
    MySt( const char * m, const char * gm ):
        firstSen(m),
        secondSen(gm)
    {
    }

    // constructor copying string inputs
    MySt( const std::string& m, const std::string& gm) :
        firstSen(m),
        secondSen(gm)
    {
    }

    // constructor moving existing strings (strings from calling code
    // will be in an unusable state other than to re-assign them to
    // something new... but it will take the allocated heap from the
    // existing strings as to avoid making another heap allocation)
    MySt( std::string&& m, std::string&& gm) :
        firstSen(std::move(m)),
        secondSen(std::move(gm))
    {
    }

    std::string firstSen;
    std::string secondSen;
};

然后使用...

代码语言:javascript
复制
getTokens( cp, tokens );

if(tokens.size() == 2 )
{
    // to copy...
    dataSen.emplace_back( tokens[0], tokens[1] );

    // or to move...
    dataSen.emplace_back( std::move(tokens[0]), std::move(tokens[1]) );
}
票数 2
EN

Stack Overflow用户

发布于 2017-01-05 00:16:57

  • 如果您将对象声明为全局对象或静态本地对象,则它们是静态分配的。
  • 如果您在块中声明,则它们在堆栈上分配。
  • 如果您使用new关键字,则它们在堆上分配。STL容器的
  • 元素也存储在堆上。<代码>H29<代码>F210
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/41467795

复制
相关文章

相似问题

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