【问题标题】:what is the best way of filling map of struct in a function在函数中填充结构映射的最佳方法是什么
【发布时间】:2015-08-02 06:42:57
【问题描述】:

我有以下代码:

mystruct
{
    std::string str;
    int x;
}

void main()
{
   std::map<int, mystruct> mymap;
   func(mymap);
}

void func(std::map<int, mystruct>& mmap)
{
   mmap[1].str = "bla";
   mmap[1].x = 5;
}

在函数中填充地图的最佳方法是什么?这种方式正确吗? struct 是定义在栈上还是堆上?

【问题讨论】:

  • 你的代码不是有效的 C++,所以没有什么可担心的。映射、结构或“堆”。
  • 是的 - 我可以使用 c++11,为什么?我的方法不对吗?

标签: c++ dictionary struct


【解决方案1】:

您的代码不是有效的可编译 C++ 代码的原因有很多。我试图在下面的示例中修复它们,但除此之外,我看不出你的方式有什么特别的问题。

在 C++11 中,您可以使用初始化列表初始化 map。此外,如果您正在初始化一个新的map,使用返回值而不是引用参数会更习惯:

#include <map>
#include <string>

struct mystruct
{
    std::string str;
    int x;
};

std::map<int, mystruct> func()
{
   return {{1, {"bla", 5}}};
}

int main()
{
   auto myMap = func();
}

map 将为元素动态分配内存,因此结构将位于“堆”上。

【讨论】:

  • 谢谢,但我知道只在运行时插入地图的值,所以我不能使用初始化列表
  • @Shay Initializer 列表值不需要是编译时常量。
  • @Shay 我认为您需要展示一些更接近实际代码的内容,因为填写列表的方式有很多种,而“最佳”方式取决于您实际尝试执行的操作。就目前而言,我们只能根据您编写或猜测的代码来真正回答。
【解决方案2】:

嗯,这将是一种常见的最小下降方式。并且不用担心取消分配或堆。

#include <map>
#include <iostream>
using namespace std;
struct mystruct
{
   std::string str;
   int x;
   mystruct(int xx, string s) : x(xx), str(s){}
   mystruct() {}
};

void func(std::map<int, mystruct>& mmap, int k, mystruct v)
{
   auto itr = mmap.begin();
   if ((itr = mmap.find(k)) == mmap.end())
   {
      mmap.insert(pair<int, mystruct>(k, v));
   }
   else
   {
      mmap[k] = v;
   }

}

int main()
{
   std::map<int, mystruct> mymap;

   mystruct s(5, "bla");
   func(mymap, 1, s);

   // look up
   if (mymap.find(1) != mymap.end())
   {
      cout << "found";
   }
   else
   {
      cout << "not found";
   }
return 0;
}

【讨论】:

  • 只是mmap.insert(std::map&lt;int, mystruct&gt;::value_type(k, v)),返回一对iterator/bool,其中second表示插入成功(key不存在)
  • 谢谢,但是结构的值只知道运行时和内部函数 func,所以我需要在函数 func 中创建结构
  • @Shay 然后删除参数并在函数内部执行您必须执行的操作。
【解决方案3】:

如果func 旨在将元素添加到可能已经包含元素的现有地图并且不应删除这些元素,那么这是最好的方法:

void func(std::map<int, mystruct>& mmap)
{
   mmap[1] = { "bla", 5 };
}

否则,如果 func 只是应该填充(初始化)一个空映射,那么这是最好的方法(前提是您至少使用 C++11,对于 move返回值):

std::map<int, mystruct> func()
{
   std::map<int, mystruct> mmap;
   mmap[1] = { "bla", 5 };
   return mmap;
   // you could also use list initialization here as shown in Chris Drew's answer
}

auto mymap = func();

在这两种情况下,mmap 都在堆栈中。将它放在堆上需要调用std::make_uniquestd::make_sharednew(不要使用它)。

【讨论】:

  • mmap 本身将在堆栈上,是的,但在内部它将为堆上的元素分配内存。所以结构本身(这是他们要求的)将在堆上。
  • @ChrisDrew 哦,对,没错,我不知何故错过了句子的那一部分,谢谢。
猜你喜欢
  • 2015-12-18
  • 1970-01-01
  • 2021-05-20
  • 2019-05-29
  • 1970-01-01
  • 2012-08-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多