Мы никогда больше не сохраняем перечисления как числовые порядковые значения; это делает отладку и поддержку слишком сложной. Мы сохраняем фактическое значение перечисления, преобразованное в строку:
public enum Suit { Spade, Heart, Diamond, Club }
Suit theSuit = Suit.Heart;
szQuery = "INSERT INTO Customers (Name, Suit) " +
"VALUES ('Ian Boyd', %s)".format(theSuit.name());
и затем прочитайте обратно:
Suit theSuit = Suit.valueOf(reader["Suit"]);
В прошлом проблема была в том, что я смотрел на Enterprise Manager и пытался расшифровать:
Name Suit
================== ==========
Shelby Jackson 2
Ian Boyd 1
стихи
Name Suit
================== ==========
Shelby Jackson Diamond
Ian Boyd Heart
последнее намного проще. Для первого требовалось получить исходный код и найти числовые значения, которые были назначены элементам перечисления.
Да, это занимает больше места, но имена членов перечисления короткие, а жесткие диски дешевы, и гораздо полезнее помочь в случае возникновения проблем.
Кроме того, если вы используете числовые значения, вы привязаны к ним. Вы не можете красиво вставить или переставить элементы, не форсируя старые числовые значения. Например, изменив перечисление Suit на:
public enum Suit { Unknown, Heart, Club, Diamond, Spade }
должен был бы стать:
public enum Suit {
Unknown = 4,
Heart = 1,
Club = 3,
Diamond = 2,
Spade = 0 }
для сохранения устаревших числовых значений, хранящихся в базе данных.
Как отсортировать их в базе данных
Возникает вопрос: допустим, я хотел упорядочить значения. Некоторые люди могут захотеть отсортировать их по порядковому значению перечисления. Конечно, упорядочивать карточки по числовому значению перечисления бессмысленно:
SELECT Suit FROM Cards
ORDER BY SuitID; --where SuitID is integer value(4,1,3,2,0)
Suit
------
Spade
Heart
Diamond
Club
Unknown
Это не тот порядок, который мы хотим - мы хотим, чтобы они были в порядке перечисления:
SELECT Suit FROM Cards
ORDER BY CASE SuitID OF
WHEN 4 THEN 0 --Unknown first
WHEN 1 THEN 1 --Heart
WHEN 3 THEN 2 --Club
WHEN 2 THEN 3 --Diamond
WHEN 0 THEN 4 --Spade
ELSE 999 END
Если вы сохраняете целочисленные значения, требуется та же работа, что и при сохранении строк:
SELECT Suit FROM Cards
ORDER BY Suit; --where Suit is an enum name
Suit
-------
Club
Diamond
Heart
Spade
Unknown
Но это не тот порядок, который мы хотим - мы хотим, чтобы они были в порядке перечисления:
SELECT Suit FROM Cards
ORDER BY CASE Suit OF
WHEN 'Unknown' THEN 0
WHEN 'Heart' THEN 1
WHEN 'Club' THEN 2
WHEN 'Diamond' THEN 3
WHEN 'Space' THEN 4
ELSE 999 END
Мое мнение, что этот вид рейтинга принадлежит пользовательскому интерфейсу. Если вы сортируете элементы по значению перечисления: вы делаете что-то не так.
Но если бы вы действительно хотели это сделать, я бы создал таблицу размеров Suits
:
| Suit | SuitID | Rank | Color |
|------------|--------------|---------------|--------|
| Unknown | 4 | 0 | NULL |
| Heart | 1 | 1 | Red |
| Club | 3 | 2 | Black |
| Diamond | 2 | 3 | Red |
| Spade | 0 | 4 | Black |
Таким образом, когда вы хотите поменять свои карты на использование Kissing Kings Новый заказ на колоду , вы можете изменить его для отображения, не выбрасывая все свои данные:
| Suit | SuitID | Rank | Color | CardOrder |
|------------|--------------|---------------|--------|-----------|
| Unknown | 4 | 0 | NULL | NULL |
| Spade | 0 | 1 | Black | 1 |
| Diamond | 2 | 2 | Red | 1 |
| Club | 3 | 3 | Black | -1 |
| Heart | 1 | 4 | Red | -1 |
Теперь мы разделяем внутреннюю деталь программирования (имя перечисления, значение перечисления) с настройкой отображения, предназначенной для пользователей:
SELECT Cards.Suit
FROM Cards
INNER JOIN Suits ON Cards.Suit = Suits.Suit
ORDER BY Suits.Rank,
Card.Rank*Suits.CardOrder