当前位置: 首页 > 面试题库 >

在数据库中保存枚举的方法

空正豪
2023-03-14
问题内容

将枚举保存到数据库中的最佳方法是什么?

我知道Java提供name()valueOf()方法来枚举值转换为字符串和背部。但是还有其他(灵活的)选项来存储这些值吗?

有没有一种聪明的方法可以使枚举成为唯一的数字(ordinal()使用不安全)?

更新:

感谢您提供的所有出色且快速的答案!就像我怀疑的那样。

但是要注意“工具包”;那是一种方式。问题是我必须向创建的每个Enum类型添加相同的方法。那就是很多重复的代码,并且目前Java不支持任何解决方案(Java枚举不能扩展其他类)。


问题答案:

我们 再也不会 将枚举存储为数字序数值了。这使得调试和支持方式太困难了。我们存储转换为字符串的实际枚举值:

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"]);

该问题过去一直盯着企业管理器并试图破译:

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  |

这样,当您想更改卡以使用“ 接吻王”卡牌 定单时 ,可以出于显示目的进行更改,而不会丢弃所有数据:

| 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


 类似资料:
  • 我希望使用枚举将值映射到数据库表行: 我想使用status=active从FE中搜索和获取状态,但只存储到数据库行字段中的符号A。 我如何将枚举键A存储到数据库中?

  • 问题内容: 除了简单地为每个枚举创建查找表(以Id,代码和名称作为列)之外,是否有更好或更简便的方法将枚举(在C#等编程语言中可用的枚举)存储在SQL Server数据库中,而不是为每个枚举创建查找表(尤其是在存在枚举时)每个表中只有很少的几行)?我发现有一篇文章建议只为所有枚举创建一个查找表,并且有人批评这种方法违反了引用数据的完整性,因此有人批评该方法。如果枚举仅由一个表使用,那么使用一些预定

  • 问题内容: 大多数项目的某些数据在版本之间基本上是静态的,并且非常适合用作枚举,例如状态,事务类型,错误代码等。例如,我只使用一个通用的状态枚举: 我想知道其他人在处理此类数据方面的持久性。我看到一些选择,每个选择都有明显的优点和缺点: 将可能的状态保留在状态表中,并保留所有可能的状态域对象,以供在整个应用程序中使用 只使用一个枚举,而不保留可用状态列表,这在我和我的DBA之间造成了数据一致性的圣

  • 问题内容: 因此,我对Java枚举中是否可以包含函数感到困惑。我正在制作一个简单的html编辑器,并希望使用枚举来表示html标签,是的,我知道这不是解决问题的最佳方法,而是我小组决定实现它的方法。 所以我一直在尝试做这样的事情,但是当我试图称其为静态方法时,我想我想知道这是否正确,或者是否有更好的方法来实现它而不是公开成为 问题答案: 是的,Java枚举可以具有功能。 http://docs.o

  • 问题内容: 我有一个模型对象,我想要一个带有日期的字段。目前,我正在使用适合我们需求的产品。 Hibernate将该字段以形式存储在数据库中。我们可以将其在数据库中的保存方式更改为更易读的格式,更重要的是将其更改为可排序的格式吗? 使用的数据库是mysql db。 问题答案: 这个问题已经解决了作为一种新的改进来 ,原来这是一个孤立的捆绑模块 现在,它直接捆绑,所以只要确保你使用的是最新的版本,它