'C++ unordered_set insert accepts constructor parameters?
Given these two classes
class User {
string name;
string eMail;
pair<string, string> titleReading;
vector<pair<string, string> > titlesRead;
}
class UserRecord {
User* userPtr;
public:
UserRecord(User* user);
string getName() const;
string getEMail() const;
void setEMail(string eMail);
};
And this class which contains an unordered_set of UserRecords
struct userRecordHash
{
int operator() (const UserRecord& ur) const
{
hash<string> h;
return h(ur.getEMail());
}
bool operator() (const UserRecord& ur1, const UserRecord& ur2) const
{
return ur1.getEMail()==ur2.getEMail();
}
};
typedef tr1::unordered_set<UserRecord, userRecordHash, userRecordHash> HashTabUserRecord;
class ReadingClub {
vector<Book*> books;
BST<BookCatalogItem> catalogItems;
HashTabUserRecord userRecords;
priority_queue<User> readerCandidates;
};
Why am I able to do unordered_set.insert(User*)? Does it call the UserRecord constructor?
Solution 1:[1]
Your UserRecord::UserRecord(User*) constructor is a converting constructor, which means that it implicitly converts a User* value into a UserRecord object.
If you wish to prohibit this you can mark the constructor as explicit such that no automatic conversion is ever performed implicitly. You will always have to explicitly call the constructor you want to use.
This has nothing to with std::unordered_set. Observe:
struct I { I(int) {} };
struct E { explicit E(int) {} };
int main(){
I a = 0; // okay
E b = 0; // not okay
E c(0); // okay
E d = E(0); // okay
}
Note that with an explicit constructor, you could still std::unordered_set::emplace values (as opposed to insert). Or you could explicitly create the object you want to insert.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 |
