Reputation: 35
What is the best way to populate with values this type?
typedef std::map<std::string, std::pair<std::vector<double>, std::vector<double>>> buf;
So, I need something like this:
(“Label”, {1,2,3}, {100,200,300})
Thank you in advance!
UP: So, I came to this. But it looks not very nice I think:
double a[] = {0.1, 0.2};
double b[] = {0.0, 0.0};
foo.insert( make_pair("box", make_pair(vector<double>(a, a + sizeof(a) / sizeof(a[0])), vector<double>(b, b + sizeof(b) / sizeof(b[0]))) ) );
Upvotes: 0
Views: 1324
Reputation: 1
For simplifying the creation of a (with compile-time constants) filled map I created templates like this:
#include <map>
#include <type_traits>
template<typename... Ts>
constexpr auto make_map(Ts&&... ts)
-> std::map<typename std::common_type_t<Ts...>::first_type,typename std::common_type_t<Ts...>::second_type>
{
return { std::forward<Ts>(ts)... };
}//---------------------------------------------------------
It can be used like this:
using namespace std;
auto myDict = make_map(make_pair(666,string("the number of the beast"))
,make_pair(667,string("the neighbor of the beast"))
);
creating myDict as a "map< int,string >".
Or in your case use it like this:
using namespace std;
auto myDict = make_map(make_pair(string("label")
, make_pair(make_vector(1.,2.,3.)
,make_vector(100.,200.,300.)
)
)
);
("make_vector" can be defined pretty similar to "make_map")
The make_... approach is helpful (or at least "to me seems to be") because it omits an explicit template type declaration by taking the type(s) from the parameters.
Maybe this is somehow helpful to others too (or at least inspiring :-))...
Upvotes: 0
Reputation: 12178
if it's C++11 or newer
buf x = {{"Label", {{1,2,3}, {100, 200, 300}}};
EDIT
Without C++11 if you really want to populate with literals (like in your example), create helper function:
template <int N, int M>
std::pair<std::vector<double>, std::vector<double>> build_pair(double(&x)[N], double(&y)[M])
{
return std::make_pair(std::vector<double>(x, x + N), std::vector<double>(y, y + M));
}
and you can use it:
double x[] = { 1, 2, 3 };
double y[] = { 100, 200, 300 };
b["Label"] = build_pair(x, y);
Upvotes: 1
Reputation: 10756
Just in case you meant that the vectors already exist and you're not initializing the map at the time of construction with literal values, then you'd typically use std::make_pair
for creating the pair of vectors, as well as the key/value pair going into the map.
#include <utility>
buf my_map;
my_map.insert(std::make_pair(label, std::make_pair(vector1, vector2)));
Upvotes: 1
Reputation: 69882
typedef std::map<std::string, std::pair<std::vector<double>, std::vector<double>>> buf;
buf mybuf {
{
"Label",
{
{1,2,3}, {100,200,300}
}
},
{
"Label2",
{
{4,5,6}, {400,500,600}
}
}
};
Upvotes: 0
Reputation: 303067
With lots and lots of braces:
buf my_map { // <== whole map
{ // <== next individual map item
"Label", // <== key
{ // <== value
{1.0, 2.0, 3.0}, // <== value.first
{100.0, 200.0, 300.0} // <== value.second
}
}
};
Which when you put the whole item on one line reads:
buf my_map {
{"Label", {{1.0, 2.0, 3.0}, {100.0, 200.0, 300.0}}}
};
Upvotes: 1
Reputation: 117876
You can use insert
typedef std::map<std::string, std::pair<std::vector<double>, std::vector<double>>> buf;
int main()
{
buf foo;
foo.insert({"Label", {{1,2,3}, {100,200,300}}});
}
Note that you need an enclosing {}
to indicate your std::pair
.
Upvotes: 2