我正在用 PHP + MySQL 编写一个小型应用程序,并且已经到了一个对象有几个(目前为 8 个,但预计不会增加)与之关联的标志的地步。这些标志几乎没有关系,尽管有些组合没有意义。该对象代表数据库中的一行(也有一些保存/加载它的方法),所以这个问题也适用于选择存储方法。
问题是 - 如何在代码和数据库中最好地表示它们?我可以想到几种方法:
将它们存储在数据库中的一种方法是在单个整数字段中作为按位标志。在 PHP 方面,我可以想象几种表示它们的方式:
- 只需导出整数值并定义几个标志常量;让每个需要标志的地方发挥自己的按位魔法;
- 定义类方法
GetFlag()
、SetFlag()
和UnsetFlag()
对私有(private)整数变量执行按位魔法;然后将这些方法作为参数传递给标志常量之一。 - 定义方法
GetFlagA()
、GetFlagB()
等(以及 Set 和 Unset 对应方法); - 定义一堆成员变量,每个变量代表一个标志;将它们设置为从数据库加载并在保存时收集它们。
- 创建一个包含所有标志值的数组的成员变量。使用预定义的常量作为数组索引来访问每个标志。还在加载/保存时填充/收集数组。
另一种方法是将它们作为单独的 BIT 字段存储在数据库中。在 PHP 中,这将转换为几个成员变量。恕我直言,这会使查询复杂化。
最后一种方法是为所有标志定义另一个表,并为标志和原始对象之间的多对多关系定义一个中间表。恕我直言,这是所有解决方案中最困惑的,否则只有 3 张 table 。
我没有做过太多的 PHP 开发,所以我不知道最佳实践是什么。在 C# 中,我可能会将它们存储为按位标志,并创建对私有(private)整数执行按位魔术的属性。但是 PHP 没有属性(我使用的是最新的稳定版本)...
最佳答案
在你的model , 该对象有 8 个 bool 属性。这意味着数据库表中有 8 个 bool 值(MySQL 的 TINYINT)列,对象中有 8 个 getter/setter 方法。简单而常规。
重新考虑您当前的方法。想象一下下一个必须维护这个东西的人会说什么。
CREATE TABLE mytable (myfield BIT(8));
好的,看来我们要在这里生成一些二进制数据。
INSERT INTO mytable VALUES (b'00101000');
等等,有人再告诉我这些 1 和 0 分别代表什么。
SELECT * FROM mytable;
+------------+
| mybitfield |
+------------+
| ( |
+------------+
什么?
SELECT * FROM mytable WHERE myfield & b'00101000' = b'00100000';
WTF! WTF!?
用刀捅自己的脸
-- 与此同时,在仙女与 unicorn 玩耍、程序员不讨厌 DBA 的平行宇宙中......--
SELECT * FROM mytable WHERE field3 = 1 AND field5 = 0;
幸福与阳光!
关于php - PHP 中位标志的最佳实践,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/429104/