MongoDB入门之增删改查(Java)

测试代码,请重构

	//枚举数据库
	private static void listDB()
	{
		MongoClient mongoClient = new MongoClient("localhost", 27017);
	    for (String dbName : mongoClient.listDatabaseNames())
	    {
	    	System.out.println("dbName: " + dbName);
	    }
	}
	
	//枚举collection
	private static void listCollection()
	{
		MongoClient mongoClient = new MongoClient("localhost", 27017);
		MongoDatabase db = mongoClient.getDatabase("test");
	    for (String collectionName : db.listCollectionNames())
	    {
	    	System.out.println("collectionName: " + collectionName);
	    }
	}

	//查询全部数据
	private static void testQueryAll()
	{
		MongoClient mongoClient = new MongoClient("localhost", 27017);
		MongoDatabase db = mongoClient.getDatabase("test");
		MongoCollection collection = db.getCollection("person");
		BasicDBObject query = new BasicDBObject();
		FindIterable iterable = collection.find(query);
		MongoCursor cursor = iterable.iterator();
		while (cursor.hasNext()) 
		{
		   org.bson.Document person = (org.bson.Document)cursor.next();
		   System.out.println(person.get("name"));
		   System.out.println(person.toString());
		}
		cursor.close();
	}

	//按条件查询数据
	private static void testQuery()
	{
		MongoClient mongoClient = new MongoClient("localhost", 27017);
		MongoDatabase db = mongoClient.getDatabase("test");
		MongoCollection collection = db.getCollection("person");
		
		BasicDBObject query = new BasicDBObject("name","Joe");
		FindIterable iterable = collection.find(query);
		MongoCursor cursor = iterable.iterator();
		while (cursor.hasNext()) 
		{
		   org.bson.Document person = (org.bson.Document)cursor.next();
		   System.out.println(person.get("name"));
		   System.out.println(person.toString());
		}
		cursor.close();
	}

	//插入
	private static void testInsert() 
	{
		MongoClient mongoClient = new MongoClient("localhost", 27017);
		MongoDatabase db = mongoClient.getDatabase("test");
		MongoCollection collection = db.getCollection("person");
		
		Document doc = new Document();
		doc.put("name", "tuzi");
		doc.put("age", 27);
		doc.put("sex", "Female");
		collection.insertOne(doc);
	}

	//删除
	private static void testDelete() {
		MongoClient mongoClient = new MongoClient("localhost", 27017);
		MongoDatabase db = mongoClient.getDatabase("test");
		MongoCollection collection = db.getCollection("person");
		BasicDBObject query = new BasicDBObject("name", "tuziki");
		collection.deleteMany(query);
	}

	//更新
	private static void testUpdate() {
		MongoClient mongoClient = new MongoClient("localhost", 27017);
		MongoDatabase db = mongoClient.getDatabase("test");
		MongoCollection collection = db.getCollection("person");
		
		BasicDBObject query = new BasicDBObject("name", "tuzi");
		
		BasicDBObject newDocument = new BasicDBObject();
		newDocument.put("name", "tuziki");
		
		BasicDBObject updateObj = new BasicDBObject();
		updateObj.put("$set", newDocument);
		
		collection.updateMany(query, updateObj);
	}

MongoDB入门之增删改查(命令行)

1、首先要启动mongodb

set MANGO_HOME=C:\Database\MongoDB\Server\3.0
Set PATH=%MANGO_HOME%\bin;%PATH%
mongod --dbpath=D:\Database\MongoDB3\db

2、然后启动mongo命令行

set MANGO_HOME=C:\Program Files\MongoDB\Server\3.0
Set PATH=%MANGO_HOME%\bin;%PATH%
mongo

3、列出并选用db

show dbs
use test
show collections

4、插入数据,新建collection

db.person.insert({"name":"neo","age":"26","sex":"male"})
db.person.insert({"name":"joe","age":"28","sex":"male"})

5、查询

db.person.find()
db.person.find({"name":"joe"})

6、更新

db.person.update({"name":"joe"},{"name":"joe","age":"29","sex":"male"})
db.person.update({"name":"joe"},{$set:{"age":"28"}})

