聚合标签与位运算

前段时间的工作中做过一个东西,用到过一种方法。感觉很新颖,也一直想写,一直又懒得动。今天正好没事,来写一写。
当时做的很简单的一个功能——聚合标签,第一反映 ,要几个标签,就再建几个字段,后来想想太二b了,维护起来又不方便。那咋办呢?看别的产品呗,机器里直接有DZ,看了一眼他的数据表,里面聚合标签就一个字段,int类型,然后就一点点的试,发现是这样

标签1	  对应	        1
标签2			2
标签3			4
标签4			8
标签5			16
…………

如果同时拥有几个标签就取其之和。感觉这种方法很好,便开始研究这是怎么个原理(各位读者是不想问我为啥不直接看DZ的源码,我也想啊亲,无奈DZ的源码可读性太差,找东西也不好找阿,权当脑力游戏了)。

最后查阅资料和到处问,得到如下方法:

现在很明显能看到1、2、4、8、16为2的0、1、2、3、4次方。插入的时候就没问题。

取的时候可以使用位运算来取
SQL语句
SELECT * FROM table WHERE tags & POW(2,N) = POW(2,N)
(其中N代表标签id)

期间测试时候发现一现象,比如执行SELECT 10111 & 1000结果为872,后证明发现是自动将两个数转成二进制进行运算后结果转回十进制。

10011101111111(10111的二进制)
00001111101000(1000的二进制)
00001101101000(872的二进制)

此方法可有效的减少数据库中使用的字段,在其他场景也可应用,特与大家分享。

发表评论

电子邮件地址不会被公开。 必填项已用*标注

您可以使用这些HTML标签和属性: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

You must enable javascript to see captcha here!