MongoDB位運算基本使用以及位運算應用場景

最近在公司業務上用到了二進制匹配數據,但是MongoDB進行二進制運算(Bitwise)沒用過,網上博客文章少,所以就上官網看API,因此記錄一下,順便在普及一下使用二進制位運算的一些應用。

在MongoDB的V3.2版本以后才支持的位運算,在這個版本之前是不支持,所以想要用位運算,需先將MongoDB的版本升級至V3.2。

說明

查詢操作

在官方文檔中,在查詢操作中共支持四種位運算方法,官方文檔鏈接

$bitsAllClear所有指定二進制的位數都為0
$bitsAllSet所有指定二進制的位數都為1
$bitsAnyClear任意一位指定二進制的位數為0
$bitsAnySet任意一位指定二進制的位數為1

這個指定的位數是不是有點難以理解

例如255這個數字的二進制有8位,那么位數則是position指定的位置,Integer的最大值為2的31次方,那么指定的位置(position)最大為31位

bit11111111
position76543210

更新操作

使用$bit進行更新操作,支持and|or|xor?三種位運算符?即對應位運算符的? &(與) 、|(或) 、~(異或)

將指定列的值(field)通過指定的位運算計算出的結果更新至數據庫中,下面有示例

更新語法如下:

{ $bit: { <field>: { <and|or|xor>: <int> } } }

位運算的使用

查詢操作

在MongoDB數據庫中user集合的數據為:

{ "_id" : "03ddb005-6e8e-45b9-be74-9c840f925f1f", "name" : "Tomcar", "bitData" : NumberLong(100), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "dccb1549-bbaf-438b-9c52-dd9549de6fde", "name" : "Java", "bitData" : NumberLong(20), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "1bcf44ba-92ee-4dda-ae1b-4b0b28816fc1", "name" : "python", "bitData" : NumberLong(131), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "50b76890-d533-4455-8a13-fce98bbd96fe", "name" : "php", "bitData" : NumberLong(8), "_class" : "com.mongodb.mongo_test.bean.User" }

二進制對應

1000110 0100
200001 0100
1311000 0011
80000 1000

$bitsAllSet

執行命令:

db.user.find({"bitData":{$bitsAllSet:[1,4]}}) //將二進制的第2位以及第5位上為1的匹配出來

?結果:

{ "_id" : "1bcf44ba-92ee-4dda-ae1b-4b0b28816fc1", "name" : "python", "bitData" : NumberLong(131), "_class" : "com.mongodb.mongo_test.bean.User" }

$bitsAllClear

執行命令:

db.user.find({"bitData":{$bitsAllClear:[1,4]}}); //將二進制的第2位以及第5位上為0的匹配出來

結果:

{ "_id" : "03ddb005-6e8e-45b9-be74-9c840f925f1f", "name" : "Tomcar", "bitData" : NumberLong(100), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "50b76890-d533-4455-8a13-fce98bbd96fe", "name" : "php", "bitData" : NumberLong(8), "_class" : "com.mongodb.mongo_test.bean.User" }

?$bitsAnyClear

執行命令:

db.user.find({"bitData":{$bitsAnyClear:[1,4]}}); //將第2位或者第5位上為0的查詢出來

結果:

{ "_id" : "03ddb005-6e8e-45b9-be74-9c840f925f1f", "name" : "Tomcar", "bitData" : NumberLong(100), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "dccb1549-bbaf-438b-9c52-dd9549de6fde", "name" : "Java", "bitData" : NumberLong(20), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "1bcf44ba-92ee-4dda-ae1b-4b0b28816fc1", "name" : "python", "bitData" : NumberLong(131), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "50b76890-d533-4455-8a13-fce98bbd96fe", "name" : "php", "bitData" : NumberLong(8), "_class" : "com.mongodb.mongo_test.bean.User" }

?$bitsAnySet

執行命令:

db.user.find({"bitData":{$bitsAnySet:[1,4]}}); //將第2位或者第5位上為1的查詢出來

結果:

{ "_id" : "dccb1549-bbaf-438b-9c52-dd9549de6fde", "name" : "Java", "bitData" : NumberLong(20), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "1bcf44ba-92ee-4dda-ae1b-4b0b28816fc1", "name" : "python", "bitData" : NumberLong(131), "_class" : "com.mongodb.mongo_test.bean.User" }

通過數字進行位運算

如果不是用過指定位數進行運算的話,而是指定數字進行的話,查詢結果$bitsAllClear與$bitsAnyClear一致;$bitsAllSet與$bitsAnySet一致。