6、删除

db.person.remove({"name":"joe"})
db.person.remove({})

下一次技术进步是什么呢

恩,我说的是技术进步,不是技术革命哦。

个人认为,比较近的一次技术进步有可能为能源的进步,或者说是电池的进步。
电池现在其实是遇到了很大的瓶颈。
随便打开一个智能手机后盖,至少三分之一是电池,而且瞬间会耗光。

另一个进步,就是屏幕的进步,
或者说,可能不再需要特定的屏幕了,
桌面,皮肤,衣服,都可以作为屏幕,甚至这些都不需要。

然后,就是可穿戴设备的进步,
前两个进步完成后,可穿戴设备才会真的牛起来。
现在的可穿戴设备,还没有真正能超越智能手机的。

另外,AI还没有跟上来哦,需要真正天才的指引,这个需要的是技术革命哦。

其他的吗,就要看物理的发展啦。

为什么DICOM不适合差异化压缩

前几天,同事参加了一个技术讨论会,会间有人热烈的讨论了DICOM影像的单序列多幅的差异化压缩。

想法很简单,就是类似于视频压缩的方法,找出关键帧影像,对非关键帧影像就可以做差异化压缩了。

说实话,我认为这种做法没什么实际价值,原因如下:

1、现在存储很便宜,存储量已经不是什么大问题,但存储的读写速度却一直上不来(SSD太贵),这才是现在要解决的首要问题,所以现在有些人在尝试用HDFS这样的分布式存储系统,来解决这个问题,同时可以解决可靠性

2、DICOM本身没有关键帧的概念,每一幅扫描的人体部位都不同,差距都不小,差异化压缩效果不一定好

3、DICOM文件原本可以独立打开,差异化压缩后,一个关键帧出了问题,其余非关键帧就都报废了,可靠性其实是降低了

4、DICOM影像的每一幅都有MetaData,差异压缩后MetaData如何存储,也是个问题

5、同时,这些计算太消耗CPU了,而且其他厂商并不支持这种压缩方法

PS:
其实有一种解决方案是这样的,将多个DICOM文件合并为一个更大的文件,并记录每个文件的位置索引,支持顺序和随机读写
这样可以大幅提升存取效率,规避LOSF问题,本身就可以降低存储的使用,并且更适配HDFS
已经申请专利了

移动医疗不应该按打车模式推进

现在一些移动医疗的厂商,在做产品的时候,完全采用了打车模式进行推进。

甚至开始照抄出租、专车模式,出来了现有医院、新建医院模式。

但他们忽略了一个问题。

那就是医疗,并不像打车,有如此多的线下资源可以调用。

有几个明显的现象要注意:
1、中国的医疗资源十分匮乏
2、中国的医疗资源过于集中
3、越好的医生越忙,越难以到线上
4、好的医院,不缺患者;
5、看病和打车不一样,不是是个医院你就敢去,是个人你就让他给你治疗
不信?那我问下,如果是你关心的人生病了,你会随便找家医院看看,还是各种打听哪里靠谱?

那问题就来了,即使能有医生到线上,人数有限不说,水平也不会很高。
新建医院,需要有医院的实体,这样成本就高了,而且医生整体数量,不会呈爆炸性增加。
所以,不会像打车软件这样,一呼百应,这个并非不能为的事情,而是一个要持之以恒的工作。

那有哪些是讨巧,现在又能推进的呢:
1、把学医的学生拉到线上,他们不一定有行医资格,但有医疗知识,可以做咨询、网上导诊,这是个不错的开始,比如丁香园就在做
2、用好退休医生队伍,他们经验丰富,有一定闲散时间,但对互联网及移动设备使用不熟练,需要更易用的软件及设备
3、推动国内的社区医院,我们现在的社区医院形同虚设,社区医院的价值根本没有体现出来,其实小问题就应该在社区医院搞定。这个出现的原因,上面已经说到了。解决的方式应该是与政府合作,才会长久。
4、私人诊所,比如牙医、私人医生,这样的服务,这个有美国模式可以借鉴。但要等待政策。
5、远程预诊,缺少专业易用廉价的设备
6、大集团化医院,这个建议几个巨头联合起来,在一二线城市,进行推动。打响品牌战。
7、快速做好远程会诊、诊断、手术等

