C语言服务器集群调度算法
依赖项
直接复制然后保存为main.c.然后三个文件放到一个目录.
cd 目录
#编译
make
#运行
./cluster
直接上代码
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <time.h>
#include "instr_time.h"
#ifndef __cplusplus
#ifndef bool
typedef char bool;
#endif
#ifndef true
#define true ((bool) 1)
#endif
#ifndef false
#define false ((bool) 0)
#endif
#endif
//服务器数量
#define SERVER_COUNT (5)
#define RANGE_RANDOM(x,y) (x+rand()%(y-x+1))
#define SE_PTR_ISNULL(ptr) (NULL == ptr )
#define SE_check_nullptr(ptr) do{\
if (SE_PTR_ISNULL(ptr)){\
fprintf(stdout, "Memory overflow\n");\
goto SE_ERROR_CLEAR; \
}\
} while (0)
//各服务器的配置信息
struct SE_SERVER_ITEM {
int32_t weight; //初始化设置的权限系数.这个值不会改变
int32_t current_weight; //当前权重系数.
int32_t serid; //服务器编号
int32_t id; //当前连接自定义编号
//其它连接信息略
};
//服务器集群信息
struct SE_SERVER_CLUSTER {
uint32_t count;
struct SE_SERVER_ITEM **items;
};
//服务器集群配置信息
struct SE_SERVER_CONF {
//当前服务器编号
int32_t id;
//其它连接信息略
//当前服务器允许的最大连接数
uint32_t max_conn;
};
void cluster_free(struct SE_SERVER_CLUSTER **ptr) {
struct SE_SERVER_CLUSTER *cluster = *ptr;
uint32_t i = 0;
if (!SE_PTR_ISNULL(cluster)) {
for (i = 0; i < cluster->count; ++i) {
if (!SE_PTR_ISNULL(cluster->items[i]))
free(cluster->items[i]);
}
if (!SE_PTR_ISNULL(cluster->items))
free(cluster->items);
free(cluster);
}
*ptr = NULL;
}
struct SE_SERVER_ITEM * get_next_server_index(struct SE_SERVER_CLUSTER *cluster) {
uint32_t i = 0, total = 0, index = 0;
for (i = 0; i < cluster->count; ++i) {
cluster->items[i]->current_weight += cluster->items[i]->weight;
total += cluster->items[i]->weight;
if (-1 == index || cluster->items[index]->current_weight < cluster->items[i]->current_weight)
index = i;
}
cluster->items[index]->current_weight -= total;
return cluster->items[index];
}
bool init_cluster(struct SE_SERVER_CONF *serconf, uint32_t sconf_count, struct SE_SERVER_CLUSTER **ptr) {
struct SE_SERVER_CLUSTER *cluster = NULL;
uint32_t i = 0, index = 0;
SE_check_nullptr((cluster = (struct SE_SERVER_CLUSTER *) calloc(1, sizeof (struct SE_SERVER_CLUSTER))));
for (i = 0; i < sconf_count; ++i)
cluster->count += serconf[i].max_conn;
fprintf(stdout, "all connection count:%u\n", cluster->count);
SE_check_nullptr((cluster->items = (struct SE_SERVER_ITEM **) calloc(cluster->count, sizeof (struct SE_SERVER_ITEM *))));
for (i = 0; i < cluster->count; ++i) {
SE_check_nullptr((cluster->items[index] = (struct SE_SERVER_ITEM *) malloc(sizeof (struct SE_SERVER_ITEM))));
//访问权重可以在配置文件中设置 ,这里默认所有服务器的访问机会均等
cluster->items[index]->current_weight = 1;
cluster->items[index]->weight = 1;
//按物理服务器的顺序依次使用各个服务器
cluster->items[index]->serid = serconf[ i % sconf_count ].id;
cluster->items[index]->id = index;
++index;
}
(*ptr) = cluster;
return true;
SE_ERROR_CLEAR:
cluster_free(&cluster);
return false;
}
int main(int argc, char** argv) {
//3台服务器
struct SE_SERVER_CONF serconf[SERVER_COUNT];
struct SE_SERVER_CLUSTER *cluster = NULL;
int32_t i = 0;
instr_time before, after;
double elapsed_msec = 0;
srand(time(NULL));
//初始化服务配置信息
for (i = 0; i < SERVER_COUNT; ++i) {
serconf[i].id = i;
serconf[i].max_conn = RANGE_RANDOM(16, 64);
}
//根据服务配置信息,初始化服务器集群
if (!init_cluster(serconf, SERVER_COUNT, &cluster))
goto SE_ERROR_CLEAR;
INSTR_TIME_SET_CURRENT(before);
//访问服务器10000次
for (i = 0; i < 10000; ++i) {
struct SE_SERVER_ITEM *item = get_next_server_index(cluster);
fprintf(stdout, "%d request\tuse server:%d\titem:%d\n", i, item->serid, item->id);
}
INSTR_TIME_SET_CURRENT(after);
INSTR_TIME_SUBTRACT(after, before);
elapsed_msec += INSTR_TIME_GET_MILLISEC(after);
fprintf(stdout, "Time: %.3f ms\n", elapsed_msec);
cluster_free(&cluster);
return (EXIT_SUCCESS);
SE_ERROR_CLEAR:
cluster_free(&cluster);
return (EXIT_FAILURE);
}
运行截图