自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(64)
  • 收藏
  • 关注

原创 Nginx:正向代理与反向代理的区别

正向代理的概念正向代理,也就是传说中的代理,他的工作原理就像一个跳板,简单的说,我是一个用户,我访问不了某网站,但是我能访问一个代理服务器这个代理服务器呢,他能访问那个我不能访问的网站于是我先连上代理服务器,告诉他我需要那个无法访问网站的内容代理服务器去取回来,然后返回给我从网站的角度,只在代理服务器来取内容的时候有一次记录有时候并不知道是用户的请求,也隐藏

2016-12-08 01:30:20 455

原创 浅谈操作系统的内存管理

为了支持多进程(同一时间允许多个进程),解决直接操作内存带来的各种问题,引入了地址空间——允许每个进程都拥有自己的地址,硬件上需要两个寄存器——基址寄存器(保存进程开始地址)和界址寄存器(保存上界,防止内存溢出)。当我们执行一条指令,实际的物理内存地址是根据基址和偏移量来计算得到。而每个进程拥有的地址空间是不同的,因此也就使得多进程成为可能。考虑到内存大小很难容纳下所有并发执行的进程—

2016-12-03 18:53:40 778

原创 Linux内核详解(五)

Linux块I/O层系统能够随机访问固定大小数据块的硬件设备称作块设备,比如硬盘/闪存;按照字符流的方式被有序访问就是字符设备,比如键盘。两者的区别在于是否可以随机访问数据。块设备中最小的可寻址单元是扇区,扇区大小一般是2的整数倍(512B),虽然物理磁盘寻址是以扇区为基本单位的,但内核执行的所有磁盘操作都是以块为基本单位的。块是文件系统的一种抽象——只能基于块来访问文件系统。内核

2016-11-24 13:04:31 557

原创 Linux内核详解(四)

Linux内核时间和定时器管理硬件为内核提供了一个系统定时器用来计算时间,系统定时器以某种频率自动触发时钟中断,该频率可通过编程预定,称作节拍率。当时钟中断发生时,内核就通过一种特殊的中断处理程序对其进行处理。因为预编的节拍率对内核来说是可知的,所以内核知道连续两次时钟中断的间隔时间(节拍),它等于节拍率分之一秒。内核就是通过这种已知的时钟间隔来计算墙上(实际)时间和系统运行时间的。另外内核也

2016-11-23 21:57:09 509

原创 Linux内核详解(三)

Linux中断处理中断使硬件发出通知给cpu,cpu接收到中断后即停止当前工作并立刻向操作系统告知此信号的到来(中断控制器连接着多路中断管线,当接收到一个中断后,中断控制器便向cpu发送一个电信号)。硬件设备生成中断并不考虑与处理器的时钟同步——中断随时可以产生,内核随时被中断。不同的设备对应不同的中断,每个中断都有一个唯一的数字标志,这样操作系统就可以给不同的中断提供对应的中断处理程序。

2016-11-23 16:04:22 388

原创 Linux内核详解(二)

