1. 程式人生 > >Java訂單號生成工具(實現二)基於佇列

Java訂單號生成工具(實現二)基於佇列

使用了ConcurrentLinkedQueue,ConcurrentLinkedQueue是一個基於連結節點的無界執行緒安全佇列,它採用先進先出的規則對節點進行排序,當我們新增一個元素的時候,它會新增到佇列的尾部,當我們獲取一個元素時,它會返回佇列頭部的元素。它採用了“wait-free”演算法來實現,該演算法在Michael & Scott演算法上進行了一些修改, Michael & Scott演算法的詳細資訊可以參見參考資料一。
關於ConcurrentLinkedQueue詳情:http://ifeve.com/concurrentlinkedqueue/

package
util; import java.text.SimpleDateFormat; import java.util.Date; import java.util.concurrent.ConcurrentLinkedQueue; import java.util.concurrent.CountDownLatch; import java.util.concurrent.TimeUnit; import play.Configuration; public class OrderNumberGenerator { private static final ConcurrentLinkedQueue<Integer> queue = new
ConcurrentLinkedQueue<Integer>(); private static final CountDownLatch latch = new CountDownLatch(1); /** * 每毫秒生成訂單號數量最大值,約定取整百,整千。 */ public static final int maxPerMSECSize = Configuration.root().getInt("maxPerMSECSize", 1000); private static void init() { for (int
i = 0; i < maxPerMSECSize; i++) { queue.offer(i); } latch.countDown(); } public static Integer poll() { try { if (latch.getCount() > 0) { init(); latch.await(1, TimeUnit.SECONDS); } } catch (InterruptedException e) { e.printStackTrace(); } Integer i = queue.poll(); queue.offer(i); return i; } public static String get() { long nowLong = Long.parseLong(new SimpleDateFormat("yyyyMMddHHmmssSSS").format(new Date())); String number = maxPerMSECSize + poll() + ""; return nowLong + number.substring(1); } }