2

im making an operator for comparing objects of my own class 'Paciente', but when calling (const) getters of that class, Im getting errors. Here I leave the code:

bool operator==(const Paciente& p1, const Paciente& p2){
    return (p1.getNombre() == p2.getNombre() && p1.getApellidos() == p2.getApellidos());
}

Here the class Paciente:

class Paciente {

    private:
        string nombre_;
        string apellidos_;
        int edad_;

    public:
        Paciente(const string &nombre="none", const string &apellidos="none", const int &edad=0): nombre_(nombre), apellidos_(apellidos), edad_(edad){};
        const string & getNombre(){return nombre_;};
        const string & getApellidos(){return apellidos_;};
        const int & getEdad() {return edad_;};
        string setNombre(const string &nombre){nombre_ = nombre;};
        string setApellidos(const string & apellidos){apellidos_ = apellidos;};
        int setEdad(const int &edad){edad_ = edad;};
};

Class Paciente is allocated at 'paciente.hpp', and the operator and many more functions at 'functions.hpp'. I know it's not the right way to implemente operators, but with the other ways also got errors. Thanks.

EDIT: forgot to mention, the error is: passing ‘const Paciente’ as ‘this’ argument discards qualifiers [-fpermissive]

Ðаn
  • 10,934
  • 11
  • 59
  • 95

1 Answers1

4

bool operator==(const Paciente& p1, const Paciente& p2)

This has two constant objects as parameters.

However,
const string & getNombre(){return nombre_;};
is not a constant method and thus not allowed to be called on a constant object, which is what you try to do with p1.getNombre().
Simply change it to
const string& getNombre() const { return nombre_; }.

To elaborate a bit more on that, since you wrote "but when calling (const) getters of that class": A method is exactly const if you declare it as such, as I did. Simply it semantically not changing the object is not enough. The compiler is not "clever" enough to check semantics, and it really shouldn't be, easy source for errors.
Also note that it returning a const string& does not make the method const. Simply think of a signature like
const string& iterate_one_step_and_return_status_string();
(yes, this is horrible long name one should not use).

By the way, the semicolons at the end of your method implementations do nothing. You need those only when you only declare but not implement.
Also, I'd recommend to use english for everything but values. In this case, it is not that important, but should you post code for which us understanding what you want to do is important, it is helpful if we can get to know that by the names.

Edit: another problem with your code I noticed:
string setNombre(const string &nombre){nombre_ = nombre;};
This method has return type string yet does not return anything. I actually wonder why your compiler hasn't given you a warning or error like Error: control may reach end of non-void function.
(This also applies to your other setters.)

Aziuth
  • 3,652
  • 3
  • 18
  • 36
  • Great, answer, because we can call only const methods on const objects, since such objects are read-only and are not supposed to change unless they have mutable data members – octopus Jan 21 '20 at 15:31
  • ...at which point only those mutable vars may be changed. That's what `mutable` is for. And `mutable` is used mostly for "lazy evaluation" getFoo(): When the return value won't change, but you haven't determined what that value is. EX: A class has `int a, b, mutable sum`. Rather than doing *all that work* to add a couple integers every time someone calls getSum(), you only calculate it when it's changed *and then queried*, and set the mutable `sum`, so it can be reused. Great when some values may never be queried, and some might be queried repeatedly. – Mark Storer Jan 21 '20 at 15:43