Короткий ответ, как вы видели, таков: вы не можете этого сделать.
Я думаю, что вы действительно хотите это:
std::map<std::string, Foo> map;
int main()
{
map["bar"] = Foo();
Если вам действительно нужна инициализация для выполнения до main()
, вы часто будете видеть такие примеры:
namespace {
struct StaticInitHelper {
StaticInitHelper() { map["bar"] = Foo(); }
} _helper_obj;
}
Однако теперь у вас возникла новая проблема, заключающаяся в том, что нет гарантии, что map
будет создан до _helper_obj
. Один из способов обойти это - объединить их:
namespace {
struct StaticInitHelper : public std::map<std::string, Foo> {
StaticInitHelper() { (*this)["bar"] = Foo(); }
} map;
}
Однако наследование от классов контейнеров STL обычно не рекомендуется. Обратите внимание, что этот пример скрывает любые другие конструкторы, и базовый класс STL не имеет виртуального деструктора. Многие считают это "взломом", и его действительно следует избегать.
Еще одна альтернатива - определить класс с помощью std::map
:
namespace {
struct StaticInitHelper {
StaticInitHelper() { map["bar"] = Foo(); }
std::map<std::string, Foo> map;
} map_holder;
}
map_holder.map.find(...
Но, конечно, это затрудняет любое использование карты.
Обновление:
Я забыл упомянуть другой вариант, используя boost::assign
:
#include <boost/assign/list_of.hpp>
map<int,int> map = boost::assign::map_list_of(1,2)(2,3)(3,4)(4,5)(5,6);
Я не могу найти информацию о том, безопасно ли это для статического объекта.