示例:

命令:
db.user.find({"bitData":{$bitsAnySet:4}})
結果:
{ "_id" : "03ddb005-6e8e-45b9-be74-9c840f925f1f", "name" : "Tomcar", "bitData" : NumberLong(100), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "dccb1549-bbaf-438b-9c52-dd9549de6fde", "name" : "Java", "bitData" : NumberLong(20), "_class" : "com.mongodb.mongo_test.bean.User" }命令:
db.user.find({"bitData":{$bitsAnyClear:4}})
結果:
{ "_id" : "1bcf44ba-92ee-4dda-ae1b-4b0b28816fc1", "name" : "python", "bitData" : NumberLong(131), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "50b76890-d533-4455-8a13-fce98bbd96fe", "name" : "php", "bitData" : NumberLong(8), "_class" : "com.mongodb.mongo_test.bean.User" }

大家可以各自去試一下。

更新操作

在命令中指定更新某個ID的bitData列,當前列數據為8,這里通過使用與(&)運算做示例:

db.user.update({"_id":"50b76890-d533-4455-8a13-fce98bbd96fe"},{$bit:{"bitData":{and:NumberLong(4)}}})

結果集:

{ "_id" : "03ddb005-6e8e-45b9-be74-9c840f925f1f", "name" : "Tomcar", "bitData" : NumberLong(100), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "dccb1549-bbaf-438b-9c52-dd9549de6fde", "name" : "Java", "bitData" : NumberLong(20), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "1bcf44ba-92ee-4dda-ae1b-4b0b28816fc1", "name" : "python", "bitData" : NumberLong(131), "_class" : "com.mongodb.mongo_test.bean.User" }
{ "_id" : "50b76890-d533-4455-8a13-fce98bbd96fe", "name" : "php", "bitData" : NumberLong(0), "_class" : "com.mongodb.mongo_test.bean.User" }

其他的兩個命令也可以各自調試。

在Java代碼中使用位運算

查詢操作

在Spring Boot封裝好的MongoTemplate中帶條件查詢使用Query以及Criteria配合使用,使用位運算的話需使用Criteria的bits()方法:這些方法對應上面的四個方法

而采用Mongo客戶端查詢位運算:

	MongoCollection<Document> collection = mongoTemplate.getCollection("user");Document filter = new Document();//0110 0100 100//0001 0100 20//1000 0011 131//0000 1000 8filter.append("bitData", new Document("$bitsAllClear", Arrays.asList(1,4)) );/*** $bitsAllClear 進行位運算并且計算結果為 0 的匹配出來* $bitsAllSet 進行位運算并且計算結果不為 0 的匹配出來* $bitsAnyClear 進行位運算并且計算結果為 0 的匹配出來* $bitsAnySet 進行位運算并且計算結果不為 0 的匹配出來*/FindIterable<Document> iterable = collection.find(filter);MongoCursor<Document> iterator = iterable.iterator();System.out.println("采用Bson形式查詢");while(iterator.hasNext()) {Document next = iterator.next();Object object = next.get("bitData");if(object instanceof Long)System.out.println(Long.toBinaryString((Long) object));System.out.println(next);}

?更新操作

在SpringBoot的MongoTemplate的更新操作為:

	Update update = new Update();update.bitwise("bitData").and(2);mongoTemplate.updateFirst(Query.query(Criteria.where("_id").is("50b76890-d533-4455-8a13-fce98bbd96fe")), update, User.class);

?采用mongo的客戶端為:

MongoCollection<Document> collection = mongoTemplate.getCollection("user");
collection.updateOne(new Document().append("_id", "50b76890-d533-4455-8a13-fce98bbd96fe"),Updates.bitwiseAnd("bitData", Long.valueOf(4)));

位運算的應用

位運算即使用二進制進行計算,所以這個的計算效率是最快的,先看一下常用使用的位運算

public static void main(Stringa rgs []){//位與  &(1&1=1 1&0=0 0&0=0)
System.out.println("the 4 is "+Integer.toBinaryString(4));
System.out.println("the 6 is "+Integer.toBinaryString(6));
System.out.println("the 4&6 is "+Integer.toBinaryString(4&6));
//位或 | (1|1=1 1|0=1 0|0=0)
System.out.println("the 4|6 is "+Integer.toBinaryString(4|6));
//位非~(~1=0  ~0=1)
System.out.println("the ~4 is "+Integer.toBinaryString(~4));
//位異或 ^ (1^1=0 1^0=1 0^0=0)
System.out.println("the 4^6 is "+Integer.toBinaryString(4^6));
// <<有符號左移 >>有符號的右移  >>>無符號右移
//取模的操作 a % (2^n) 等價于 a&(2^n-1)
System.out.println("the 345 % 16 is "+(345%16)+ " or "+(345&(16-1)));
}

