Как обрабатывать неправильные значения в конструкторе? - PullRequest
23 голосов
/ 21 июля 2009

Обратите внимание, что здесь задается вопрос о конструкторах, а не о классах, которые обрабатывают время.

Предположим, у меня есть такой класс:

class Time
{
protected:
    unsigned int m_hour;
    unsigned int m_minute;
    unsigned int m_second;
public:
    Time(unsigned int hour, unsigned int minute, unsigned int second);
};

Хотя я хотел бы, чтобы a был успешно создан, я бы хотел, чтобы конструктор b потерпел неудачу.

Time a = Time(12,34,56);
Time b = Time(12,34,65); // second is larger than 60

Однако это невозможно, поскольку конструкторы не возвращают никаких значений и всегда будут успешными.

Как конструктор скажет программе, что она не счастлива? Я подумал о нескольких методах:

  1. имеет конструктор, генерирующий исключение, и имеет обработчики в вызывающей функции для его обработки.
  2. имеет флаг в классе и устанавливает его в true, только если значения являются приемлемыми для конструктора, и программа проверяет флаг сразу после построения.
  3. имеет отдельную (возможно, статическую) функцию для вызова, чтобы проверить входные параметры непосредственно перед вызовом конструктора.
  4. изменить класс так, чтобы он мог быть создан из любых входных параметров.

Какой из этих методов наиболее распространен в промышленности? Или я что-то пропустил?

Ответы [ 11 ]

0 голосов
/ 20 июля 2016

Рассмотрим фабричный шаблон для генерации объектов времени:

static bool Time::CreateTime(int hour, int min, int second, Time *time) {
  if (hour <= 12 && hour >= 0 && min < 60 && min >= 0 && 
      second < 60 && second >= 0)  {
     Time t(hour, min, second);
     *time = t;
     return true;
  }
  printf("Your sense of time seems to be off");
  return false;
}

Time t;
if (Time::CreateTime(6, 30, 34, &t)) {
  t.time(); // :)
} else {
  printf("Oh noes!");
  return;
}

Это предполагает, что Время имеет:

  • конструктор по умолчанию
  • конструктор копирования
  • оператор присваивания копии
...