专业的JAVA编程教程与资源

网站首页 > java教程 正文

Java中顺序轮询算法实现

temp10 2024-11-19 11:32:03 java教程 14 ℃ 0 评论

顺序轮询算法,简单点来说就是挨个挨个的使用。

举例来说,在分布式微服务项目中,服务是集群部署并注册到服务注册中心,当某个微服务被其它微服务调用时,就需要从服务注册中心根据服务名称获取该服务的实例,由于是集群部署的,我们可能多次调用同一台服务器上的微服务,造成该机器压力过大,如果实现被调用的微服务能够均分的分发给调用者,能够减轻局部服务器压力,从而提升效率。其实这就是负载均衡的一种思想,压力由大家均摊,而今天讲的顺序轮询算法就是负载均衡的一种实现方式。

Java中顺序轮询算法实现

实现方式: 取余

由于在多线程环境下,i++是线程不安全(i, i=i+1, i),即使加了volatile也不能保证线程安全,因此使用AtomicInteger的getAndIncrement()方法能够实现i++的线程安全性。

可以将下述代码想象成微服务的实例名称都是以数组形式存放在arr里,然后每次获取实例名称的时候都是按照数组的索引获取。

public class LoadBalance {

    static final AtomicInteger atomic = new AtomicInteger();
    private static final int[] arr;
    static {
        arr = new int[5];
        for (int i = 0; i < 5; i++) {
            arr[i] = i;
        }
    }

    public static void main(String[] args) {
        // 创建10个线程,分配arr
        for (int i = 0; i < 10; i++) {
            new Thread(new Runnable() {
                @Override
                public void run() {
                    int index = atomic.getAndIncrement();;
                    System.out.println(arr[index % arr.length]);
                }
            }).start();
            
        }
    }
}

输出结果将会按照0 1 2 3 4 0 1 2 3 4 轮询。

实现方式二:相与

实现方式:index & arr.length -1

前提条件:arr.length必须是2的幂次方

优点:由于在计算机中数值的计算都是以2进制的形式计算的,所以这种相与的方式性能优于取余。

缺点:有限定条件,长度必须为2的幂次方

public class PowerOfLoadBalance {

    static final AtomicInteger atomic = new AtomicInteger();
    private static final int[] arr;
    static {
       // 数组长度为2的幂次方
        arr = new int[4];
        for (int i = 0; i < 4; i++) {
            arr[i] = i;
        }
    }

    public static void main(String[] args) {
        // 创建8个线程,分配arr
        for (int i = 0; i < 8; i++) {
            new Thread(new Runnable() {
                @Override
                public void run() {
                    int index = atomic.getAndIncrement();
                    System.out.println(arr[index & arr.length -1]);
                    //System.out.println(arr[index % arr.length]);
                }
            }).start();

        }
    }
}

为什么这种情况成立,以4为例,4-1=3,它可以为

而对于任意一个数,它的二进制可以表示为

  • m&q 的值,最小值为0,取值范围在[0, q]之间。

而对于q为什么是呢?

对于任意一个2的幂次方的数来说,它的二进制形式只能为

  • 当n>=m时,m&q = () & ( ) =
  • 当n<m时,m&q=0

这样就会导致出现相与的值都是2的幂次方或者是0,而不是在[0,2^m]之间,因此需要对其减1,且必须是2的幂次方。

Tags:

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表