public void testSmoothwarmingUp() throws Exception { RateLimiter r = RateLimiter.create(2, 3, TimeUnit.SECONDS); Class<RateLimiter> rateLimiterClass = RateLimiter.class; Field storedPermits = rateLimiterClass.getDeclaredField("storedPermits");// 必须要getDeclaredField, 不能getField storedPermits.setAccessible(true); ReflectionUtils.makeAccessible(storedPermits); Object o = storedPermits.get(r); System.out.println(o + " get 1 tokens: ++++++++ " + 000000); try { Thread.sleep(3000); } catch (Exception e) { e.printStackTrace(); } while (true) { o = storedPermits.get(r); System.out.println(o + " get 1 tokens: " + r.acquire(3) + "s");// 前3个permets耗时warmupPeriod, o = storedPermits.get(r); System.out.println(o + " get 1 tokens: " + r.acquire(1) + "s"); o = storedPermits.get(r); System.out.println(o + " get 1 tokens: " + r.acquire(1) + "s");// 第四个permets之后 速率已经达到最高,完全稳定。 o = storedPermits.get(r); System.out.println(o + " get 1 tokens: " + r.acquire(1) + "s"); o = storedPermits.get(r); System.out.println("o = " + o); /** * output: * get 1 tokens: 0.0s * get 1 tokens: 1.329289s * get 1 tokens: 0.994375s * get 1 tokens: 0.662888s 上边三次获取的时间相加正好为3秒 * end * get 1 tokens: 0.49764s 正常速率0.5秒一个令牌 * get 1 tokens: 0.497828s * get 1 tokens: 0.49449s * get 1 tokens: 0.497522s */ System.out.println(o + " get 1 tokens: " + r.acquire(3) + "s"); try { int millis = 4000; // 不管之前是什么情况,不管之前acquire多少, 这里只要sleep超过warmupPeriod时间, 就会完全冷却 // xxx 错错错 // 不管之前是什么情况,只要上一个acquire小于maxPermits - thresholdPermits, 这里只要sleep超过warmupPeriod时间, 就会完全冷却 Thread.sleep(millis); // sleep warmupPeriod + extra时间, 可以保证完全冷却;extra时间是指 // Thread.sleep(millis); // 债务还清之后(即过了extra时间之后),再sleep warmupPeriod/2 时间,将处于临界点:storedPermits = thresholdPermits System.out.println("sleep " + millis); } catch (InterruptedException e) { e.printStackTrace(); } // boolean b = r.tryAcquire(6); r.setRate(r.getRate());// 通过此方法触发resync方法,进而可以设置storedPermits字段的值为最新值 o = storedPermits.get(r);// 当限流器经过warmupPeriod时间之后,它就会完全冷却,不过此时 无法观察到storedPermits字段,因为它是惰性的 System.out.println(o + " get 1 tokens: " + r.acquire(1) + "s"); o = storedPermits.get(r); System.out.println(o + " get 1 tokens: " + r.acquire(2) + "s"); o = storedPermits.get(r); System.out.println(o + " get 1 tokens: " + r.acquire(3) + "s"); o = storedPermits.get(r); System.out.println(o + " get 1 tokens: " + r.acquire(1) + "s"); o = storedPermits.get(r); System.out.println(o + " get 1 tokens: " + r.acquire(1) + "s"); o = storedPermits.get(r); System.out.println(o + " get 3 tokens: " + r.acquire(3) + "s"); System.out.println("end"); }
动态观察 RateLimiter - WarmingUp 的许可变化
原文:https://www.cnblogs.com/FlyAway2013/p/14651386.html