I tried to use custom comparator in a std::set
. When I insert cuisine "japaneses" in a variable bucketCuisines
, I get error DEADLYSIGNAL.
But, If i eliminate the custom comparator cmp
there is no problem. But of course my results are incorrect.
Input:
["FoodRatings","highestRated","highestRated","changeRating","highestRated","changeRating","highestRated"]
[[["kimchi","miso","sushi","moussaka","ramen","bulgogi"],["korean","japanese","japanese","greek","japanese","korean"],[9,12,8,15,14,7]],["korean"],["japanese"],["sushi",16],["japanese"],["ramen",16],["japanese"]]
Result:
[null, "kimchi", "ramen", null, "sushi", null, "ramen"]
class FoodRatings {
public:
static bool cmp(pair<int, string> a, pair<int, string> b){
if(a.first == b.first)
return a.second < b.second;
return a.first > b.first;
}
unordered_map<string, int> bucketFoods;
unordered_map<string, string> bucketFoodNCuisine;
map<string, set<pair<int, string>, decltype(cmp)*>> bucketCuisines;
FoodRatings(vector<string>& foods, vector<string>& cuisines, vector<int>& ratings) {
int n = foods.size();
for(int i=0; i<n; i ){
bucketFoods.insert(make_pair(foods[i],ratings[i]));
cout << "1 ok\n";
bucketFoodNCuisine.insert(make_pair(foods[i], cuisines[i]));
cout << "2 ok\n";
bucketCuisines[cuisines[i]].insert(make_pair(ratings[i], foods[i]));
cout << "3 ok\n";
}
}
void changeRating(string food, int newRating) {
int oldRating = bucketFoods[food];
bucketFoods[food] = newRating;
string temp = bucketFoodNCuisine[food];
bucketCuisines[temp].erase(bucketCuisines[temp].find(make_pair(oldRating, food)));
bucketCuisines[temp].insert(make_pair(oldRating, food));
}
string highestRated(string cuisine) {
return bucketCuisines[cuisine].begin()->second;
}
};
CodePudding user response:
Your data type set<pair<int, string>, decltype(cmp)*>
is an odd way to specify the comparator as a function pointer. But that's what it does, and the issue is likely because you never provide a valid comparator when constructing these sets.
When you add an entry to bucketCuisines
, you're currently relying on the default constructor for this set. But that will initialize the comparator function pointer to nullptr
. When you go to add stuff to the set, the null comparator is invoked and your program crashes.
The simplest way around this is to make the comparator a functor instead:
struct cmp {
bool operator()(const pair<int, string>& a, const pair<int, string>& b) const
{
if(a.first == b.first)
return a.second < b.second;
return a.first > b.first;
}
};
map<string, set<pair<int, string>, cmp>> bucketCuisines;