利用位运算符实现一个字段表示多个bool类型属性
来源:互联网 发布:免费下载音乐软件 编辑:程序博客网 时间:2024/05/29 09:00
上周看到的,记录一下
假设一个类中有多个字段是bool类型,例如微博用户User的特权:
1.微博红名
2.微博达人
3.Vip会员
4.超级Vip会员
5.金V
6.蓝V
…
User的定义方式1:
type User struct { name string isHongMing bool isDaRen bool isVip bool isSuperVip bool ...}
对每个属性设置相应的get和set方法。
这种方式在数据库存储时需要的字段会比较多,且随着业务的变化需要修改数据库表。
若使用位运算符,可实现一个字段表示多个bool类型的属性,数据库表中只需要存储一个字段,且不需要根据业务的变化而修改表的列,int64可表示64种属性,满足大多数需求。
方式2:
type User struct { name string pre uint8}
上面定义了一个uint8类型的pre,默认值为0,二进制为0000 0000,八位可以表示八种bool类型的属性,我们用1来表示true,0表示false,事先规定好每一位所表示的属性,例如
/* 0000 0000 0000 0001 IsHongMing 表示具有红名特权,十进制为1 0000 0010 IsDaRen 表示具有达人特权,十进制为2 0000 0100 IsVip 表示具有Vip特权,十进制为4 0000 1000 IsSuperVip 表示具有SVip特权 ... */
初始化一个用户:
var user User user.name = "Sheldon" user.pre = 0
位预算表:
初始化后Sheldon的特权为0000 0000
我们想给Sheldon一个红名的特权,需要将Sheldon的pre的第一位赋为1,这里我们使用按位或运算,让0与1做按位或,结果为 0000 0001
此时Sheldon的pre为1
我们又想给Sheldon达人的权限,让他的权限由0000 0001变成0000 0011,若保持第一位不变,第二位变为1,需要将1左移1位 1<<1,让0000 0001与 0000 0010做或运算
此时Sheldon的pre为3
以此类推,若想将pre的第n位设置为1,则需要让pre和1<<(n-1)做或运算 pre | 1 << (n-1)
当我们想取消用户的某一项特权将其置为false时,使用按位异或运算,将对应的位设置为0
例如取消Sheldon的达人权限,只需要让3与1<<1做按位异或
PS:若当前某一位为0时再将其设置为0,结果将变成1,所以在将某一属性设置为false前需要先判断其当前值是0还是1,是1的话再做异或运算
下面说说怎么对某一属性做判断。
当Sheldon的pre为3,我们想判断他是否具有达人的特权,这时将3和1<<1作按位与运算,并与其位置作==判断
代码为:
result := user.pre & posi return result == posi
结果返回true
代码如下:
WeiboUser.go
package maintype User struct { name string pre uint8}func SetPre(user User, isSet bool, posi uint8) User{ /* parameters: user : user isSet : set the prerogative to true or false posi : the position of prerogative return: user */ if isSet == true{ user.pre = user.pre | posi }else { user.pre = user.pre ^ posi } return user}func GetPre(user User, posi uint8) bool{ /* parameters: user : user posi : the position of prerogative return: true or false */ result := user.pre & posi return result == posi}
main.go
package mainimport "fmt"func main() { var user User user.name = "Sheldon" user.pre = 0 fmt.Printf("user is DaRen:%v\n", GetPre(user,1<<1)) user = SetPre(user, true, 1<<1) user = SetPre(user, true, 1<<0) fmt.Println(user.pre) fmt.Printf("user is DaRen:%v\n", GetPre(user,1<<1))}
执行结果:
$ ./data_type.exeuser is DaRen:false3user is DaRen:true
- 利用位运算符实现一个字段表示多个bool类型属性
- bool类型/三木运算符/
- 利用位运算实现加法运算
- 位运算总结2:利用位运算实现加法
- C基础:布尔类型(BOOL) 关系运算符 switch
- 属性是对一个或者多个字段的封装.
- Hibernate中将一个字段映射到POJO多个属性
- Hibernate中将一个字段映射到POJO多个属性
- 利用formdata实现一个input 上传类型 上传多个图片
- 利用位运算实现四则运算-华为面试
- 利用位运算实现加密解密
- 利用位运算实现两个整数相加
- 利用位运算实现两个整数的加法运算
- VC++ 利用位运算实现两个整数的加法运算
- 利用位运算实现两个整数的加法运算
- 数据库用一个int类型的字段保存前端多个字段(该字段为多选)
- 《IOS_C语言》BOOL布尔类型、关系运算符、逻辑运算符、if语句、枚举类型、switch语句
- 位运算-Number of 1 Bits(求一个十进制数字,它的二进制表示中有多少个 1(bit))
- 好用的判断文件扩展名php
- java.awt.headlesss使用
- JAVA基础篇Java compareTo() 方法
- byte与上0xff --------------------之 & 0xff;
- sql语句执行顺序
- 利用位运算符实现一个字段表示多个bool类型属性
- CCF_ 连续叫号 20171202—erease(Vector和 Map)
- Tarjan算法模板
- 【.Net码农】【淘宝API】淘宝API开发系列---淘宝API的测试及使用2
- kindediter字体设置为微软雅黑问题
- 基于Jenkins开展集群式APP自动化测试
- SCOI2011 Day2 棘手的操作 可并堆
- Spring实战笔记(Ch01-Spring之旅)
- 【勤哲应用】用勤哲Excel服务器做工资管理系统