運算結果為:

the 4 is 100
the 4 is 100
the 6 is 110
the 4&6 is 100
the 4|6 is 110
the ~4 is 11111111111111111111111111111011
the 4^6 is 10
the 345 % 16 is 9 or 9

雖然看起來平常開發用不到,但是可以使用到權限這一塊由于Integer最大值可以到2的31次方,所以單個數字就可以存儲31中權限,不僅僅可以在業務上使用;

在JDK的反射包中有個類Modifier.class,這個類是采集每個Class的中修飾符以及類型。不僅僅是反射在JUC的包中也使用到了這個位運算,因為運算速度快,所以在很多基礎框架中用的還是很多的。

?

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/537136.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/537136.shtml
英文地址,請注明出處:http://en.pswp.cn/news/537136.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

好用的下拉第三方——nicespinner

1.簡介 GitHub地址&#xff1a;https://github.com/arcadefire/nice-spinner Gradle中添加&#xff1a; allprojects {repositories {...maven { url "https://jitpack.io" }} }dependencies {implementation com.github.arcadefire:nice-spinner:1.3.7 }2.使用 xml文…

Mybatis配置文件參數定義

官網有時候進不去&#xff0c;所以就記錄一下Mybatis的配置文件的各項參數定義&#xff0c;大家也可以上官網查詢&#xff0c;官方文檔&#xff0c;進不進的去看各自的緣分了 properties 定義配置&#xff0c;在這里配置的屬性可以在整個配置文件使用&#xff1b;可以加載指定…

python和java后期發展_Python與java的發展前景誰最大

Python和Java是目前IT行業內兩大編程語言&#xff0c;很多人都喜歡拿來比較&#xff0c;一個是后起之秀&#xff0c;潛力無限&#xff1b;一個是行業經典&#xff0c;成熟穩定。對于許多想從事IT行業的同學來說&#xff0c;這兩門語言真的很難抉擇。那么&#xff0c;Python和Ja…

JDK源碼學習筆記——Enum枚舉使用及原理

一、為什么使用枚舉 什么時候應該使用枚舉呢&#xff1f;每當需要一組固定的常量的時候&#xff0c;如一周的天數、一年四季等。或者是在我們編譯前就知道其包含的所有值的集合。 利用 public final static 完全可以實現的功能&#xff0c;為什么要使用枚舉&#xff1f; public…

Mybatis源碼日志模塊分析

看源碼需要先下載源碼&#xff0c;可以去Mybatis的github上的倉庫進行下載&#xff0c;Mybatis 這次就先整理一下日志這一塊的源碼分析&#xff0c;這塊相對來說比較簡單而且這個模塊是Mybatis的基礎模塊。 之前的文章有談到過Java的日志實現&#xff0c;大家也可以參考一下&…

python手機端給電腦端發送數據_期貨交易軟件有哪些比較好用?分手機端和電腦端...

一、電腦端交易軟件期貨電腦端交易軟件目前市場上用的最多的是文華財經和博易大師&#xff0c;這兩個軟件都是免費交易使用的。從投資者使用角度來看&#xff0c;目前電腦端文華財經的評價比博易大師高一些。當然每個投資者有自己的使用習慣&#xff0c;博易大師也有自己優點&a…

Find the Difference(leetcode389)

2019獨角獸企業重金招聘Python工程師標準>>> Given two strings s and t which consist of only lowercase letters. String t is generated by random shuffling string s and then add one more letter at a random position. Find the letter that was added in …

Mybatis源碼之數據源模塊分析

先來看看java純jdbc查詢數據的示例&#xff1a; try {//加載對應的驅動類Class.forName("com.mysql.cj.jdbc.Driver");//創建連接Connection connection DriverManager.getConnection("jdbc:mysql://127.0.0.1:3306/test?serverTimezoneUTC", "roo…

reactnative 獲取定位_[RN] React Native 獲取地理位置

