PHP中位标记的最佳做法 [英] Best practices for bit flags in PHP

查看:76
本文介绍了PHP中位标记的最佳做法的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在用PHP + MySQL编写一个小型应用程序,并且发现有一个对象带有与之相关联的几个标志(到目前为止有8个,但预计不会增加).这些标志几乎没有关联,尽管有些组合没有意义.该对象表示数据库中的一行(也有一些保存/加载方法),因此该问题也适用于选择存储方法.

I'm writng a small application in PHP + MySQL and have come to the point where there is an object that has a couple (8 so far but not expected to increase) of flags associated with it. The flags are pretty much unrelated although there are some combinations that would make no sense. The object represents a row in a DB (has some methods for saving/loading it too) so the question also applies to choosing a storage method.

问题是-如何在代码和数据库中最好地表示它们?我可以想到几种方法:

The question is - how to best represent them both in code and DB? I can think of several ways:

将它们存储在数据库中的一种方法是在单个整数字段中作为按位标志.在PHP方面,我可以想象几种表示它们的方法:

One way to store them in the DB is in a single integer field as bitwise flags. On the PHP side then I can imagine several ways of representing them:

  • 仅导出整数值并定义几个标志常量;让每个需要标志的地方都做自己的按位魔术;
  • 定义类方法GetFlag()SetFlag()UnsetFlag(),它们对私有整数变量进行按位魔术;然后,这些方法将作为参数的标志常量之一传递.
  • 定义方法GetFlagA()GetFlagB()等(以及Set和Unset对应项);
  • 定义一堆成员变量,每个成员变量代表一个标志;在从数据库加载时进行设置,并在保存时收集它们.
  • 创建一个成员变量,该成员变量是所有标志值的数组.使用预定义的常量作为数组索引来访问每个标志.还要在加载/保存时填充/收集数组.
  • Simply export the integer value and define a couple of flag constants; Let every place that needs the flags do their own bitwise magic;
  • Define class methods GetFlag(), SetFlag() and UnsetFlag() that do the bitwise magic on a private integer variable; These methods would then be passed one of the flag constants as a parameters.
  • Define methods GetFlagA(), GetFlagB() etc. (along with Set and Unset counterparts);
  • Define a bunch of member variables that each represent one flag; Set them on loading from the DB and gather them when saving.
  • Create a member variable that is an array of all the flag values. Use predefined constants as array indices to access each flag. Also fill/gather the array on loading/saving.

另一种方法是将它们作为单独的BIT字段存储在数据库中.在PHP中,它将转换为几个成员变量.恕我直言,这会使查询复杂化.

Another way would be to store them in the DB as separate BIT fields. In PHP that would then translate to several member variables. IMHO this would complicate the queries.

最后一种方法是为所有标志定义定义表,并为标志和原始对象之间的多对多关系定义一个中间表.恕我直言,所有解​​决方案中最混乱的是,考虑到否则只有3张桌子.

And the last way would be to define anothed table for all the flags and an intermediate table for many-to-many relationship between flags and the original objects. IMHO the messiest of all solutions, considering that there would be only like 3 tables otherwise.

我没有做太多的PHP开发,所以我不知道最佳实践是什么.在C#中,我可能会将它们存储为按位标志,并创建对私有整数进行按位魔术的属性.但是PHP没有属性(我使用的是最新的稳定版本)...

I haven't done much PHP development so I don't know what the best practice would be. In C# I would probably store them as bitwise flags and make properties that do the bitwise magic on a private integer. But PHP doesn't have properties (I'm using latest stable version)...

推荐答案

在您的模型,该对象具有8个布尔属性.这意味着数据库表中有8个布尔(MySQL为TINYINT)列,而对象中有8个getter/setter方法.简单而传统.

In your model, the object has 8 boolean properties. That implies 8 boolean (TINYINT for MySQL) columns in your database table and 8 getter/setter methods in your object. Simple and conventional.

重新考虑您当前的方法.想象下一个必须维护这个东西的家伙会说些什么.

Rethink your current approach. Imagine what the next guy who has to maintain this thing will be saying.

CREATE TABLE mytable (myfield BIT(8));

好的,看来我们这里将要发生一些二进制数据.

OK, looks like we're going to have some binary data happening here.

INSERT INTO mytable VALUES (b'00101000');

等等,有人再次告诉我1和0分别代表什么.

Wait, somebody tell me again what each of those 1s and 0s stands for.

SELECT * FROM mytable;
+------------+
| mybitfield |
+------------+
| (          | 
+------------+

什么?

SELECT * FROM mytable WHERE myfield & b'00101000' = b'00100000';

WTF !? WTF!?

WTF!? WTF!?

刺伤自己

-同时,在另一个宇宙中,妖精与独角兽一起玩,程序员不讨厌DBA ...-

-- meanwhile, in an alternate universe where fairies play with unicorns and programmers don't hate DBAs... --

SELECT * FROM mytable WHERE field3 = 1 AND field5 = 0;

幸福和阳光!

这篇关于PHP中位标记的最佳做法的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