Лучшая практика использовать побитовые комбинации параметров с использованием перечислений? - PullRequest
1 голос
/ 25 апреля 2011

Я реализую представление, которое живет на экране.На основе следующих параметров конфигурации представление будет позиционироваться и изменяться при каждом изменении размера экрана.

enum DLViewLayout
{
    DLViewLayoutSolo = 1,
    DLViewLayoutDual = 2
};
enum DLViewFixedHorizontalProperty
{
    DLViewFixedHorizontalPropertyWidth = 4, // View margins scale with the screen width.
    DLViewFixedHorizontalPropertyMargin = 8 // View width scales with the screen width.
};
enum DLViewFixedVerticalProperty
{
    DLViewFixedVerticalPropertyHeight = 16,
    DLViewFixedVerticalPropertyMargin = 32
};
enum DLViewHorizonalAlignment
{
    DLViewHorizonalAlignmentLeft = 64,
    DLViewHorizonalAlignmentCenter = 128,
    DLViewHorizonalAlignmentRight = 256
};
enum DLViewVerticalAlignment
{
    DLViewVerticalAlignmentTop = 512,
    DLViewVerticalAlignmentMiddle = 1024,
    DLViewVerticalAlignmentBottom = 2048
};

Интересно, в какой ситуации имеет смысл поразрядно OR объединять значения перечисления для передачи представлениясостояние.

int viewState = DLViewLayoutSolo | DLViewFixedHorizontalPropertyWidth | DLViewFixedVerticalPropertyMargin | DLViewHorizonalAlignmentCenter | DLViewVerticalAlignmentMiddle;  
// viewState = 1189

Я хочу, чтобы пользователь класса настраивал все параметры.Как я могу применить это?

Внутри класса я могу получить отдельные настройки, поразрядно AND комбинируя состояние.

if (viewState & DLViewLayoutSolo)
{
  // Set up solo view layout.
}
else if (viewState & DLViewLayoutDual)
{
  // Set up dual view layout.
}

Ответы [ 2 ]

3 голосов
/ 25 апреля 2011

Вы хотите объединить флаги, используя значения из разных перечислений?

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

Поскольку значения растут соответственно, почему бы просто не использовать точно названное перечисление, состоящее из всех членов?

Кроме того, если мы говорим .NET здесь (хотя и допустимо, точки с запятой говорятя, возможно, нет), такие типы enum должны быть украшены атрибутом [Flags], но, тем не менее, объединять только значения одного типа enum.

1 голос
/ 25 апреля 2011

Звучит так, как будто вы хотите, чтобы поля, значения которых принимают состояние каждого подусловия:

enum DLViewLayout
{
    DLViewLayoutSolo,
    DLViewLayoutDual
};
enum DLViewFixedHorizontalProperty
{
    DLViewFixedHorizontalPropertyWidth, // View margins scale with the screen width.
    DLViewFixedHorizontalPropertyMargin // View width scales with the screen width.
};
enum DLViewFixedVerticalProperty
{
    DLViewFixedVerticalPropertyHeight,
    DLViewFixedVerticalPropertyMargin
};
enum DLViewHorizonalAlignment
{
    DLViewHorizonalAlignmentLeft,
    DLViewHorizonalAlignmentCenter,
    DLViewHorizonalAlignmentRight
};
enum DLViewVerticalAlignment
{
    DLViewVerticalAlignmentTop,
    DLViewVerticalAlignmentMiddle,
    DLViewVerticalAlignmentBottom
};

struct DLView {
    DLViewLayout layout;
    DLViewFixedHorizontalProperty fixed_horizontal;
    DLViewFixedVerticalProperty fixed_vertical;
    DLViewHorizonalAlignment horizontal;
    DLViewVerticalAlignment vertical;
};

// ...
DLView viewState;
// ...
if ( viewState.layout == DLViewLayoutSolo ) { ... }
else if ( viewState.layout == DLViewLayoutDual ) { ... }
}

/// repeat per field

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

struct DLView {
    DLViewLayout layout : 1;
    DLViewFixedHorizontalProperty fixed_horizontal : 1;
    DLViewFixedVerticalProperty fixed_vertical : 1;
    DLViewHorizonalAlignment horizontal : 2;
    DLViewVerticalAlignment vertical : 2;
};
...