大家转起来…

非常感谢大家能够百忙之中参加我的婚礼,不胜感激,很多人非常好奇我是如何追到这位漂亮的妹纸的呢?谜底揭开,请打开下面的链接。

http://v.youku.com/v_show/id_XNjIxMjUzNzcy.html

话题#羊与海鸥的婚礼#在sina微薄上@IBYoung@如果爱能这样下去进行发送。如果有兴趣的童鞋可以查看weibo墙。

 

希望大家支持…

 

文艺青年致敬

 

The Perfect Singleton

以前经常常用如下方式,不过你会发现在RMI环境下,并不会生产同一实例。

1
2
3
4
5
6
7
8
9
10
public final class NonSafeSingleton implements Serializable {
 
    private static final NonSafeSingleton INSTANCE = new NonSafeSingleton();
 
    private NonSafeSingleton() {}
 
    public static NonSafeSingleton getInstance() {
        return INSTANCE;
    }
}

为了改进方式,我们采用如下几个方式

1
2
3
 protected Object readResolve() throws ObjectStreamException {
        return INSTANCE;
    }

或者

1
2
3
4
public enum SafeSingleton implements Serializable {
 
    INSTANCE;
}

最容易的方式,而且去掉乱七八糟的私有构造函数、getInstance等方法。

轻量级的对象池

Pool在N多环境下碰到,比如连接池、线程池、缓存池…

当某一对象从池中取得,那只有等待被用完放回去以后,其它的线程才能再次从池中获取。对象在池中是具有自己生命周期:创建、验证、使用、销毁等等。Pool的方式也许是最好的方式用来管理同一的资源。

 

运用的场景:

高频率的运用同一的资源

对象大且很消耗内存(DB连接)

需要长时间的初始化

IO消耗大

对象非线程安全

 

Apache Commons Pool 提供其轻量级的作用,不过它并未使用JDK1.5之后的Execute的框架,这是我觉得可能比较可惜的,就如同Proxool跟Boncp比较,性能指标提升最大一个就是分区和使用Execute、Guava等性能提升比较大的工具包。

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
package easypool;
 
import java.util.concurrent.ConcurrentLinkedQueue;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
 
public abstract class ObjectPool<T> {
private ConcurrentLinkedQueue<T> pool;
 
private ScheduledExecutorService executorService;
 
/**
* Creates the pool.
*
* @param minIdle
* 初始化最小的对象池中对象创建数量
*/
public ObjectPool(final int minIdle) {
// initialize pool
initialize(minIdle);
}
 
/**
* Pool创建
*
* @param minIdle
* 最小的数量
* @param maxIdle
* 最大数量
* @param validationInterval
* 检查最大/最小的池中的对象的频率
*/
public ObjectPool(final int minIdle, final int maxIdle,
final long validationInterval) {
// initialize pool
initialize(minIdle);
 
// check pool conditions in a separate thread
executorService = Executors.newSingleThreadScheduledExecutor();
executorService.scheduleWithFixedDelay(new Runnable() {
@Override
public void run() {
int size = pool.size();
if (size < minIdle) {
int sizeToBeAdded = minIdle - size;
for (int i = 0; i < sizeToBeAdded; i++) {
pool.add(createObject());
}
} else if (size > maxIdle) {
int sizeToBeRemoved = size - maxIdle;
for (int i = 0; i < sizeToBeRemoved; i++) {
pool.poll();
}
}
}
}, validationInterval, validationInterval, TimeUnit.SECONDS);
}
 
/**
* 获取对象,如果没有,那就创建且返回
*
* @return T borrowed object
*/
public T borrowObject() {
T object;
if ((object = pool.poll()) == null) {
object = createObject();
}
 
return object;
}
 
/**
* Returns object back to the pool.
*
* @param object
* object to be returned
*/
public void returnObject(T object) {
if (object == null) {
return;
}
 
this.pool.offer(object);
}
 
/**
* Shutdown this pool.
*/
public void shutdown() {
if (executorService != null) {
executorService.shutdown();
}
}
 
/**
* Creates a new object.
*
* @return T new object
*/
protected abstract T createObject();
 
private void initialize(final int minIdle) {
pool = new ConcurrentLinkedQueue<T>();
 
for (int i = 0; i < minIdle; i++) {
pool.add(createObject());
}
}
}

Simple and lightweight pool implementation

Object pools are containers which contain a specified amount of objects. When an object is taken from the pool, it is not available in the pool until it is put back. Objects in the pool have a lifecycle: creation, validation, destroying, etc. A pool helps to manage available resources in a better way. There are many using examples. Especially in application servers there are data source pools, thread pools, etc. Pools should be used in cases such as:

  • High-frequency using of the same objects
  • Objects are very big and consume much memory
  • Objects need much time for initialization
  • Objects use massive IO operations (Streams, Sockets, DB, etc.)
  • Objects are not thread-safe