其实,大家烧钱的地方太集中,另外有几个市场被低估了:
1、运动健身。没有特别专业厂商在做,其实已经可以开展起来了。
2、健康咨询。营养咨询、健身指导、心理咨询、幼儿护理、产前培训。
3、幼老年护理。你懂的。
4、真正的可穿戴设备,现在都是Baby Product,呵呵。
5、需要一个很强势的协会,制定标准,造福人类。

哪些医疗数据可以用HDFS

其实,几年前就有人和我建议,希望在医院用Hadoop,用云计算,来处理医院的日常业务。
但他们苦于找不到接入点。

在建设平台的过程中,更有口号说,不管数据格式如何,先收集上来再说。
但这样做的结果,往往是,数据收上来了,但获取数据的时候,却无法提供。

更有很多供应商,买了第三方的ESB、MQ等商业软件,直接卖给医院,告诉医院,这就是平台。
结果,医院根本就不会用这些产品,整个一悲剧。

但到今天,放眼望去,在医院中,建立私有云的,还是少之又少,主要原因如下:
1、缺少专业人才。医院的运维人员有限,主要以Windows系统的维护为主,日常工作十分的繁杂。没有精力及经验来维护以Linux为基础的云。
2、医疗行业相对保守,出了问题责任重大。很多医院不是不愿意,而是不敢使用新技术,不敢做第一个吃螃蟹的人。
3、现在没有好的厂商,提供优质的私有云建设服务。而医院用Windows、SQL Servr、Oracle远远多于Linux+MySQL+开源非关系数据库的原因,就是商业产品出了问题,还有人帮忙解决,而开源产品出了问题,可是举目无亲。
4、医疗资源的保密性,让医院不敢将资料放到公有云上
5、多数医疗资源,变更频繁,不适合与云存储(云存储适合量大、变更少、变更时尽量不要更新而要追加)
6、很多医院的各个科室,互联互通都没有做好,还在补课阶段

其实,从文件特性上看,还是有不少内容可以放到云上的:
1、影像数据。其实医院的影像文件,采集后,一般经过无损压缩,会N年不再修改。所以放射、核医学、超声、内镜、病理的影像数据,完全可以放到HDFS上。取回速度,会快很多。
2、归档后的病历数据。归档后的病历资料,也是很少变化的,数量也比较巨大,种类也很多,很适合HDFS存储。
3、医院的OA及资产等历史资料,也可以进行HDFS存储

待续。。。

MBP调整硬盘分区(后记)

总结了一下,应该的流程为:

1、在MBP下,用Win7自带功能缩小分区
2、MBP的硬盘取下,调整为移动硬盘,接到虚拟机上,直接Ghost备份
3、MBP硬盘安回去,到MAC下调整分区
4、MBP的硬盘取下,调整为移动硬盘,接到虚拟机上,直接Ghost还原
5、用PE修复Win7的启动项
6、MBP硬盘安回去,就可以进入Win7了
7、进入MAC,备份原装硬盘的数据
8、删除分区
9、进入Win7,扩展分区
10、进入MAC,调整GPT分区表

这样就搞定了,而且不用处理光驱问题。

MBP调整硬盘分区

我的MBP,是2011 Early,如果你体验过它的妖娆,你就懂得,为什么我不想重装。
(安装Win7必须是原装光驱在光驱位)

以前是300G的一块硬盘,后来加了500G的SSD(SSD在硬盘位,原装硬盘在光驱位),在SSD上安装了MAC和Win7。

但最近,MAC盘彻底满了,而Win7的系统盘还有不少空间,于是准备调整一下Win7系统盘的大小。

首先Win7安装了Ghost15,做了个备份,是v2i格式的。

然后重启到MAC系统,删掉Win7分区,用Bootcamp向导平分了整个SSD。

关机,将SSD拿下来,放到移动硬盘盒里,连到另一台笔记本上,准备Ghost回来。

