Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

initializing const fields in the constructor

const fields in C++ must be initialized in the initialization list, this makes non trivial the computation of interdependent values from the constructor parameters.

What is(are) the best way(s) to translate, for example, this piece of java code into c++ ?

public class SomeObject {
  private final String some_string;
  private final int some_int;

  public SomeObject(final String input_filename){
    SomeReader reader(input_filename);

    some_string = reader.getString();
    some_int = reader.getInt();

    reader.close();
  }
}

I thought of encapsulating a sub-object in SomeObject, but this is just shifting the problem; or constructing the object using a static method:

class SomeObject {
  private:
    const std::string some_string;
    const int some_int;

  public:
    static SomeObject unserialize(const char * input_filename){
      SomeReader reader = new SomeReader(input_filename);

      string str = reader.get_string();
      int i = reader.get_int();

      reader.close();

      SomeObject obj(str, i);
      return obj;
    };

    SomeObject(const std::string str, const int i) :
      some_string(str),
      some_int(i)
    {};
}

Is there a better solution ?

Thank you.

like image 280
factoriel Avatar asked Sep 14 '25 08:09

factoriel


1 Answers

This is a great application for C++11 constructor delegation:

class SomeObject {
  private:
    const std::string some_string;
    const int some_int;

  public:
    // The "real" constructor for SomeObject
    SomeObject(std::string str, const int i) :
      some_string{std::move(str)},
      some_int{i}
    {}

    // Deserialize from SomeReader (delegates to the primary constructor)
    SomeObject(SomeReader& reader) :
      SomeObject{reader.get_string(), reader.get_int()} {}

    // Deserialize from SomeReader (accepts rvalues,
    //   delegates to the lvalue constructor)
    SomeObject(SomeReader&& reader) :
      SomeObject{reader} {}

    // Deserialize from named file (delegates to the SomeReader&& constructor)
    SomeObject(const char* input_filename) :
      SomeObject{SomeReader{input_filename}} {}
};
like image 125
Casey Avatar answered Sep 15 '25 23:09

Casey