When I looked for a pool implementation for one of my Java projects, I found that many people reference the Apache Commons Pool. Apache Commons Pool provides an object-pooling API. There are interfaces ObjectPool, ObjectPoolFactory, PoolableObjectFactory and many implementations. A pool provides methods addObject, borrowObject, invalidateObject, returnObject to add, take, remove and return back objects. PoolableObjectFactory defines the behavior of objects within a pool and provides various callbacks for pool’s operations.

After looking into the implementation details I found that Apache Commons Pool is not a lightweight implementation which is an overhead for my purposes. Furthermore, it uses the old Java’s keyword synchronized for a lot of methods which is not recommended for using. Java 5 introduced Executor framework for Java concurrency (multi-threading). The Executor framework is preferable here. I decided to implement a simple and lightweight pool which I would like to present here. It is only one Java class. I think it is enough if you don’t need callbacks and other advanced stuff. I created a project easy-pool on GitHub.

The pool implementation is based on ConcurrentLinkedQueue from the java.util.concurrent package. ConcurrentLinkedQueue is a thread-safe queue based on linked nodes. This queue orders elements by FIFO principle (first-in-first-out). My implementation for a generic pool looks as follows

Stacks and Queues in Java

日志

I have been working on some Java code recently that required both a stack and a queue. The choices to use aren’t immediately obvious. There is a Queue interface, but no clear concrete implementation to use. There is also a Stack class, but the javadocs point out that other classes “should be used in preference to this class”. So, what implementation do you use for stacks and queues in Java?

I found my quick rule of thumb to be that you can use the ArrayDeque class for both Stack and Queues, but some more details are below.

Common Definitions

First, let’s start with some definitions. In common usage of the word, a queue is FIFO (first-in-first-out). Just like the first person in line at the post office gets served first. A stack is LIFO (last in first out). Think of a stack of books – the last book you put on the stack is the first book you take off.

Choices in Java

In Java, things are a little more complicated, but the same principles apply. There is the aforementioned Queue interface which has the expected methods to add, remove and look at elements. (Actually, those methods come in two flavors: one throws an exception if the operation fails, the other returns a special value such as null or false; see more here).

There is also a sub-interface of Queue called Deque, short for “double ended queue” and is usually pronounced “deck”. This interface defines methods to access the elements at both ends of the collection. This functionality makes Deque a useful base for both queue and stack implementations.

However, both Queue and Deque are interfaces, so we still haven’t found a concrete implementation to use yet…

The shortlist: ArrayDeque & LinkedList

The 2 main choices are: ArrayDeque and LinkedList. There are a couple of other implementation of Deque such as ConcurrentLinkedDeque and LinkedBlockingDeque, and a plethora of implementations of Queue such as DelayQueue, LinkedBlockingDeque and PriorityQueue. Since those are more specialized (and I haven’t used them much), I won’t go into here.

ArrayDeque

From the javadocs, ArrayDeque is a resizable-array implementation of the Deque interface. Most ArrayDeque operations run in amortized constant time (i.e. slower “once in a while”, but on average constant) except for remove*, contains* and the bulk operations, all of which run in linear time. The docs point out that this class is likely to be faster than Stack when used as a stack, and faster than LinkedList when used as a queue. It is this statement that leads me to use ArrayDeque as my default implmentation for both stacks and queues.

LinkedList

The LinkedList class implements the List, Queue and Deque interfaces. In addition to implementing the List interface, the LinkedList class provides uniformly named methods to get, remove and insert an element at the beginning and end of the list. These operations allow linked lists to be used as a stack, queue, or double-ended queue.

LinkedList vs ArrayDeque

So, when would you use a LinkedList over an ArrayDeque?

Pros of a LinkedList implementation are:

  • more flexible than the ArrayDeque implementation, as it
    • implements all optional list operations.
    • allows null elements (not allowed in ArrayDeque)
  • well suited when you need to remove/insert items in the middle of the list frequently (something that can result in large array copies for the ArrayDeque).

Cons of a LinkedList implementation:

  • not ideal when iterating over items in general
  • consumes more memory than the ArrayDeque implementation

Overall

In terms of efficiency, ArrayDeque is more efficient than the LinkedList for iteration and add/remove operation at both ends. So, as the javadocs point out, in general, ArrayDeque is likely to be faster than Stack when used as a stack, and faster than LinkedList when used as a queue.