91超碰碰碰碰久久久久久综合_超碰av人澡人澡人澡人澡人掠_国产黄大片在线观看画质优化_txt小说免费全本

溫馨提示×

常見的負載均衡算法有哪些

小晨
712
2021-07-07 19:28:50
欄目: 云計算

常見的負載均衡算法有:1、輪詢法Round Robin,將請求按順序輪流分配到后臺服務器上,從而均衡的對待每一臺服務器;2、隨機法,通過系統隨機函數,根據后臺服務器列表的大小值來隨機選取其中一臺進行訪問;3、源地址哈希法,主要是根據服務消費者請求客戶端的IP地址實現;4、加權輪詢法,將請求按照順序且根據權重分配給后端;5、加權隨機法,根據后臺服務器不同的配置和負載情況,配置不同的權重;6、最小連接法,根據最小連接數的服務器來實現負載均衡。

常見的負載均衡算法有哪些

負載均衡算法

    在分布式系統中,多臺服務器同時提供一個服務,并統一到服務配置中心進行管理,如下圖所示。

常見的負載均衡算法有哪些

消費者通過查詢服務配置中心,獲取到服務到地址列表,需要選取其中一臺來發起RPC遠程調用。如何選擇,則取決于具體的負載均衡算法,對應于不同的場景,選擇的負載均衡算法也不盡相同。負載均衡算法的種類有很多種,常見的負載均衡算法包括輪詢法、隨機法、源地址哈希法、加權輪詢法、加權隨機法、最小連接法等,應根據具體的使用場景選取對應的算法。

1、輪詢(Round Robin)法

輪詢很容易實現,將請求按順序輪流分配到后臺服務器上,均衡的對待每一臺服務器,而不關心服務器實際的連接數和當前的系統負載。

這里通過實例化一個serviceWeightMap的Map變量來服務器地址和權重的映射,以此來模擬輪詢算法的實現,其中設置的權重值在以后的加權算法中會使用到,這里先不做過多介紹,該變量初始化如下:

private static Map<String, Integer> serviceWeightMap = new HashMap<String, Integer>();

static {

    serviceWeightMap.put("192.168.1.100", 1);

    serviceWeightMap.put("192.168.1.101", 1);<br>     //權重為4

    serviceWeightMap.put("192.168.1.102", 4);

    serviceWeightMap.put("192.168.1.103", 1);

    serviceWeightMap.put("192.168.1.104", 1);<br>        //權重為3

    serviceWeightMap.put("192.168.1.105", 3);

    serviceWeightMap.put("192.168.1.106", 1);<br>        //權重為2

    serviceWeightMap.put("192.168.1.107", 2);

    serviceWeightMap.put("192.168.1.108", 1);

    serviceWeightMap.put("192.168.1.109", 1);

    serviceWeightMap.put("192.168.1.110", 1);

}

 通過該地址列表,實現的輪詢算法的部分關鍵代碼如下

private static Integer pos = 0;

 

public static String testRoundRobin() {

     

    // 重新創建一個map,避免出現由于服務器上線和下線導致的并發問題

    Map<String, Integer> serverMap = new HashMap<String, Integer>();

    serverMap.putAll(serviceWeightMap);

     

    //取得IP地址list

    Set<String> keySet = serverMap.keySet();

    ArrayList<String> keyList = new ArrayList<String>();

    keyList.addAll(keySet);

     

    String server = null;

     

    synchronized (pos) {

        if (pos > keySet.size()) {

            pos = 0;

        }

         

        server = keyList.get(pos);

         

        pos++;

    }

     

    return server;

}

    由于serviceWeightMap中的地址列表是動態的,隨時可能由機器上線、下線或者宕機,因此,為了避免可能出現的并發問題,比如數組越界,通過在方法內新建局部變量serverMap,先將域變量拷貝到線程本地,避免被其他線程修改。這樣可能會引入新的問題,當被拷貝之后,serviceWeightMap的修改將無法被serverMap感知,也就是說,在這一輪的選擇服務器中,新增服務器或者下線服務器,負載均衡算法中將無法獲知。新增比較好處理,而當服務器下線或者宕機時,服務消費者將有可能訪問不到不存在的地址。因此,在服務消費者服務端需要考慮該問題,并且進行相應的容錯處理,比如重新發起一次調用。 

    對于當前輪詢的位置變量pos,為了保證服務器選擇的順序性,需要對其在操作時加上synchronized鎖,使得同一時刻只有一個線程能夠修改pos的值,否則當pos變量被并發修改,將無法保證服務器選擇的順序性,甚至有可能導致keyList數組越界。

    使用輪詢策略的目的是,希望做到請求轉移的絕對均衡,但付出的代價性能也是相當大的。為了保證pos變量的并發互斥,引入了重量級悲觀鎖synchronized,將會導致該輪詢代碼的并發吞吐量明顯下降。

 2、隨機法

     通過系統隨機函數,根據后臺服務器列表的大小值來隨機選取其中一臺進行訪問。由概率概率統計理論可以得知,隨著調用量的增大,其實際效果越來越接近于平均分配流量到后臺的每一臺服務器,也就是輪詢法的效果。

    隨機算法的部分關鍵代碼如下:

