clear all; clc; close all

%% PARAMETROS

modelo = 'CDL-A'; % Rayleigh ou CDL-A
distancia = 0.5;
distanciaD2D = 0.015;
fatorK = 10;
velocidade = 3;
num_rbs = 100;
espacamento = 15000;
num_subportadoras = 12;
W = num_subportadoras*espacamento;
M_real = 40; % número de CUEs reais
N = 4*M_real; % número de DUEs
TTI = 1000;
num_cues_inicial = 50;
num_cues_final = 100;
usuarios = num_cues_inicial:num_cues_final;

escolheGTMplus = 1;
escolheGA = 1;
escolheProposta = 1;
escolheAleatorio = 1;

%% INICIALIZA VARIAVEIS

auxM = num_cues_inicial-1;
if(escolheGTMplus)
    t_gtmplus = zeros(TTI,num_cues_final-auxM);
    rtotal_gtmplus = zeros(TTI,num_cues_final-auxM);
    fairness_vazao_gtmplus = zeros(TTI,num_cues_final-auxM);
    retardo_gtmplus = zeros(TTI,num_cues_final-auxM);
end

if(escolheGA)
    t_ga = zeros(TTI,num_cues_final-auxM);
    rtotal_ga = zeros(TTI,num_cues_final-auxM);
    fairness_vazao_ga = zeros(TTI,num_cues_final-auxM);
    retardo_ga = zeros(TTI,num_cues_final-auxM);
end

if escolheProposta
    t_proposta = zeros(TTI,num_cues_final-auxM);
    rtotal_proposta = zeros(TTI,num_cues_final-auxM);
    fairness_vazao_proposta = zeros(TTI,num_cues_final-auxM);
    retardo_proposta = zeros(TTI,num_cues_final-auxM);
end

if escolheAleatorio
    t_aleatorio = zeros(TTI,num_cues_final-auxM);
    rtotal_aleatorio = zeros(TTI,num_cues_final-auxM);
    fairness_vazao_aleatorio = zeros(TTI,num_cues_final-auxM);
    retardo_aleatorio = zeros(TTI,num_cues_final-auxM);
end

%% REALIZA MODELAGEM DE CANAL

GGnb = zeros(TTI,1,N);
GGmb = zeros(TTI,1,num_cues_final);
GGnn = zeros(TTI,N, N);
GGmn = zeros(TTI,num_cues_final, N);
for t = 1:TTI
    if mod(t,10)==0
        fprintf(strcat(['Modela canal - TTI - ' num2str(t) '\n']));
    end
    switch modelo
        case 'Random'
            GGnb(t,:,:) = -normrand(100,10,1,N);
            GGmb(t,:,:) = -normrand(100,10,1,num_cues_final);
            GGnn(t,:,:) = -normrand(60,10,N, N);
            GGmn(t,:,:) = -normrand(60,10,num_cues_final, N);
        otherwise
            GGnb(t,:,:) = ModelaCanal(1, N, modelo, distancia, fatorK, velocidade, num_rbs);
            GGmb(t,:,:) = ModelaCanal(1, num_cues_final, modelo, distancia, fatorK, velocidade, num_rbs);
            GGnn(t,:,:) = ModelaCanalD2D(N, N, modelo, distanciaD2D, fatorK, velocidade, num_rbs);
            GGmn(t,:,:) = ModelaCanalD2D(num_cues_final, N, modelo, distanciaD2D, fatorK, velocidade, num_rbs);
    end
end

%% CARREGA BUFFER

