简单的负载均衡的Java实现

104 阅读1分钟

简单的负载均衡的Java实现

import java.util.Arrays;
import java.util.Random;

public class WeightedLoadBalancer {
    private static Random random = new Random();
    //保存原始权值
    private int[] weights;
    //用于计算
    private int[] remainingWeights;
    //计算总和
    private int totalWeight;

    public WeightedLoadBalancer(int[] weights) {
        this.weights = weights;
        this.remainingWeights = new int[weights.length];
        resetWeights();
    }
    
    //初始赋值以及之后重新赋值
    private void resetWeights() {
        System.arraycopy(weights, 0, remainingWeights, 0, weights.length);
        this.totalWeight = Arrays.stream(weights).sum();
    }
    
    //下一个的选择
    public int next() {
        if (totalWeight == 0) {
            resetWeights();
        }

        int selectedIndex = rouletteWheelSelection();
        remainingWeights[selectedIndex]--;
        totalWeight--;

        return selectedIndex;
    }

    private int rouletteWheelSelection() {
        // 判断其实可以去掉,谨慎得加上
        if (totalWeight == 0) {
            return random.nextInt(weights.length);
        }

        int value = random.nextInt(totalWeight);
        int sum = 0;
        for (int i = 0; i < remainingWeights.length; i++) {
            //求和,当sum超过value时,即返回
            sum += remainingWeights[i];
            if (value < sum) {
                return i;
            }
        }
        
        return remainingWeights.length - 1;
    }

    public static void main(String[] args) {
        int[] w = {1, 5, 7};
        WeightedLoadBalancer balancer = new WeightedLoadBalancer(w);

        // 模拟1300次请求
        int[] result = new int[w.length];
        for (int i = 0; i < 1300; i++) {
            int selected = balancer.next();
            result[selected]++;
        }

        System.out.println("访问次数分布: " + Arrays.toString(result));
    }
}