靠,Ghost了两次,都失败了。。。

心里哇凉哇凉的啊。

放回MAC里发现,文件的确可以看得见,但明显不对啊,250G空间,用了200G,还有 150G。

靠,坑爹啊,Windows干脆不认。。。

估计是直接按原来的硬盘分区恢复的,现在硬盘分区变小了,当然放不下,但Ghost大哥,你好歹提示一下啊,欲哭无泪
(如果先把Win7分区缩小,再备份,再还原,应该就可以了)

现在没招了,直接文件恢复吧

直接将v2i备份中的全部文件,还原到新的分区,测试了一下,认不到Win7。

实在不想把光驱恢复,于是想了下,用VMWare,建了个虚拟机,连上移动硬盘,光盘启动。

进入Win7修复界面,

bootrec /FixMbr
...OK

bootrec /FixBoot
...找不到元素

这算啥啊,网上找了下,用diskpart命令将Win7分区设为Active。

bootrec /FixBoot
...ok

bootrec /RebuildBcd
...找不到设备

bcdedit /export C:\bcdbackup
...找不到设备

我靠,你都能看到C盘,你告诉我找不到设备

直接修复启动,还是不行。

疯了。

最后一搏,不用虚拟机,直接将原装光驱换上,光盘启动,修复。
直接提示启动项有问题
修复后重启,好了。

进入系统后,office2010报告无法安装字体文件,直接修复安装,OK。

原装硬盘以前划分了部分空间给MAC,先在MAC系统下数据备份出来,删除分区。
到Windows下,直接扩展了分区。
到MAC下,用gdisk,调整了GPT的分区表。
终于搞定了!

结果,周末没陪老婆,被骂了。。。
哄老婆去了。。。

PS:
1、用老毛桃的PE,换了多个版本,U盘版本无法启动,硬盘版本启动后,找不到设备
2、用一键Ghost,也很挫,硬盘版启动后认不到U盘,U盘版本无法启动
3、其实,虚拟机里,提示过Win7启动项有问题,但我忽略了,否则有可能不需要换光驱
4、下一次可以试一下,直接用虚拟机备份还原,应该前面两个工具就都能用了

此外:
1、Win7驱动有问题,连接移动硬盘后,经常被认成键盘鼠标,移除后就只能强制关机了
2、不知道什么原因,使用iPhone耳机连接后,只有一个声道的声音,而用小米的耳机就有两个声道,不知道哪里的原因,好烦

IPv6地址规则

一、IPv6顾名思义,其地址长128bit(2的64次方)。
为了便于记忆,通常采用16进制表示,每4个16进制为一段,共8段(8*4*4=128):
XXXX:XXXX:XXXX:XXXX:XXXX:XXXX:XXXX:XXXX
其中,XXXX范围为0000-FFFF

二、IPv6地址表示,主要有下面几种:
1、首选法,即每一位都写全,比如:
0234:0000:0000:0000:1234:0000:0000:2234
0000:0000:0000:0000:0234:0000:0000:2234
但这样不便于书写,于是人们想办法来进行缩写

2、将相连的0000,表示为::,但只允许出现一次,上面的地址可以缩写为
0234::1234:0000:0000:2234
::0234:0000:0000:2234

3、将每一段的前导0去掉,这样上面的地址变为
234::1234:0:0:2234
::234:0:0:2234
这样就便于人们记忆了

4、另外,IPv6可以兼容IPv4:
IPV4兼容的IPV6地址,用于在IPV4网络上建立自动隧道,以传输IPV6数据包:
0000:0000:0000:0000:0000:0000:YYY.YYY.YYY.YYY
其中,YYY范围为000-255
映射IPV4的IPV6地址,仅用于拥有IPV4和IPV6双协议栈节点的本地范围:
0000:0000:0000:0000:0000:FFFF:YYY.YYY.YYY.YYY
其中,YYY范围为000-255

