位运算和权限管理系统
简介
在 Linux 文件系统中用户对文件有 读、写、执行三种权限,可以分别使用数字:4、2、1 三个数字来表示。三个数字任意组合可以表示不同的权限,例如: 7 (4 + 2 + 1)表示用户对对此文件拥有所有权限,6 (4 + 2)表示用户对此文件有读、写权限。
为什么是1、2、4 ?
对于 读、写、执行 我们用0表示由此权限,1表示无此权限。
1 | 读 写 执行 二进制 十进制 |
为什么是1、2、4?1、2、4 的二进制表现形式是001、010、100,它们的二进制表现形式只有一位是1。这样,在权限叠加时,不会出现进位的情况。我们就可以判断最终结果的二进制位的0、1情况来判断是否有此权限。
例如读 + 写 权限 101。第一位读权限为1,有读权限。第二位写权限为0,无写权限。第三位执行权限为1表示有执行权限。
位运算实现权限操作
或运算实现权限的添加
增加权限使用或(|)运算实现。
如,为用户增加“读取”、“写入”两种权限
1 | 读 写 执行 二进制 十进制 |
“读写”两种权限,权限码为6(110),其由权限码2(010)和4(100)进行或(|)运算后实现,即:6 = 2 | 4,也可以由6 = 2 + 4计算得出。
1 | addPermission (权限集值, 权限项) { |
与运算实现权限的判断
在需要进行用户权限判断时,可以使用与(&)运算判断用户是否据有某项权限。
如,判断权限码为6用户是否有读取权限:
1 | 读 写 执行 二进制 十进制 |
权限码6(110)和4(100)的与运算结果为 4,即:4 = 6 & 4。
判断权限码为6用户是否有执行权限:
1 | 读 写 执行 二进制 十进制 |
权限码6(110)和1(001)的与运算结果为0,即:0 = 6 & 1。
根据与运算的计算规律,当运算结果为所要判断权限本身值时,我们可以认为用户具有这个权限。而当运算结果为 0 时,我们可以认为用户不具有这个权限。
1 | checkPermission (权限集值, 权限项) { |
非运算实现权限的减少
位运算同样可以实现用户权限的减少,减少用户权限使用非(^)运算。
如,将权限码为7用户,移除执行权限:
1 | 读 写 执行 二进制 十进制 |
权限码7(111)和1(001)的非运算结果为6,即:6 = 7 ^ 1,也可以由6 = 7 - 1计算得出。
1 | deletePermission (权限集值, 权限项) { |
延伸
如果权限集超过三种呢?
例子:用位权限表示增、删、改、查。
1 | 增 删 改 查 二进制 十进制 |
如果类型有N种,我们就用N位二进制来表示。
位运算也有一些局限性,随着权限码增加,数据长度也相应的增长。这就要求权限码不能超过计算本身运算长度,在数据库中存储权限码时,权限码长度也不能的超过所使用数据类型。如:在32位系统中不能超过232,也就是权限数量不能多于32个。而mySQL数据库的BIGINT,其存储空间为8Byte,使用BIGINT存储存储码时,权限数不能多于64个(8*8-1)。