fix(EO): allow readFrom to work on std::cin + invalidTag

- std::cin does not allow seekg/tellg, so instead one wrap the read string
  in a istringstream, and then read from it.
  This allows to read from any istream, with or without seekg.
- Adds an EO::invalidTag member, in case someone would need to use it
  (for instance as a regexp to sanitize inputs).
This commit is contained in:
Johann Dreo 2024-09-30 20:42:20 +02:00
commit 190a30495e

View file

@ -64,6 +64,8 @@ template<class F = double> class EO: public eoObject, public eoPersistent
public: public:
typedef F Fitness; typedef F Fitness;
static constexpr const char* invalidTag = "INVALID";
/** Default constructor. /** Default constructor.
*/ */
EO(): repFitness(Fitness()), invalidFitness(true) { } EO(): repFitness(Fitness()), invalidFitness(true) { }
@ -124,25 +126,21 @@ public:
* The read and print methods should be compatible and have the same format. * The read and print methods should be compatible and have the same format.
* In principle, format is "plain": they just print a number * In principle, format is "plain": they just print a number
* @param _is a std::istream. * @param _is a std::istream.
* @throw eoInvalidFitnessError If a valid object can't be read.
*/ */
virtual void readFrom(std::istream& _is) { virtual void readFrom(std::istream& _is)
{
// the new version of the reafFrom function.
// It can distinguish between valid and invalid fitness values.
std::string fitness_str; std::string fitness_str;
int pos = _is.tellg();
_is >> fitness_str; _is >> fitness_str;
if (fitness_str == "INVALID") if (fitness_str == invalidTag)
{ {
invalidFitness = true; invalidFitness = true;
} }
else else
{ {
invalidFitness = false; invalidFitness = false;
_is.seekg(pos); // rewind std::istringstream iss(fitness_str);
_is >> repFitness; iss >> repFitness;
} }
} }
@ -150,12 +148,11 @@ public:
* Write object. Called printOn since it prints the object _on_ a stream. * Write object. Called printOn since it prints the object _on_ a stream.
* @param _os A std::ostream. * @param _os A std::ostream.
*/ */
virtual void printOn(std::ostream& _os) const { virtual void printOn(std::ostream& _os) const
{
if (invalid())
// the latest version of the code. Very similar to the old code {
if (invalid()) { _os << invalidTag << ' ';
_os << "INVALID ";
} }
else else
{ {