三、IPv6的地址分为单播(Unicast)、多播(Multicast)和任意播(Anycast)。
其中单播分为本地链路,本站点地址,ULA,可聚合全球单播地址,回环。
1、本地链路地址(Link-Local Addresses):同一链路相邻节点之间通讯,不能被路由
地址前10个bit是1111 1110 10,规则为FE80::/64,即FE80::/10+54bit0+EUI-64
FE80:0000:0000:0000:EUI-64

2、本地站点地址(Site-Local Addresses):只能在一个站点内使用,私有地址
地址前10个bit是1111 1110 11,规则为FEC0::/48,即FEC0::/10+38bit0+16bit子网表示+EUI-64
FEC0:XXXX:XXXX:XXXX:EUI-64

3、唯一的本地IPv6单播地址(ULA,Unique Local IPv6 Unicast Address):用于替代Site-Local Addresses
地址规则为FD00::/8,后面跟一个被称为全局ID的40bit随机标识符。

4、可聚合全球单播地址(Aggregatable Global Unicast Addresses):公网地址,全球路由
前三bit为001,第一个地址为:
2000:0000:0000:0000:0000:0000:0000:0000
最后一个地址为:
3FFF:FFFF:FFFF:FFFF:FFFF:FFFF:FFFF:FFFF

5、回环地址:
0000:0000:0000:0000:0000:0000:0000:0001
0:0:0:0:0:0:0:1
::1

6、未指定地址(Unspecified address)
0000:0000:0000:0000:0000:0000:0000:0000
0:0:0:0:0:0:0:0
::

四、多播地址:一对多
前8个bit为1111 1111,地址规则为FE00::/8
FF01::到FF0F::的多播地址是保留专用地址
FF01::1 节点本地范围所有节点多播地址
FF02::1 链路本地范围所有节点多播地址
FF01::2 节点本地范围所有路由器多播地址
FF02::2 链路本地范围所有路由器多播地址
FF05::2 站点本地范围所有路由器多播地址

五、任意播:任意播是多个设备共享一个地址,应用在一到附近模式(one-to-nearest)
发送方发送一个以任意播为目标地址的包,当路由器接受到这个包以后,就转发给具有这个地址的离它最近的设备。
任意播地址是从单播地址中划分出来的,对于那些没有配备任意播的的地址就是单播地址;但是当一个单播地址分配给不止一个接口的时候,单播地址就成了任意播地址。
所以单播地址与任意播地址的规则是一样的。

六、EUI-64计算方法:
假设电脑的MAC是00:0C:85:AB:50:01;
首先在MAC地址正中间插入FFFE,得到00:0C:85:FF:FE:AB:50:01
然后由左到右第七bit置反,得到02:0C:85:FF:FE:AB:50:01
将其改写为EUI-64规则,得到020C:85FF:FEAB:5001
需要对第七位取反的原因:
在MAC地址中,第7比特为1表示本地管理,为0表示全球管理
在EUI-64格式中,第7位为1表示全球惟一,为0表示本地惟一

七、隧道协议地址转换
6over4地址
[64bit-prefix]:0:0:WWXX:YYZZ,其中的WWXX:YYZZ是w.x.y.z IPv4公共地址的十进制点号表示法,用于一个使用6to4协议的隧道机制的节点。
6to4地址
2002:WWXX:YYZZ:[SLA ID]:[Interface ID],用于表示一个使用6to4协议的隧道机制节点。

如何快速路由DICOM通讯

DICOM通讯是典型的socket通讯,一般的route方式,都是SCP收到图后,然后CStore给第三方。
但这样的效率不会很高,因为要先收取,解析、再转发。

如何提高转发效率呢?
大家知道DICOM通讯中,对带宽的占用率还是比较高的,而DICOM使用的socket是基于TCP协议的应用层,这样一层层上来,量又大,效果不可能会好。
所以直接用DICOM通讯进行转发,效果不会好。

比较好的方法是,借鉴路由器的工作方式,至少应该在网络层或传输层搞定会比较好。
这样,直接调整一下包的内容,就直接发出去了,效率应该是比较高的。

先记录一下,有空了再试试看。

PS:
利用nginx的转发功能,可以达到快速转发的目的。
先存到对象存储,直接转发文件地址,效率也不错。