fprintf(strcat(['Modela canal - TTI - ' num2str(t) '\n']));
serie1 = load('mat-1ms-20110520-000000-0.txt')';
serie2 = load('mat-1ms-20110623-230233-4.txt')';
serie3 = load('mat-1ms-20111027-213205-5.txt')';
serie4 = load('mat-1ms-20110921-000000-0.txt')';
serie5 = load('mat-1ms-20111029-110001-1.txt')';
tamanhoTotal = TTI;
amostra=[serie1(1,1:tamanhoTotal); serie1(1,tamanhoTotal+1:2*tamanhoTotal); serie1(1,2*tamanhoTotal+1:3*tamanhoTotal); serie1(1,3*tamanhoTotal+1:4*tamanhoTotal); serie1(1,4*tamanhoTotal+1:5*tamanhoTotal);
    serie2(1,1:tamanhoTotal); serie2(1,tamanhoTotal+1:2*tamanhoTotal); serie2(1,2*tamanhoTotal+1:3*tamanhoTotal); serie2(1,3*tamanhoTotal+1:4*tamanhoTotal); serie2(1,4*tamanhoTotal+1:5*tamanhoTotal);
    serie3(1,1:tamanhoTotal); serie3(1,tamanhoTotal+1:2*tamanhoTotal); serie3(1,2*tamanhoTotal+1:3*tamanhoTotal); serie3(1,3*tamanhoTotal+1:4*tamanhoTotal); serie3(1,4*tamanhoTotal+1:5*tamanhoTotal);
    serie4(1,1:tamanhoTotal); serie4(1,tamanhoTotal+1:2*tamanhoTotal); serie4(1,2*tamanhoTotal+1:3*tamanhoTotal); serie4(1,3*tamanhoTotal+1:4*tamanhoTotal); serie4(1,4*tamanhoTotal+1:5*tamanhoTotal);
    serie5(1,1:tamanhoTotal); serie5(1,tamanhoTotal+1:2*tamanhoTotal); serie5(1,2*tamanhoTotal+1:3*tamanhoTotal); serie5(1,3*tamanhoTotal+1:4*tamanhoTotal); serie5(1,4*tamanhoTotal+1:5*tamanhoTotal)];
amostra=amostra';
clear serie1; clear serie2; clear serie3; clear serie4; clear serie5;

%% REALIZA SIMULACAO

for t = 1:TTI
    if mod(t,1)==0
        fprintf(strcat(['Simula - TTI - ' num2str(t) '\n']));
    end
    
    for M = num_cues_inicial:num_cues_final
        if mod(M,5)==0
            fprintf(strcat(['Simula - TTI - ' num2str(t) ' - M - ' num2str(M) '\n']));
        end
        
        [~, tamAmostra] = size(amostra);
        q=zeros(1,M);
        for mm=1:M
            q(mm)=amostra(t,randi(tamAmostra));
            amostra_m(:,mm) = amostra(:,randi(tamAmostra));
        end
                
        K = M-M_real; % blocos ociosos
        Pm = zeros(1,M);
        Pm(1:K) = 23;
        Pn = zeros(1,N) + 10;
        gama_m = zeros(1,M) + 7;
        gama_n = zeros(1,N) + 4.7;
        Wm = CalculaWm(num_rbs,M,W);
        sigma2_m = zeros(1,M) - 174 + 10*log10(Wm);
        sigma2_n = zeros(1,N) - 174 + 10*log10(W);
        Gnb = squeeze(GGnb(t,:,:))';
        Gmb = squeeze(GGmb(t,:,1:M))';
        Gnn = squeeze(GGnn(t,:,:));
        Gmn = squeeze(GGmn(t,1:M,:));
        
        if 1
            Pm = ConverteDBW(Pm)/1000;
            Pn = ConverteDBW(Pn)/1000;
            gama_m = ConverteDBW(gama_m);
            gama_n = ConverteDBW(gama_n);
            sigma2_m = ConverteDBW(sigma2_m)/1000;
            sigma2_n = ConverteDBW(sigma2_n)/1000;
            Gnb = ConverteDBW(Gnb);
            Gmb = ConverteDBW(Gmb);
            Gnn = ConverteDBW(Gnn);
            Gmn = ConverteDBW(Gmn);
        end
        
        if escolheGTMplus
            tic
            [ r_gtmplus] = AlgoritmoGTMplus(M, K, N, Pm, Pn, gama_m, gama_n, Gnb, Gmb, Gnn, Gmn, sigma2_m, sigma2_n, Wm);
            t_gtmplus(t,M-auxM) = toc*1000;
        end
        
        if escolheGA
            tic
            [ r_ga ] = AlgoritmoGenetico(M, K, N, Pm, Pn, gama_m, gama_n, Gnb, Gmb, Gnn, Gmn, sigma2_m, sigma2_n, Wm);
            t_ga(t,M-auxM) = toc*1000;
        end
        
        
        if escolheProposta
            tic
            [ r_proposta ] = AlgoritmoProposta(M, K, N, Pm, Pn, gama_m, gama_n, Gnb, Gmb, Gnn, Gmn, sigma2_m, sigma2_n, Wm, q, amostra_m);
            t_proposta(t,M-auxM) = toc*1000;
        end
        
        if escolheAleatorio
            tic
            [ r_aleatorio ] = AlgoritmoAleatorio(M, K, N, Pm, Pn, gama_m, gama_n, Gnb, Gmb, Gnn, Gmn, sigma2_m, sigma2_n, Wm);
            t_aleatorio(t,M-auxM) = toc*1000;
        end
       
        if escolheGTMplus 
            rtotal_gtmplus(t,M-auxM) = sum(r_gtmplus); end
        if escolheGA 
            rtotal_ga(t,M-auxM) = sum(r_ga); end
        if escolheProposta
            rtotal_proposta(t,M-auxM) = sum(r_proposta); end
        if escolheAleatorio 
            rtotal_aleatorio(t,M-auxM) = sum(r_aleatorio); end
        
        if escolheGTMplus 
            fairness_vazao_gtmplus(t,M-auxM) = CalculaJusticaVazao(r_gtmplus); end
        if escolheGA 
            fairness_vazao_ga(t,M-auxM) = CalculaJusticaVazao(r_ga); end
        if escolheProposta
            fairness_vazao_proposta(t,M-auxM) = CalculaJusticaVazao(r_proposta); end
        if escolheAleatorio 
            fairness_vazao_aleatorio(t,M-auxM) = CalculaJusticaVazao(r_aleatorio); end
        
        if escolheGTMplus 
            retardo_gtmplus(t,M-auxM) = CalculaRetardo(r_gtmplus,q); end
        if escolheGA 
            retardo_ga(t,M-auxM) = CalculaRetardo(r_ga,q); end
        if escolheProposta
            retardo_proposta(t,M-auxM) = CalculaRetardo(r_proposta,q); end
        if escolheAleatorio 
            retardo_aleatorio(t,M-auxM) = CalculaRetardo(r_aleatorio,q); end
        
    end