public static String testRandom() {

 

    // 重新創建一個map,避免出現由于服務器上線和下線導致的并發問題

    Map<String, Integer> serverMap = new HashMap<String, Integer>();

    serverMap.putAll(serviceWeightMap);

 

    //取得IP地址list

    Set<String> keySet = serverMap.keySet();

    ArrayList<String> keyList = new ArrayList<String>();

    keyList.addAll(keySet);

 

    Random random = new Random();

    int randomPos = random.nextInt(keyList.size());

     

    String server = keyList.get(randomPos);

     

    return server;

}

     跟前面類似,為了避免并發的問題,需要將serviceWeightMap拷貝到serverMap中。通過Random的nextInt函數,取到0~keyList.size之間的隨機值, 從而從服務器列表中隨機取到一臺服務器的地址,進行返回。根據概率統計理論,吞吐量越大,隨機算法的效果越接近于輪詢算法的效果。

3、源地址哈希法 

    源地址哈希法的思想是根據服務消費者請求客戶端的IP地址,通過哈希函數計算得到一個哈希值,將此哈希值和服務器列表的大小進行取模運算,得到的結果便是要訪問的服務器地址的序號。采用源地址哈希法進行負載均衡,相同的IP客戶端,如果服務器列表不變,將映射到同一個后臺服務器進行訪問。

    源地址哈希法部分關鍵代碼如下:

public static String testConsumerHash(String remoteIp) {

 

    // 重新創建一個map,避免出現由于服務器上線和下線導致的并發問題

    Map<String, Integer> serverMap = new HashMap<String, Integer>();

    serverMap.putAll(serviceWeightMap);

 

    //取得IP地址list

    Set<String> keySet = serverMap.keySet();

    ArrayList<String> keyList = new ArrayList<String>();

    keyList.addAll(keySet);

     

    int hashCode = remoteIp.hashCode();

    int pos = hashCode % keyList.size();

     

    return keyList.get(pos);

}

4、加權輪詢(Weight Round Robin)法

    不同的后臺服務器可能機器的配置和當前系統的負載并不相同,因此它們的抗壓能力也不一樣。跟配置高、負載低的機器分配更高的權重,使其能處理更多的請求,而配置低、負載高的機器,則給其分配較低的權重,降低其系統負載,加權輪詢很好的處理了這一問題,并將請求按照順序且根據權重分配給后端。

    加權輪詢法部分關鍵代碼如下:

public static String testWeightRoundRobin() {

 

    // 重新創建一個map,避免出現由于服務器上線和下線導致的并發問題

    Map<String, Integer> serverMap = new HashMap<String, Integer>();

    serverMap.putAll(serviceWeightMap);

 

    //取得IP地址list

    Set<String> keySet = serverMap.keySet();

    Iterator<String> it = keySet.iterator();

 

    List<String> serverList = new ArrayList<String>();

 

    while (it.hasNext()) {

        String server = it.next();

        Integer weight = serverMap.get(server);

        for (int i=0; i<weight; i++) {

            serverList.add(server);

        }

    }

 

    String server = null;

 

    synchronized (pos) {

        if (pos > serverList.size()) {

            pos = 0;

        }

         

        server = serverList.get(pos);

        pos++;

    }

     

    return server;

}

與輪詢算法類似,只是在獲取服務器地址之前增加了一段權重計算代碼,根據權重的大小,將地址重復增加到服務器地址列表中,權重越大,該服務器每輪所獲得的請求數量越多。

 5、加權隨機(Weight Random)法

    加權隨機法跟加權輪詢法類似,根據后臺服務器不同的配置和負載情況,配置不同的權重。不同的是,它是按照權重來隨機選取服務器的,而非順序。

    部分關鍵代碼如下:

public static String testWeightRandom() {

    // 重新創建一個map,避免出現由于服務器上線和下線導致的并發問題

    Map<String, Integer> serverMap = new HashMap<String, Integer>();

    serverMap.putAll(serviceWeightMap);

 

    //取得IP地址list

    Set<String> keySet = serverMap.keySet();

    List<String> serverList = new ArrayList<String>();

    Iterator<String> it = keySet.iterator();

     

    while (it.hasNext()) {

        String server = it.next();

        Integer weight = serverMap.get(server);

        for (int i=0; i<weight; i++) {

            serverList.add(server);

        }

    }

 

    Random random = new Random();

    int randomPos = random.nextInt(serverList.size());

 

    String server = serverList.get(randomPos);

 

    return server;

}

 6、最小連接數法

    前面我們費盡心思來實現服務消費者請求次數分配的均衡,我們知道這樣做是沒錯的,可以為后端的多臺服務器平均分配工作量,最大程度地提高服務器的利用率,但是,實際上,請求次數的均衡并不代表負載的均衡。因此我們需要介紹最小連接數法,最小連接數法比較靈活和智能,由于后臺服務器的配置不盡相同,對請求的處理有快有慢,它正是根據后端服務器當前的連接情況,動態的選取其中當前積壓連接數最少的一臺服務器來處理當前請求,盡可能的提高后臺服務器利用率,將負載合理的分流到每一臺服務器。

0
太白县| 沙湾县| 赫章县| 抚松县| 曲沃县| 青铜峡市| 灵川县| 乐清市| 于田县| 芦溪县| 彰化市| 吉林省| 灵宝市| 丰台区| 繁昌县| 建始县| 万山特区| 山东省| 莱芜市| 津市市| 嘉禾县| 商丘市| 宁德市| 太和县| 桐乡市| 肥乡县| 波密县| 北碚区| 大安市| 微山县| 微博| 巫山县| 盘锦市| 敦煌市| 上饶县| 汉中市| 开封市| 迭部县| 资中县| 精河县| 太仓市|