tags:

views:

121

answers:

3

is it possible to insert a new element to std::set like in case of std::list for example:

//insert one element named "string" to sublist of mylist

std::list< std::list<string> > mylist;
mylist.push_back(std::list<string>(1, "string"));

Now, mylist has one element of type std::string in its sub-list of type std::list.

How can you do the same in if std::set is the sub-set of std::list my list i.e

std::list<std::set <string>> mylist;

if you can't then why not?

+4  A: 

I think this should do the trick:

int main()
{
    string s = "test";
    set<string> mySet(&s, &s+1);

    cout << mySet.size() << " " << *mySet.begin();

    return 0;
}

For clarification on the legality and validity of treating &s as an array, see this discussion: http://stackoverflow.com/questions/2405555/string-s-s1-legal-ub

John Dibling
It works, but how does it?
Dave18
John Dibling
Kristo
@Kristo: Yes, I was wondering about that myself. And I was prepared to accept downvotes on this if that were the case, but I'm still not sure. After all, you are doing the same thing: `std::set<int> foo(
John Dibling
John Dibling
I'm going to accept it as a answer, If I get any errors on testing, I'll post an update.
Dave18
@Kristo: John Dibling posted a question to get clarification on whether it's undefined behavior or not. Bottom line - a single object can be treated as an array of one element for the purposes of pointer arithmetic: http://stackoverflow.com/questions/2405555/string-s-s1-legal-ub
Michael Burr
@Michael - thanks, I learned something new today. And the Josuttis book, p. 218-219 confirms it. I've updated my answer accordingly.
Kristo
+1  A: 

std::set doesn't have a constructor that takes an element to be inserted. The best you can do is use the range constructor:

int a[] = {1,2,3,4,5};
std::set<int> foo(a, a+5);  // insert the values 1 through 5 into foo

This version takes a begin and end iterator describing the range to be inserted into the set. You can optionally supply a sorting criterion as well. It's not quite what you wanted, but it's close. So if you had your elements stored in a container v, you can insert a new set to your list like this:

list<set<string> > myList;
myList.push_back(set<string>(v.begin(), v.end()));
Kristo
A: 

Or, in C++0x:

    std::list<std::set<int>> foo;
    foo.push_back({1,2,3});
McBeth
This also worked foo.push_back(set<string>({"foo","bar","quzz"}));
McBeth