end

%% FIGURA 1

figure(1)
if escolheProposta
    plot(usuarios,mean(rtotal_proposta),'k-','LineWidth',2)
    hold on
end
if escolheGA
    plot(usuarios,mean(rtotal_ga),'c:','LineWidth',2)
    hold on
end
if escolheGTMplus
    plot(usuarios,mean(rtotal_gtmplus),'b--','LineWidth',2)
    hold on
end
if escolheAleatorio
    plot(usuarios,mean(rtotal_aleatorio),'r-.','LineWidth',2)
end
legend('Proposed','GA','GTM+','Rand','Location','NorthWest')
grid on
xlabel('Number of CUEs'); ylabel('Total throughput (Mbits/s)');
set(gca,'FontName','Times New Roman');

%% FIGURA 2

figure(2)
if escolheProposta
    plot(usuarios,mean(t_proposta),'k-','LineWidth',2)
    hold on
end
if escolheGA
    plot(usuarios,mean(t_ga),'c:','LineWidth',2)
    hold on
end
if escolheGTMplus
    plot(usuarios,mean(t_gtmplus),'b--','LineWidth',2)
end
if escolheAleatorio
    plot(usuarios,mean(t_aleatorio),'r-.','LineWidth',2)
end
legend('Proposed','GA','GTM+','Rand','Location','NorthWest')
grid on
xlabel('Number of CUEs'); ylabel('Processing time (ms)')
set(gca,'FontName','Times New Roman');

%% FIGURA 3

figure(3)
if escolheProposta
    plot(usuarios,mean(fairness_vazao_proposta),'k-','LineWidth',2)
    hold on
end
if escolheGA
    plot(usuarios,mean(fairness_vazao_ga),'c:','LineWidth',2)
    hold on
end
if escolheGTMplus
    plot(usuarios,mean(fairness_vazao_gtmplus),'b--','LineWidth',2)
end
if escolheAleatorio
    plot(usuarios,mean(fairness_vazao_aleatorio),'r-.','LineWidth',2)
end
legend('Proposed','GA','GTM+','Rand','Location','North')
grid on
xlabel('Number of CUEs'); ylabel('Fairness index')
set(gca,'FontName','Times New Roman');

%% FIGURA 4

figure(4)
if escolheProposta
    plot(usuarios,mean(retardo_proposta),'k-','LineWidth',2)
    hold on
end
if escolheGA
    plot(usuarios,mean(retardo_ga),'c:','LineWidth',2)
    hold on
end
if escolheGTMplus
    plot(usuarios,mean(retardo_gtmplus),'b--','LineWidth',2)
end
if escolheAleatorio
    plot(usuarios,mean(retardo_aleatorio),'r-.','LineWidth',2)
end
legend('Proposed','GA','GTM+','Rand','Location','NorthWest')
grid on
xlabel('Number of CUEs'); ylabel('Delay (ms)')
set(gca,'FontName','Times New Roman');