代码之旅

I love Coding !

散列技术是在记录的存储位置和它的关键字之间建立一个确定的对应关系f,使得每个关键字key对应一个存储位置f(key)。査找时,根据这个确定的对应关系找到给定值key的映射f(key),若査找集合中存在这个记录,则必定在f(key)的位置上。

我们把这种对应关系f称为散列函数,又称为哈希(Hash)函数。按这个思想,采用散列技术将记录存储在一块连续的存储空间中,这块连续存储空间称为散列表或哈希表(Hashtable)。那么关键字对应的记录存储位置我们称为散列地址。

阅读全文 »

LMAX Disruptor是一个高性能的线程间消息库。下面是其简单架构示意图

阅读全文 »

之前把ubuntu装到了ssd上,速度变得快了很多。顺手就安装了steam,昨天突然发现磁盘接近满了🤣。立马插上了一块新买的ssd。

阅读全文 »

Ubuntu + window双系统,删除window后,在grub和bios的EFI启动项中残留WindowBootManager。

单纯修改/boot/grub下的菜单配置,在执行sudo upgrade-grub2后启动项又会恢复WindowBootManager.

阅读全文 »

1000瓶药水,1瓶有毒药,服用后一小时毒发,毒药可以无限稀释,那么一小时内用几只小白鼠能够找出毒药?

一只老鼠的状态是2种生或死,这里可以看做bit位,而1000瓶药水有1000种情况,显然我们可以使用2^10 = 1024>1000 来描述这1000种可能,而2进制数的唯一性可以唯一确定一种情况。

用信息熵来计算,1000个瓶子之中有1个有毒药,包含的信息熵为log2(1000)< log2(1024)=10bit。每个老鼠有死和活两种可能,故一只的信息量是log2(2)=1bit

10只小白鼠可以表示为10bit。将1000瓶药水表示为长度为10的二进制数:

老鼠10老鼠9老鼠8老鼠7老鼠6老鼠5老鼠4老鼠3老鼠2老鼠1
0000000001
0000000010
0000000011
1111101000

第1号小白鼠喝 xxxxx xxxx1的药,第2号小白鼠喝xxxxx xxx1x的药,第3号小白鼠喝 xxxxx xx1xx的药,… 第10号小白鼠喝 1xxxx xxxxx的药(x表示0/1)。

举个例子,如果最后的毒药的编号是10010 11001,则容易知道死的小白鼠是1号,4号,5号,7号,10号,其他小白鼠没死。(除了1024外的毒药编号同情况)如果最后没有小白鼠死亡,则容易想到1024号是毒药。

变种1

如果可以测两轮,那么可以测多少瓶水中的一瓶毒药?

首先是第一轮死掉的小鼠不能被replace的情况,小鼠有三种状态,第一轮死,第二轮死,和两轮都没死,那么三种状态可以类比为3进制,小鼠的量程为3^10即59049瓶。对不能replace的N轮,量程为(N+1)^10

如果第一轮死掉小鼠可以被replace,显然一轮最多能描述2^10种状态。N轮可以确定2^(10N)种状态。实现方法类似变种3的思想,通过剪枝实现。

变种2

如果1000瓶里有2瓶毒药,需要多少只小鼠?

1000瓶里1瓶毒药有1000种可能性,而1000瓶2瓶毒药则有C(1000,2),即499500种可能性,那么2^18<499500<2^19。需要19只小鼠。

变体3

有16瓶水1瓶有毒,一轮时间,用多少只小白鼠能测出14瓶无毒的水?

将16瓶药水用二进制XXXX表示,取3只小白鼠来测,测出的状态为XXX。那么毒在XXX0或XXX1中,剩下14瓶无毒。

把XXX0和XXX1看做是一种情况的。16种情况就变为了16/2种情况。

3只小白鼠:

  • 0000=0
  • 0001=1
  • 0010=2
  • 0011=3
  • 0100=4
  • 0101=5
  • 0110=6
  • 0111=7
  • 1000=8
  • 1001=9
  • 1010=10
  • 1011=11
  • 1100=12
  • 1101=13
  • 1110=14
  • 1111=15

参考资料:

bitmap适用于什么场景?

bitmap的核心思想是将一个元素的可能取值映射为某个空间内的值(常见的是1bit空间,提供0,1两种状态。或是2bit空间,提供 0,1,2,3四种状态)。通过某种顺序的映射表来节省存储空间。

阅读全文 »

tmpwatch 会在指定目录中递归删除指定时间段内未被访问的文件。通常,它用于自动清除临时文件系统目录,例如 /tmp/var/tmp

  • 它只会删除空目录、常规文件和符号链接。它不会切换到其他文件系统,并避开了属于根用户的 lost+found 目录。
  • 默认情况下,tmpwatch 会根据文件的 atime(访问时间)而不是 mtime(修改时间)删除文件。
  • 可以在 tmpwatch 命令中添加其他参数来更改这些行为。

警告: 不要在 / 中运行 tmpwatchtmpreaper,因为该程序中没有防止这种情况的机制。

阅读全文 »

(JDK version:1.8)使用Timer执行定时任务很简单:

1
2
3
4
5
6
7
8
Timer timer = new Timer();
TimerTask task = new TimerTask() {
@Override
public void run() {
System.out.println("hello world");
}
};
timer.schedule(task, 10, 2000);// 延迟10ms后,每隔2s就执行一次timer task。

下面我们来来分析Timer的源码。

阅读全文 »

我的Effective Java开发笔记

阅读全文 »