Linux调度程序Linux调度程序负责决定执行哪个(处于可运行状态的)进程,何时执行以及执行多长时间。多进程操作系统分为两种:抢占式和非抢占式;Linux实现了抢占式机制,即有调度程序决定何时挂起一个正在运行的进程,而让其他进程能够执行;非抢占式下的进程除非自己主动挂起(yield),否则将会一直执行。调度策略决定何时让什么进程运行。进程可以被分为I/O密集型(比如G

2016-11-22 22:56:48 463

原创 Linux内核详解(一)

Linux内核描述通常Linux内核有负责响应中断的中断服务程序,负责管理多个进程从而分享cpu时间的调度程序,负责管理进程地址空间的内存管理程序和网络、进程间通信等系统服务程序组成。在系统中运行的应用程序通过系统调用来与内核通信,通常是调用库函数(比如C库函数),再由库函数通过系统调用让内核完成各种不同任务。另外库函数和系统调用并不一定是一一对应的。内核还要负责管理系统的硬件设备,当硬件

2016-11-22 21:32:34 2294

原创 子进程和线程的区别

相同点:二者都具有ID,一组寄存器,状态,优先级以及所要遵循的调度策略;每个进程都有一个进程控制块,线程也拥有一个线程控制块;线程和子进程共享父进程中的资源;线程和子进程独立于它们的父进程,竞争使用处理器资源;线程和子进程的创建者可以在线程和子进程上实行某些控制,比如,创建者可以取消、挂起、继续和修改线程和子进程的优先级;线程和子进程可以改变其属性并创建新的资源;不同的:

2016-11-22 14:51:37 2231

原创 Redis时延分析

Redis采用Reactor模式,Reactor模式将事件驱动逻辑和具体的业务逻辑分离,同时将不同类型请求通过面向对象的方式分离,在Reactor上提供了注册/移除事件等方法,供应用代码使用,而事件分发方法,通常是一个循环调用,Reactor模式一般都是单线程的,好处是每个事件处理时不需要考虑共享资源的互斥访问,缺点是不能高效利用CPU,对于时间驱动,程序向中间人注册一个Event Handl

2016-11-22 11:54:31 1452

原创 Redis学习笔记

Redis是一个远程内存数据库,复制特性和提供了不同类型的数据结构,非关系数据库可以存储键和五种不同类型的值之间的映射,可以将存储在内存的键值对数据持久化到硬盘,可以使用复制特性来扩展读性能,使用客户端分片来扩展写性能,用户可以将Redis扩展成一个能够包含数百GB数据,上百万TPS的系统。Redis不使用表,也不会预定义或强制去要求用户对Redis存储的数据进行关联。Memcached和Redi

2016-11-21 09:09:22 642

转载 Redis计数在新浪微博的应用

微博业务的迅速发展,对基础架构层面的要求也越来越高。新浪作为国内最早使用redis,并且是国内最大的redis使用者,在redis的使用上,也在逐步优化和提高。作为微博中一项重要的数据,计数类业务在微博业务中占的比重和重要性逐步提高。计数结果的准确度直接影响用户体验,并且很容易引起用户的投诉。在计数业务上,在不断的优化和改进中,我们主要经历了以下三个阶段:初级阶段从2010

2016-11-19 15:50:32 805

转载 微博关系服务与Redis的故事

新浪微博的工程师们曾经在多个公开场合都讲到过,微博平台当前在使用并维护着可能是世界上最大的Redis集群,其中最大的一个业务,单个业务使用了超过 10T 的内存,这里说的就是微博关系服务。风起2009年微博刚刚上线的时候,微博关系服务使用的是最传统的 Memcache+Mysql 的方案。Mysql 按 uid hash 进行了分库分表,表结构非常简单:业务方存在两

2016-11-19 15:17:13 377

原创 Select和Epoll

当有数以万计的并发连接存在时,可能每一毫秒只有数百个活跃连接,当调用select返回活跃连接时,它需要将所有待监控连接传入,且需要在内核中遍历所有传递进来的fd,同时在高并发下会频繁调用。而epoll使用了三个方法来完成select要做的事情,这样就区分了频繁调用和不频繁调用的操作;比如对于创建epoll描述的epoll_create方法和用于添加/删除待监控连接的epoll_ctrl方法是不太频

2016-11-18 10:12:26 292

原创 TCP协议详解

在TCP协议中客户端和服务端之间的交互主要分为3个部分:客户端与服务端建立一个TCP连接;客户端和服务端在该连接上接收和发送数据;关闭TCP连接。当服务端调用ServerSocket的bind方法绑定并监听某个端口时,内核就会建立该端口的SYN队列和ACCEPT队列。当客户端调用Socket的connect方法向服务端发起连接建立请求,一个TCP连接的建立需要经过三次握手:首先客户端向服务端发

2016-11-18 10:11:24 499

原创 Java线程池

线程池的关闭我们可以通过调用线程池的shutdown方法或者shutdownNow方法来关闭线程池,其原理是遍历线程池中的所有工作线程,然后逐个调用线程的interrupt方法来中断线程。这也就意味着无法响应中断的线程可能就无法终止。shutdown方法按顺序中断之前已提交的任务,同时拒绝接收新的任务。这个方法不会等待之前已提交任务执行完成,可通过调用awaitTermin

2016-06-03 18:45:27 443

原创 几种排序算法总结

归并排序归并排序是将一个待排序记录构成的文件看做是由多个有序子文件构成,通过对有序子文件使用若干次归并的方法得到一个有序文件。该算法是采用分治法的一个非常典型的应用。归并排序的基本思路是,首先将待排序文件分为一个个的有序子文件(具体做法是将文件分成两部分,接下来对分出来的两部分各自分成两部分,以此类推,当分出来的部分中只有一个元素时,就可以认为该部分已经有序了),然后依次合并相邻的两个子文

2016-04-03 13:40:14 471

原创 非阻塞算法

在基于锁的算法中可能会由于线程在持有锁或者内存页缺失导致I/O阻塞,从而引发活跃性问题。而在非阻塞算法中,一个线程的失败不会导致其他线程也失败或挂起。通常我们会使用CAS来协调各个线程之间的操作,无竞争的CAS总能执行成功,并且如果有多个线程竞争同一个CAS,那么总会有一个线程在竞争中胜出并执行下去。创建非阻塞算法的关键在于,要找出如何将原子修改的范围缩小到单个变量上,同时还要维护数据的一致性

2016-03-30 10:37:52 714

原创 把Java数组转换为List时的注意事项

现在将一个Java数组转换成List。对此,Arrays这个类中提供了一个asList的方法,但是如果没有慎重思考就随便使用可能会产生一些糟糕的后果。比如执行下面的代码:System.out.println( Arrays.asList(new String[] { "a", "b" })); System.out.println(

2016-03-06 09:32:24 440

原创 布隆过滤器

哈希函数哈希函数(Hash)是将一个大的数据集映射到一个小的数据集上,这些小的数据集叫做哈希值或散列值。一个应用是Hash table(散列表,也叫哈希表),是根据哈希值 (Key value) 而直接进行访问的数据结构。也就是说,它通过把哈希值映射到表中一个位置来访问记录,以加快查找的速度。下面是一个典型的 hash 函数 / 表示意图:哈希函数有两个特点:如果根据同

2016-02-23 11:02:22 740

原创 Java内存模型

假设有一个线程为变量 aVariable 赋值:aVariable = 10;内存模型需要解决的问题是:在什么条件下,读取 aVariable 的线程将看到这个新值。通常而言,如果缺少同步,那么将会有许多因素使得线程无法立即甚至永远看到另一个线程的操作结果:在编译器中生成的指令顺序,可以与源代码中的顺序不同;编译器可能会把变量保存在寄存器而不是内存中;处理器可以采取乱序或并行等方式来执行指

2016-02-12 20:09:53 319

原创 AbstractQueuedSynchronizer(AQS)

概述AQS提供了实现阻塞锁和相关依赖于FIFO等待队列的同步器(semaphore,events等)的框架;这个类设计成用来构建依赖于单个原子int值去代表状态的同步器;其子类必须定义改变状态的protected方法;这个类的其它方法用来实现入队列和阻塞机制;子类可以持有其它状态域,但是仅仅使用getState,setState以及compareAndSetState方法原子更新int值。子类

2016-02-11 15:29:14 383

原创 Java NIO

Java NIO引入了一套新的抽象用于I/O处理。关于NIO主要分为以下几点:缓冲区的操作;内核空间和用户进程空间;虚拟内存和分页;面向流的I/O和面向文件的I/O;多工I/O(就绪性选择);缓冲区操作缓冲区和缓冲区如何操作,是所有I/O的基础。所谓输入和输出无非就是讲数据移入和移出缓冲区。进程执行 I/O 操作,归结起来,也就是向操作系统发出请求,让它要么把缓

2016-01-31 16:56:44 452

原创 ThreadLocal详解

ThreadLocal类用来提供线程内部的局部变量。这种变量在多线程环境下访问(通过get或set方法访问)时能保证各个线程里的变量相对独立于其他线程内的变量。ThreadLocal实例通常来说都是private static类型的,用于关联线程和线程的上下文。ThreadLocal的设计初衷是,提供线程内部的局部变量,在本线程内随时随地可取,隔离其他线程。ThreadLocal基本操

2016-01-16 23:51:36 375

原创 HashMap解析

HashMap是基于哈希表的Map接口的实现,允许key和value为null,并且不保证其内部元素的顺序,随着时间推移,同一元素的位置也可能改变(resize)。HashMap有两个因素影响其性能:初始容量(initial capacity)和负载因子(load factor)。初始容量即哈希表创建时桶(bucket)的数量,负载因子是用来衡量在哈希表容量自动扩展之前允许的多满,过高

2016-01-16 22:49:21 818

原创 Executor和ExecutorService

ExecutorExecutor用来执行已提交的Runnable任务,该接口将任务的提交与具体执行进行了解耦。它通常用来代替显示地创建线程,例如:Executor executor = anExecutor;executor.execute(new RunnableTask1());executor.execute(new RunnableTask2());

2016-01-16 21:04:54 336

原创 UDP:用户数据报协议

UDP是一个简单的面向数据报的运输层协议。进程的每个操作都刚好产生一个UDP数据报,并组装成一份带发送的IP数据报。这与面向流字符的协议不同,如TCP,应用程序产生的全体数据与真正发送的单个IP数据报可能没有什么联系。UDP封装格式如下:UDP不提供可靠性:它把应用程序传给IP层的数据发送出去,但是并不保证它们能够成功达到目的端。任何可靠性必须由上层来提供。UDP首部如下:

2016-01-16 15:44:20 806

原创 String#intern解析

在Java中,JVM为8种基本类型以及String类型提供了常量池。基于String类型使用常量池,通常有两种方法:在直接使用双引号声明的String对象会直接存储在常量池中。否则,使用String的intern方法。String的intern方法会从字符串常量池中查询当前字符串是否存在,如果不存在则将当前字符串放入常量池,否则返回字符串。

2016-01-15 21:22:14 431

原创 垃圾回收器种类

Hotspot VM目前有四种垃圾回收器:串行垃圾回收器(Serial Garbage Collector);并行垃圾回收器(Parallel Garbage Collector);串行垃圾回收器(Serial Garbage Collector)并行垃圾回收器(Parallel Garbage Collector)并发标记扫描垃圾回收器(CMS

2016-01-15 15:33:01 493

原创 强引用、软引用、弱引用、虚引用

Java将对象引用分为4种级别,从而使程序更加灵活控制对象的生命周期,这四种级别从高到低依次为:强引用,软引用如果一个对象只有弱引用指向它,垃圾回收器会立即回收该对象,这是一种急切回收方式。相对的,如果有软引用指向这些对象,则只有在JVM需要内存时才回收这些对象。弱引用和软引用的特殊行为使得它们在某些情况下非常有用。例如:软引用可以很好的用来实现缓存,当JVM需要内存时,垃圾回收器就会回收

2016-01-14 18:46:04 364

原创 TCP拥塞控制

为了防止网络的拥塞现象,TCP提出了一系列的拥塞控制机制。最初由V. Jacobson在1988年提出的TCP的拥塞控制由慢启动(Slow start)和拥塞避免(Congestion avoidance)组成,后来USD Reno版本中又针对性的加入了快速重传(Fast retransmit)、快速恢复(Fast Recovery)算法,再后来在USD NewReno中又对快速恢复算法进行了改进

2016-01-14 14:38:12 372

原创 WeakHashMap解析

WeakHashMap是一个带有弱引用key的HashMap实现。Map中的entry将会被删除当其key不再被正常使用,即除了对key的引用外,没有其它对key的强引用。此时key将会被垃圾回收器回收,然后相应的entry会被删除。示例如下:@org.junit.Testpublic void test0() { Map weakMap = new WeakHash

2016-01-14 14:34:00 411

转载 Java字节代码的操纵

在一般的Java应用开发过程中,开发人员使用Java的方式比较简单。打开惯用的IDE,编写Java源代码,再利用IDE提供的功能直接运行Java 程序就可以了。这种开发模式背后的过程是:开发人员编写的是Java源代码文件(.java),IDE会负责调用Java的编译器把Java源代码编译成平台无关的字节代码(byte code),以类文件的形式保存在磁盘上(.class)。Java虚拟机(JVM)

2016-01-14 11:49:14 369

原创 I/O复用

什么是I/O复用?操作系统为你提供一个功能,当内核发现进程指定的一个或多个I/O条件就绪时(即输入已经准备好被读取,获取描述符能够接受更多的输出),他就会给进程一个通知。这种功能就称之为“I/O复用”。I/O复用主要是由select和poll两个函数提供。I/O复用典型使用在一下场景:当客户处理多个描述符(通常是交互式输入和网络套接字)时,必须使用I/O复用。一个客

2016-01-13 11:55:28 759

转载 深入理解Java内存模型

并发编程模型的分类在并发编程中,我们需要处理两个关键问题:线程之间如何通信及线程之间如何同步(这里的线程是指并发执行的活动实体)。通信是指线程之间以何种机制来交换信息。在命令式编程中,线程之间的通信机制有两种:共享内存和消息传递。在共享内存的并发模型里,线程之间共享程序的公共状态,线程之间通过写-读内存中的公共状态来隐式进行通信。在消息传递的并发模型里,线程之间没有公共状态,线程之

2016-01-12 22:55:41 299

原创 缓存算法

缓存就是临时存储数据(通常是使用频繁的数据)的地方,以避免额外的开销较大的计算,并且使得获取结果的速度更快。缓存相关的术语:命中(如果在缓存中,一个条目通过get被找到了,我们就称之为缓存命中)缓存Miss存储成本(数据放入缓存所需要的时间和空间)索引成本失效(当存在缓存中的数据需要更新时,就意味着该数据失效了)缓存算法(当缓存未命中时,且缓存容量已满,就需要从缓存中置换出

2016-01-12 15:26:28 1142

原创 ConcurrentHashMap解析(JDK8)

在JDK8中,ConcurrentHashMap实现机制较JDK7发生了很大变化,其摒弃了分段锁(Segment)的概念,而是利用CAS算法,与Hashtable一样,内部由“数组+链表+红黑树”的方式实现。同时又增加了许多辅助类,例如TreeBin,以实现并发性。构造函数构造器中有3个参数,分别是initialCapacity,loadFactor,concurr

2016-01-11 17:23:22 2138 1

原创 Java阻塞队列

阻塞队列(BlockingQueue)是指一个这样的一个Queue,它支持两个额外的操作:当队列为空时,获取元素的线程会一直阻塞等待直到队列变为非空;当队列已满时,添加元素的线程会一直阻塞等待直到队列有可用空间;阻塞队列常用于生产者消费者模式。阻塞队列提供了四种不同的形式操作方法:JDK提供了7个阻塞队列,分别是:ArrayBlockingQueue

2016-01-11 11:53:05 282

原创 ConcurrentHashMap解析

同步容器类在执行每个操作期间都会持有一个锁,有时当持有锁花费时间较长,此时其它线程在这段时间内都不能访问该容器,从而导致性能下降。ConcurrentHashMap与HashMap一样,也是一个基于散列的Map,但它使用了一种完全不同的加锁策略来提供更高的并发性和伸缩性。ConcurrentHashMap使用粒度更细的称为分段锁(Lock Striping)的加锁机制实现更大程度的共享。分

2016-01-11 10:19:09 358

原创 Java集合概览

Collection类层次图:Map类层次图: Set接口继承了Collection接口。Set集合中不能包含重复的元素,每个元素必须是唯一的。当将元素加入Set中,重复元素会自动移除。有三种常见的Set实现——HashSet, TreeSet和LinkedHashSet。总体而言,当需要一个访问快速的Set,应使用HashSet;需要一个排序的Set,应该

2016-01-10 16:28:11 288

原创 Java不可变对象

不可变对象是指一个对象的状态在对象被创建之后就不再变化。不可变对象对于缓存是非常好的选择,因为你不需要担心它的值会被更改。创建一个不可变类:将类声明为final,所以它不能被继承;将所有的成员声明为私有的,这样就不允许直接访问这些成员;对变量不要提供setter方法;将所有可变的成员声明为final,这样只能对它们赋值一次;通过构造器初始化所有成员,进行深拷贝(deep copy)

2016-01-10 16:27:28 5061

空空如也

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除