import React, {Component} from react;import {StyleSheet, Text, View}from react-native;exportdefault classTestGeo extends Component {state{longitude:,//經度latitude: ,//緯度city: ,district:,street:,position:,//位置名稱};componentWillMount () >{this.getPo…

第二沖刺階段第三天

查閱資料&#xff0c;修改控件界面轉載于:https://www.cnblogs.com/gyy0/p/10066452.html

Mybatis源碼之緩存模塊分析

緩存這個東西在很多應用中都能看到它們的身影&#xff0c;這次就講講在Mybatis中的緩存是怎么應用的&#xff0c;雖然說吧Mybatis中的緩存基本不怎么用&#xff0c;用的更多是第三方組件redis、MongoDB、MemCache等等。 Mybatis的緩存是基于Map實現的&#xff0c;從緩存中讀寫…

Mybatis源碼之核心流程分析

終于談到了Mybatis最核心的東西了&#xff0c;最核心的就是通過配置XML文件或注解中的SQL&#xff0c;直接調用接口就能執行配置好的SQL語句并封裝成對應的返回類型的數據。 先看一下Mybatis使用示例&#xff1a; //創建Builder對象 SqlSessionFactoryBuilder builder new S…

mimakatz用法_兩步完成利用procdump64+mimikatz獲取win用戶密碼

使用procdump64mimikatz可實現從內存中獲取明文密碼工具鏈接&#xff1a;https://pan.baidu.com/s/1gNc9qLcNSNBohIVrAiqShw 密碼&#xff1a;fc38首先得先獲取到內存文件lsass.exe進程, 它用于本地安全和登陸策略,一般在進程管理器中能看到, 比如這樣1.導出lsass.exeprocdump6…

ios app提交之前需要哪幾個證書

1、遇到的問題 一款App在別人的機器上開發和發布&#xff0c;現在迭代更新和開發需要在一臺新mac機上開發和發布。&#xff08;使用同一個開發者賬號&#xff09;問題&#xff1a; 1.在新mac機器上開發并導入真機測試&#xff0c;是不是需要從別人的機器上面導處開發者證書、開…

Mybatis源碼之與Spring集成包

這次講講Mybatis與Spring的整合&#xff0c;作為兩款優秀的開源框架&#xff0c;被大眾廣泛使用&#xff0c;自然是需要強強聯合的。 使用示例 先看一下怎么使用&#xff0c;首先需要引用這兩款框架的jar包&#xff1a; <dependency>//spring-webmvc會自動去引入其他S…

hadoop主節點切換_hadoop2.0 HA的主備自動切換

在《hadoop2.0 QJM方式的HA的配置》一文中介紹了HA的配置&#xff0c;是通過手工進行主備切換的。本文在這基礎上&#xff0c;繼續介紹HA的主備自動切換(automatic failover)的配置。自動切換是通過配置zookeeper來實現的&#xff0c;關于zookeeper的安裝和配置&#xff0c;在這…

Mybatis源碼之插件模塊分析

總結完這個Mybatis的整體主要功能基本上就差不多完&#xff0c;還有一些細節的部分&#xff0c;后續都會記錄補充。 插件這個東西一般用的比較少&#xff0c;就算用的多的插件也算是PageHelper分頁插件&#xff1b; PageHelper官網&#xff1a;https://github.com/pagehelper…

AMD推出7nm高端顯卡Radeon VII,直指英偉達RTX 2080

顯卡戰爭已經發展到了2019年&#xff0c;并且變得比任何人預想的都要激烈。 CES 2019大會上&#xff0c;AMD發布了第一款消費級的 7nm GPU&#xff0c;取名&#xff1a;Radeon VII。據了解&#xff0c;這不是 AMD 的第一顆 7nm 處理器&#xff08;早期以 AI 運算為主的 Radeon …

電子繪本pdf_【孩子必看的】20本世界著名英文繪本 | PDF電子版+MP3音頻

原標題&#xff1a;【孩子必看的】20本世界著名英文繪本 | PDF電子版MP3音頻2 —6歲年齡段的孩子&#xff0c;自我意識逐漸萌芽&#xff0c;已經明白書是一種“特殊”的玩具&#xff0c;不在撕書、咬書、把書搬來搬去。這個階段他們記憶力超強&#xff0c;唐詩、三字經啥的&…

Spring集成Mybatis多數據源配置

既然在整理Mybatis那就把經常用的這個多數據源的筆記也整一下吧。 Spring集成Mybatis在之前就已經提到了。Spring集成Mybatis 集成Mybatis多數據源有兩種方式&#xff1a; 1、創建多個SqlSessionFactory&#xff0c;掃描每個SqlSessionFactoryBean對應的包&#xff0c;形成了…