В основном я хочу ограничить переменные значениями 0, 1 или 2.

Я пробовал сделать это следующим образом:

enum Value
{
    0,
    1,
    2
};
Value var;

Но это ошибка компиляции, потому что значения перечисления не помечены. Это просто делает код менее читаемым для присвоения имен, таких как «ZERO», «ONE» и «TWO», вместо того, чтобы ссылаться на значения как 0, 1 и 2. Есть ли способ обойти это или мне просто нужно избавиться от перечисления и обеспечить соблюдение правила в другом месте?

0
Anoman 17 Май 2011 в 05:23
8
Это называется int ...?
 – 
sehe
17 Май 2011 в 05:24
2
Если вы можете, я бы предложил объявить ваши переменные как частные члены класса, а затем предоставить общедоступные методы установки, которые обеспечивают соблюдение ограничения.
 – 
aroth
17 Май 2011 в 05:25
Похоже, вам нужен тип утилиты, как я описывал ранее здесь
 – 
GManNickG
17 Май 2011 в 05:26
Имейте в виду, что есть языки, которые поддерживают то, что хочет OP, например type MySmallInt is range 0 .. 2; в ADA. Однако реализовать что-то подобное в C ++ довольно громоздко.
 – 
Lyke
17 Май 2011 в 05:41
1
Даже если вы назвали их ZERO, ONE, TWO, перечисление все равно сможет содержать ONE | TWO, то есть 3.
 – 
MSalters
17 Май 2011 в 11:29

2 ответа

Лучший ответ

Если вы хотите использовать enum, вам нужно назвать их. Поскольку вы просто работаете с целочисленными значениями и, очевидно, хотите, чтобы они действительно представляли целые значения, лучше всего использовать параметр int и выполнить быструю проверку в верхней части метода. Комментарий к методу, определяющему это ограничение, будет приветствоваться.

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

1
dlev 17 Май 2011 в 05:28

Тот факт, что вы добавляете идентификаторы для значений, не означает, что вы должны их использовать ... вы можете использовать Value(0), Value(2) и т. Д., Если это удобнее, но есть опасность: enum не ограничивает сохраняемое значение перечисленными ... например это не защитит вас от Value(3).

Внутри структур / классов вы можете использовать битовые поля для ограничения хранилища, используемого для чисел, но даже в этом случае: - диапазон должен соответствовать либо знаковым, либо беззнаковым значениям, возможным в количестве запрошенных битов - попытки присвоить другие значения приведут к удаляются старшие биты, а не какая-либо ошибка компиляции или времени выполнения

Если вы намерены создать отдельный тип, который применяет ограниченные значения от 0 до 2, вам понадобится класс со специализированным конструктором и операторами присваивания:

template <int MIN, int MAX>
class Bound
{
  public:
    explicit Bound(int n) { *this = n; }

    Bound& operator=(int n)
    {
        if (n < MIN or n > MAX)
            throw std::runtime_error("out of bounds");
        n_ = n;
        return *this;
    }
    Bound& operator+=(int n) { *this = n_ + n; }

    // should "+" return int or Bound?  entirely usage dependent...
    Bound operator+(int n) { return Bound(n_ + n); }

    // -=, -, *=, *, /=, /, %=, %, bitwise ops, pre/post ++/-- etc...

    operator int() const { return n_; }

  private:
    int n_;
};
1
Tony Delroy 17 Май 2011 в 07:07