加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

c – 使用char *构建动态结构的更好方法?

发布时间:2020-12-16 10:01:08 所属栏目:百科 来源:网络整理
导读:我想使用C语言的C风格的API,它采用可变数量的结构与char *成员,如下所示: typedef struct _FOO{ const char * name; const char * value;} FOO;void ApiFunc(FOO const* args,unsigned count); 为了填充参数,我需要循环其他一些数据并动态创建FOO条目.最优
我想使用C语言的C风格的API,它采用可变数量的结构与char *成员,如下所示:

typedef struct _FOO
{
    const char * name;
    const char * value;
} FOO;

void ApiFunc(FOO const* args,unsigned count);

为了填充参数,我需要循环其他一些数据并动态创建FOO条目.最优雅的方式是什么?

下面的方法起初看起来很简单,但不起作用(因为字符串实例超出范围并在调用ApiFunc()之前被销毁):

// Approach A: this does *not* work
std::vector<FOO> args;

for (...)
{
   string name = ...   // something which gets
   string value = ...  // calculated in the loop
   args.push_back( FOO{name.c_str(),value.c_str()} );
}

ApiFunc( args.data(),args.size() );

将字符串对象放在向量中(以防止它们被破坏)也不起作用 – 因为字符串在放入向量时被复制,而原始字符串仍然被销毁:

// Approach B: this also does *not* work
std::vector<string> strings;
for (...)
{
   string name = ...   // something which gets
   string value = ...  // calculated in the loop
   strings.push_back( name );
   strings.push_back( value );
   args.push_back( FOO{name.c_str(),args.size() );

我可以通过在堆上创建字符串对象并使用auto_ptr来跟踪它们来防止这种情况,但是有更好的方法吗?

// Approach C: this does work
std::vector<auto_ptr<string>> strings;
for (...)
{
   string* name = new ...   
   string* value = new  ... 
   strings.push_back( auto_ptr<string>(name) );
   strings.push_back( value );
   args.push_back( FOO{name.c_str(),args.size() );

虽然方法C似乎有用,但我发现它相当不明显/难以理解.有什么建议我可以改进吗?

解决方法

我很确定std :: vector< auto_ptr< T>>标准不允许.请改用unique_ptr.或者,在向量中构建字符串,然后从中构建args.

std::vector<std::pair<std::string,std::string>> strings;
for (...)
{
     const std::string name = ...;
     const std::string value = ...;
     strings.push_back( std::make_pair( name,value ) );
}
// Note: This loop must be separate so that 'strings' will not reallocate and potentially
// invalidate the pointers returned by elements in it.
for (const auto& pair : strings)
{
    args.push_back( FOO{pair.first.c_str(),pair.second.c_str()} );
}

ApiFunc( args.data(),args.size() );

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读