dimanche 29 mai 2022

c++ shared pointer as key to map causes crash

So I'm working on a project for University in CPP, the idea is to utilize STL and smart pointers as much as possible(in an efficient matter of course).

I have created a map which contains a shared pointer to object of type Movie, and a vector of doubles. I have added a Comparison Class so the map compares the objects themselves and not pointers. When I initialize the map all is good, values are stored properly and I'm able to print them out. but when trying to access from a different function I get a EXC_BAD_ACCESS. while debugging I can still see the information exists so from my understanding its not that the pointers all went out of scope and the memory is freed.

Im adding the add and get functions,

typedef std::shared_ptr<Movie> sp_movie;

RecommenderSystem::get_movie (const std::string &name, int year) const
{
  const auto movie (std::make_shared<Movie> (name, year));
  const auto it=_database.find (movie);
  return it->first;
}


sp_movie RecommenderSystem::add_movie (const std::string &name, int year,
                              FeaturesVec &features)
{
  auto movie = std::make_shared<Movie> (name, year);
  _database.insert (std::make_pair (movie, features));
  return movie;
}

The exception gets thrown from _database.find call. This is the constructor and comparator:

struct DatabaseComp {
    bool operator() (const sp_movie &m1, const sp_movie &m2) const
    { return *m1 < *m2; }
};
/**
 * Key : sp_movie, Value : FeaturesVec(Just a fancy name for double vector)
 */
typedef std::map<sp_movie, FeaturesVec, DatabaseComp> MovieDatabase;

class RecommenderSystem {
 private:
  MovieDatabase _database = MovieDatabase (DatabaseComp ());
 public:
  /**
   * Constructor
   */
  explicit RecommenderSystem () = default;

Any ideas about what could be causing this?

EDITS The comparison operator for the Movie class itself :

bool operator< (const Movie &lhs) const
  {
    return this->_movie_year < lhs._movie_year
           || (this->_movie_year == lhs._movie_year && this->_movie_name <= lhs._movie_name);
  }

Crashing example , the program crashes on get_name method

int main ()
{
  RecommenderSystem rs;
  rs.add_movie ("Matrix1", 1999, {5, 5, 5, 5});
  rs.add_movie ("Matrix2", 2000, {4, 5, 4, 5});
  auto m = rs.get_movie ("Matrix1", 1999);
  std::cout << m->get_name () << " : " << m->get_year () << std::endl;
  rank_map rm (0, &sp_movie_hash, &sp_movie_equal);
  rm.insert (std::make_pair (m, 5.0));
  RSUser rs_user ("John", rm, std::make_shared<RecommenderSystem> (rs));
}

Aucun commentaire:

Enregistrer un commentaire