package org.cloudbus.cloudsim.power;

import org.cloudbus.cloudsim.*;
import org.cloudbus.cloudsim.power.lists.PowerVmList;
import org.cloudbus.cloudsim.power.models.PowerModel;
import org.cloudbus.cloudsim.power.models.PowerModelSpecPowerHpProLiantMl110G5Xeon3075;
import org.cloudbus.cloudsim.power.models.PowerModelSpecPowerHpProLiantMl110G4Xeon3040;
import java.util.*;

public class PowerVmAllocationPolicyMigrationqlearning
        extends PowerVmAllocationPolicyMigrationAbstract{
    private PowerVmAllocationPolicyMigrationAbstract fallbackVmAllocationPolicy;
    private double safetyParameter = 0;


    public PowerVmAllocationPolicyMigrationqlearning(
            List<? extends Host> hostList,
            PowerVmSelectionPolicy vmSelectionPolicy,
            double safetyParameter,
            PowerVmAllocationPolicyMigrationAbstract fallbackVmAllocationPolicy) {
        super(hostList, vmSelectionPolicy);
        setSafetyParameter(safetyParameter);
        setFallbackVmAllocationPolicy(fallbackVmAllocationPolicy);
    }
    //判断主机是否过载
    @Override
//    protected boolean isHostOverUtilized(PowerHost host) {
//        if(host.getUtilizaionOfCpu() > 0.7){
//            return true;
//        }
//        else {return false;}
//
//    }

    protected boolean isHostOverUtilized(PowerHost host) {
//        List<Integer> c = new ArrayList<>();
////        for (PowerHost host1 : this.<PowerHost>getHostList()) {
////            List<? extends Vm> a = host1.getVmList();
////            int b = a.size();
////            c.add(b);
////        }
////        System.out.println(c);
        double mipmax = Double.MIN_VALUE;
        double mipmin = Double.MAX_VALUE;
//        double rammax = Double.MIN_VALUE;
//        double rammin = Double.MAX_VALUE;
//        double bwmax = Double.MIN_VALUE;
//        double bwmin = Double.MAX_VALUE;
        for (Vm vm : host.getVmList()){
            double vmmip = vm.getMips()*vm.getCurrentUtilizationOfCpu();
//            double vmram = vm.getRam();
//            double vmbw = vm.getBw();
            if (vmmip > mipmax){
                mipmax = vmmip;
            }
            if (vmmip < mipmin){
                mipmin = vmmip;
            }
//            if (vmram > rammax){
//                rammax = vmram;
//            }
//            if (vmram < rammin){
//                rammin = vmram;
//            }
//            if (vmbw > bwmax){
//                bwmax = vmbw;
//            }
//            if (vmbw < bwmin){
//                bwmin = vmbw;
//            }
        }
        double Wvm = 0;
        for (Vm vm : host.getVmList()){
            double vmmip = vm.getMips() * vm.getCurrentUtilizationOfCpu();
            double s;
            if (mipmax == mipmin){
                s = 0;
            }
            else {
                s = (vmmip - mipmin)/(mipmax - mipmin);
            }
            Wvm += s;
//            double vmram = vm.getRam();
//            if (rammax == rammin){
//                s = 0;
//            }
//            else {
//                s = (vmram - rammin)/(rammax - rammin);
//            }
//            Wvm += s;
//            double vmbw = vm.getBw();
//            if (bwmax == bwmin) {
//                s = 0;
//            }
//            else{
//                s = (vmbw - bwmin)/(bwmax - bwmin);
//            }
//            Wvm += s;
        }
        double T= 3.0;
//        System.out.println(hostResourceWeight1(host));
//        int whost =(int)hostResourceWeight().get(host.getId());
//        System.out.println(whost);
        double Whost = hostResourceWeight1(host);
//        System.out.println(Wvm);
//        System.out.println((Wvm - Whost)/3);
        return (Wvm - Whost)> T;
    }
    protected double hostResourceWeight1(PowerHost host1){
        List<Map<String, Object>> migrationMap = new LinkedList<Map<String, Object>>();
        double mipmax = Double.MIN_VALUE;
        double mipmin = Double.MAX_VALUE;
//        double rammax = Double.MIN_VALUE;
//        double rammin = Double.MAX_VALUE;
//        double rwmax = Double.MIN_VALUE;
//        double rwmin = Double.MAX_VALUE;
        Map<String, Object> migrate = new HashMap<String, Object>();
        for (PowerHost host : this.<PowerHost> getHostList()){
            double hostmip = host.getTotalMips();//host.getMaxAvailableMips()*host.getNumberOfPes();
//            double hostram = host.getRam();
//            double hostrw = host.getBw();
//            PowerModel model = host.getPowerModel();
//            System.out.println(model);
            if (hostmip > mipmax){
                mipmax = hostmip;
            }
            if (hostmip < mipmin){
                mipmin = hostmip;
            }

        }
        double Whost = 0;
        double whost ;

        for (PowerHost host : this.<PowerHost> getHostList()){
            if (mipmax == mipmin){
                whost = Double.MIN_VALUE;
            }
            else {
                double hostmip = host.getTotalMips();//getMaxAvailableMips()*host.getNumberOfPes();
                whost = (hostmip - mipmin)/(mipmax - mipmin);
            }
            Whost += whost;
            Map<String, Object> migrate1 = new HashMap<String, Object>();

            migrate1.put("host", host);
            migrate1.put("resourceweight",Whost);
            migrationMap.add(migrate1);

            //migrate.put("host.getId()",Whost);
        }
        double result = 0;
        for (Map<String, Object> map :migrationMap){
            if (map.get("host") == host1){
                result = (double) map.get("resourceweight");
            }
        }
        return result;
    }
//    @Override
//    protected PowerHost getUnderUtilizedHost(Set<? extends Host> excludedHosts){
//
//    }

    /**
     * Q-learning得思想为虚拟机寻找合适主机
     */
    public PowerHost getHost(HashMap<PowerHost, Double> qa, double eta, Vm vm, Set<? extends Host> excludedHosts){
        PowerHost allocatedhost = null;
        double max = Double.MIN_VALUE;
        double was;
        for(PowerHost host : qa.keySet()){
            if (host.isSuitableForVm(vm)){
                double power = getPowerAfterAllocation((PowerHost) host, vm);
                double powerDiff = power - ((PowerHost) host).getPower();
                was = (getpositive(host.getUtilizaionOfCpu() - host.getUtilizationOfRam()) + 0.0001)/(host.getUtilizaionOfCpu() + host.getUtilizationOfRam());
                double x = 1/was;
                double cpuratiomin = vm.getMips()*vm.getCurrentUtilizationOfCpu()/host.getAvailableMips();
                double cpuratiomax = getratio();
                double a = getpositive(cpuratiomax-cpuratiomin);
                double y = 1/a;
                double zzz= host.getUtilizaionOfCpu();
                double z = 1/zzz;
                rew = 100*(1-host.getUtilizaionOfCpu())/powerDiff; //+ (1/was) + (1/getpositive(cpuratiomax-cpuratiomin)) + 0.00001*(1/host.getUtilizaionOfCpu());
                if (rew > max){
                    max = rew;
                    allocatedhost = host;
                }
            }

        }
        if (allocatedhost == null){
            for (PowerHost host : this.<PowerHost>getHostList()){
                /*double a = host.getAvailbleStorage();
                double b = vm.getSize();
                double c = host.getStorage();
                if ( c > b){
                    allocatedhost = host;
                    break;
                }*/
                if (host.isSuitableForVm(vm)){
                    allocatedhost = host;
                    break;
                }
            }
        }
        if (allocatedhost == null){
            allocatedhost  = etaGreedy(qa, eta, vm, excludedHosts);
        }
        /*if (allocatedhost.isSuitableForVm(vm)){
                return allocatedhost;
        }
        else {
            allocatedhost  = etaGreedy(qa, eta, vm, excludedHosts);
            *//*for (Host host : this.<PowerHost>getHostList()) {
                double a = host.getAvailbleStorage();
                double b = vm.getSize();
                double c = host.getStorage();
                if (a > b && c > b) {
                    allocatedhost = host;
                    break;
                }
            }*//*
        }*/
        return allocatedhost;
//        else {
//            if (allocatedhost.isSuitableForVm(vm)){
//                return allocatedhost;
//            }
//            else {
//                allocatedhost = getNewVmPlacementa(vm, excludedHosts);
//            }
//            if (allocatedhost.isSuitableForVm(vm)){
//                return allocatedhost;
//            }
//            else {
//                for (Host host : this.<PowerHost>getHostList()){
//                    if (host.isSuitableForVm(vm)){
//                        allocatedhost = host;
//                        break;
//                    }
//                }
//            }
//        }
//        if (allocatedhost == null ){
//            allocatedhost  = etaGreedy(qa, eta, vm, excludedHosts);
//        }
//        if (allocatedhost.isSuitableForVm(vm)){
//            return allocatedhost;
//        }
//        else{
//            allocatedhost  = etaGreedy(qa, eta, vm, excludedHosts);
//        }
//        return allocatedhost;
    }
    public PowerHost etaGreedy(HashMap<PowerHost, Double> qa, double eta, Vm vm, Set<? extends Host> excludedHosts){
        Random rand = new Random();
        Double maxValue = Double.NEGATIVE_INFINITY;
        int maxCount = 0;
        int totalCount = 0;
        PowerHost allocatedhost = null;
        LinkedList<PowerHost> actions = new LinkedList<PowerHost>();
        LinkedList<Double> probs = new LinkedList<Double>();
        for(PowerHost action : qa.keySet()){
//            if (!action.isSuitableForVm(vm)){
//                continue;
//            }
            totalCount++;
            Double currValue = (double)qa.get(action);
            // System.out.printf("%f vs. %f\n", currValue, maxValue);
            int compare = currValue.compareTo(maxValue);
            if(compare > 0){
                maxValue = currValue;
                maxCount = 1;
            }else if(compare == 0){
                // System.out.println("duplicate max");
                maxCount++;
            }
        }
        Double exploreProb = eta/totalCount;
        Double greedyProb = (1.0 - eta)/maxCount + exploreProb;
        Double oldProb = 0.0;
        // System.out.printf("eV: %f\n gV: %f\nmaxCount: %d\n max: %f\n", exploreValue, greedyValue, maxCount, max);
        for(PowerHost action : qa.keySet()){
//            if (!action.isSuitableForVm(vm)){
//                continue;
//            }
            Double currValue = (double)qa.get(action);
            if(currValue.compareTo(maxValue)==0){
                oldProb += greedyProb;
            }else{
                oldProb += exploreProb;
            }
            // System.out.printf("%f\n", oldValue);
            probs.add(oldProb);
            actions.add(action);
        }
        double r = rand.nextDouble();
        for(int i = 0; i < totalCount; i++){
            if(r < probs.get(i)){
                allocatedhost = actions.get(i);
            }
        }
        if (allocatedhost == null) {
            allocatedhost = actions.get(totalCount - 1);
        }
        if (allocatedhost.isSuitableForVm(vm)){
            return allocatedhost;
        }
        else {
            allocatedhost = getNewVmPlacementa(vm, excludedHosts);
        }
        if (allocatedhost.isSuitableForVm(vm)){
            return allocatedhost;
        }
        else {
            for (PowerHost host : this.<PowerHost>getHostList()){
                if (host.isSuitableForVm(vm)){
                    allocatedhost = host;
                    break;
                }
            }
        }
        return allocatedhost;
    }


    protected PowerHost getNewVmPlacementa(
            Vm vm,
            Set<? extends Host> excludedHosts){
        List<Map<String, Object>> migrationMap = new LinkedList<Map<String, Object>>();
        double Umin = Double.MAX_VALUE;
        PowerHost allocatedhost = null;
        for (PowerHost host : this.<PowerHost>getHostList()){
            if (excludedHosts.contains(host)) {
                continue;
            }
            boolean flag = true;
            double Akmip = host.getAvailableMips();
            double Xkmip = vm.getMips()*vm.getCurrentUtilizationOfCpu();
            double Pkmip = host.getTotalMips();
            if (Akmip + Xkmip > Pkmip){
                flag = false;
            }
//                double Akram = host.getAvailableRam();
////                double Xkram = vm.getRam();
////                double Pkram = host.getRam();
////                if (Akram + Xkram > Pkram){
////                    flag = false;
////                }
////                double Akbw = host.getAvailbleBw();
////                double Xkbw = vm.getBw();
////                double Pkbw = host.getBw();
////                if (Akbw + Xkbw > Pkbw){
////                    flag = false;
////                }
            int hostid;
            if (flag == true){
                double U = (Xkmip/Pkmip) ;//+ (Xkram/Pkram) + (Xkbw/Pkbw);
                if (U < Umin){
                    Umin = U;
                    allocatedhost = host;
                }
            }
        }
        Map<String, Object> migrate = new HashMap<String, Object>();
        migrate.put("vm", vm);
        migrate.put("host",allocatedhost);
        migrationMap.add(migrate);



        return allocatedhost;
    }


    public Double getMaxQAV(HashMap<PowerHost, Double> qa){
        Double maxValue = Double.NEGATIVE_INFINITY;
        Host maxAction = null;
        for(PowerHost action : qa.keySet()){
            Double currValue = qa.get(action);
            int compare = currValue.compareTo(maxValue);
            if(compare > 0){
                maxValue = currValue;
                maxAction = action;
            }
        }
        return maxValue;
    }
    List<PowerHostUtilizationHistory> overUtilizedHosts = getOverUtilizedHosts();
    //List<? extends Vm> vmsToMigrate = getVmsToMigrateFromHosts(overUtilizedHosts);
    List<PowerHost> switchedOffHosts = getSwitchedOffHosts();
    //List<PowerHost> excludedHosts = new LinkedList<PowerHost>();
    //List<PowerHost> underUtilizedHost =getUnderUtilizedHost(excludedHosts);


    int Ohostsum = overUtilizedHosts.size();
    //int Uhostsum = underUtilizedHost.size()；
    //int vmsum = vmsToMigrate.size();

//    Vm vms;
//    public String getState(){
//        return String.format("%d", vms);
//    }

    int index;
    double rew;
//    public VmState(int x){
//        reset();
//        length = x;
//
//    }

    public void reset(){
        index = 0;
    }

    public void action(Host host){
        index+=1;
        reward(host);
    }


    public void reward(Host host){

    }
    public double getpositive(double x){
        if (x >= 0){
        return x;}
        else {
            return -x;
        }
    }
    //此函数是计算整体总vm所需cpu占总host提供cpu得比例
    public double getratio(){
        Set<PowerHost> excludedHosts = new HashSet<PowerHost>();
        excludedHosts.addAll(overUtilizedHosts);
//        if (switchedOffHosts.size() != 800) {
//            excludedHosts.addAll(switchedOffHosts);
//        }
        //此处excludehost除外的主机里缺少欠载主机
        //List<PowerHost> underUtilizedHost =getUnderUtilizedHost(excludedHosts);
        double cpuhost = 0;
        double cpuvm = 0;
        for (PowerHost host1 : this.<PowerHost> getHostList()){
            if (excludedHosts.contains(host1)) {
                continue;
            }
            cpuhost += host1.getAvailableMips();
            for (Vm vm : host1.getVmList()){
                cpuvm += vm.getMips()*vm.getCurrentUtilizationOfCpu();
            }
        }
        return cpuvm/cpuhost;
    }


    public double getReward(Host host , int s, List<? extends Vm> vmsToMigrate){
        Vm vm = vmsToMigrate.get(s);
        double Rwas;
        if (host.vmCreate(vm)){
            double power = getPowerAfterAllocation((PowerHost) host, vm);
            double powerDiff = power - ((PowerHost) host).getPower();
            Rwas = (getpositive(host.getUtilizaionOfCpu() - host.getUtilizationOfRam()) + 0.0001)/(host.getUtilizaionOfCpu() + host.getUtilizationOfRam());
            double x = 1/Rwas;
            double cpuratiomin = vm.getMips()*vm.getCurrentUtilizationOfCpu()/host.getAvailableMips();
            double cpuratiomax = getratio();
            double a = getpositive(cpuratiomax-cpuratiomin);
            double y = 1/a;
            double zzz= host.getUtilizaionOfCpu();
            double z = 1/zzz;
            rew = 100*(1-host.getUtilizaionOfCpu())/powerDiff ;//+ (1/Rwas) + (1/getpositive(cpuratiomax-cpuratiomin)) + 0.00001*(1/host.getUtilizaionOfCpu());
        }
        else {
            rew = -100;
        }
        return rew;
    }

//    public boolean terminate(){
//        return (index >= vmsum);
//    }

    public int getState(){
        return (index);
    }






    public HashMap<Vm, HashMap<PowerHost, Double>> QLearning(double eta, double alpha, double gamma, int n, Set<? extends Host> excludedHosts,List<? extends Vm> vmsToMigrate){
        HashMap<Vm, HashMap<PowerHost, Double>> q = new HashMap<Vm, HashMap<PowerHost, Double>>();
        int vmsum = vmsToMigrate.size();
        int c = excludedHosts.size();
        // initialize Q arbitrarily
        for (Vm vm : vmsToMigrate){
            HashMap<PowerHost, Double> qa = new HashMap<PowerHost, Double>();
            for (PowerHost host : this.<PowerHost>getHostList()){
                if (excludedHosts.contains(host)){
                    continue;
                }
                double m = 1/(800 - c);
                qa.put(host,m);
            }
            q.put(vm, qa);
        }
        for(int i = 0; i < n; i++){
            reset();
            int s = getState();//初始化状态State
            int rs = 0;
                while (s < vmsum) {//括号内容是判断此状态是否超过需要迁移虚拟机的总数
                    Vm vmm = vmsToMigrate.get(s);
                    PowerHost a = getHost(q.get(vmm), eta, vmm, excludedHosts);//使用η策略将从Qtable中选择一个动作action
                    action(a);//使用该动作，然后，在该动作的结束之后，产生相关的奖励和更新Q-table然后，更新状态state
                    double r = getReward(a,s,vmsToMigrate);
                    int s_n = s+1;//获得下一状态
                    if (s_n == vmsum) {
                        s = s_n;
                        continue;
                    }
                    if (i > 130){
                        int m = 1;
                    }
                    HashMap<PowerHost, Double> qa = q.get(vmm);
                    if (!qa.containsKey(a)){
                        qa.put(a,r);
                    }
                    Double qav = qa.get(a) + alpha * (r + gamma * (getMaxQAV(q.get(vmsToMigrate.get(s_n)))) - qa.get(a));
                    qa.put(a, qav);
                    q.put(vmm, qa);
                    s = s_n;
                    rs += r;
                    // System.out.printf("%d: %s-%s %f\n", i, s, a, qav);
                }

//            if(i==(n-1)){
//                System.out.printf("%d\n",rs);
//            }else{
//                System.out.printf("%d, ",rs);
//            }
        }
        return q;
    }


    protected List<Map<String, Object>> getNewVmPlacement1(List<? extends Vm> vmsToMigrate, Set<? extends Host> excludedHosts){
        List<Map<String, Object>> migrationMap = new LinkedList<Map<String, Object>>();
        //关闭的主机
        List<PowerHost> switchedOffHosts = this.<PowerHost>getSwitchedOffHosts();
        //PowerVmList.sortByCpuUtilization(vmsToMigrate);
        for (Vm vm :vmsToMigrate){
            double minCriterion=Double.MAX_VALUE;
            Host allocatedHost = null;
            for (Host host :this.getHostList()){
                if ( excludedHosts.contains(host)) {
                    continue;
                }
                if ( switchedOffHosts.contains(host)) {
                    continue;
                }
                double dertaUtilizaiton  = 1 - ((PowerHost) host).getUtilizationOfCpu() - (vm.getCurrentUtilizationOfCpu() * vm.getMips()) / host.getTotalMips();
                if (dertaUtilizaiton > 0){
                    if (host.isSuitableForVm(vm)) {
                        double power = getPowerAfterAllocation((PowerHost) host, vm);
                        double powerDiff = power - ((PowerHost) host).getPower();
                        double rwas = (getpositive(host.getUtilizaionOfCpu() - host.getUtilizationOfRam()) + 0.0001)/(host.getUtilizaionOfCpu() + host.getUtilizationOfRam());
                        //double comparevalue = 0.288*(Math.exp(-powerDiff))+0.479*(1-host.getUtilizaionOfCpu())+0.059*rwas+0.174/host.getUtilizaionOfCpu();
                        HostDynamicWorkload host2 = (HostDynamicWorkload)host;
                        //double predictvalue =getpredictutilization(host2);
                        //HostDynamicWorkload host3 = (HostDynamicWorkload) host2;
                        double slatah = getSlatah(host2);
                        //double pdm = getSlaMetrics(vm);
                        double comparevalue = slatah;
                        if (comparevalue < minCriterion) {//谁大选谁
                            minCriterion = comparevalue;
                            allocatedHost = host;
                        }
                    }
                }

            }
            if (allocatedHost != null) {
                Log.printConcatLine("VM #", vm.getId(), " allocated to host #", allocatedHost.getId());
                Map<String, Object> migrate = new HashMap<String, Object>();
                migrate.put("vm", vm);
                migrate.put("host", allocatedHost);
                migrationMap.add(migrate);
            }
        }
        return migrationMap;
    }
    //计算主机的SLATAH值
    protected static double getSlatah(HostDynamicWorkload host) {
        double slaViolationTimePerHost = 0;
        double totalTime = 0;
        double previousTime = -1;
        double previousAllocated = 0;
        double previousRequested = 0;
        boolean previousIsActive = true;

        for (HostStateHistoryEntry entry : host.getStateHistory()) {
            if (previousTime != -1 && previousIsActive) {
                double timeDiff = entry.getTime() - previousTime;
                totalTime += timeDiff;
                if (previousAllocated < previousRequested) {
                    slaViolationTimePerHost += timeDiff;
                }
            }

            previousAllocated = entry.getAllocatedMips();
            previousRequested = entry.getRequestedMips();
            previousTime = entry.getTime();
            previousIsActive = entry.isActive();
        }


        return slaViolationTimePerHost / totalTime;
    }
    @Override
    protected List<Map<String, Object>> getNewVmPlacement(
            List<? extends Vm> vmsToMigrate,
            Set<? extends Host> excludedHosts){
        List<Map<String, Object>> migrationMap = new LinkedList<Map<String, Object>>();
        HashMap<Vm, HashMap<PowerHost, Double>> vmlast = QLearning(0.01, 0.5, 1.0, 1000, excludedHosts, vmsToMigrate);
        for (Vm vm : vmsToMigrate){
            Host allocatedhost = null;
            HashMap<PowerHost, Double> vmhashmap = vmlast.get(vm);
            double a = 0;

            for (Host hostt : vmhashmap.keySet()){
                if (vmhashmap.get(hostt) > a){
                    a = vmhashmap.get(hostt);
                }
            }
            for (Host host2 : vmhashmap.keySet()){
                if (vmhashmap.get(host2).equals(a)){
                    allocatedhost = host2;
                }
            }
            if (allocatedhost.isSuitableForVm(vm)){
            Map<String, Object> migrate = new HashMap<String, Object>();
            migrate.put("vm", vm);
            migrate.put("host",allocatedhost);
            migrationMap.add(migrate);
        }
            else {
                double Umin = Double.MAX_VALUE;
                for (PowerHost host : this.<PowerHost>getHostList()){
                    if (excludedHosts.contains(host)) {
                        continue;
                    }
                    boolean flag = true;
                    double Akmip = host.getAvailableMips();
                    double Xkmip = vm.getMips()*vm.getCurrentUtilizationOfCpu();
                    double Pkmip = host.getTotalMips();
                    if (Akmip + Xkmip > Pkmip){
                        flag = false;
                    }
//                double Akram = host.getAvailableRam();
////                double Xkram = vm.getRam();
////                double Pkram = host.getRam();
////                if (Akram + Xkram > Pkram){
////                    flag = false;
////                }
////                double Akbw = host.getAvailbleBw();
////                double Xkbw = vm.getBw();
////                double Pkbw = host.getBw();
////                if (Akbw + Xkbw > Pkbw){
////                    flag = false;
////                }
                    int hostid;
                    if (flag == true){
                        double U = (Xkmip/Pkmip) ;//+ (Xkram/Pkram) + (Xkbw/Pkbw);
                        if (U < Umin){
                            Umin = U;
                            allocatedhost = host;
                        }
                    }
                }

                Map<String, Object> migrate = new HashMap<String, Object>();
                migrate.put("vm", vm);
                migrate.put("host",allocatedhost);
                migrationMap.add(migrate);
            }
        }
        return migrationMap;

    }

    /**
     * Sets the safety parameter.
     *
     * @param safetyParameter the new safety parameter
     */
    protected void setSafetyParameter(double safetyParameter) {
        if (safetyParameter < 0) {
            Log.printConcatLine("The safety parameter cannot be less than zero. The passed value is: ",
                    safetyParameter);
            System.exit(0);
        }
        this.safetyParameter = safetyParameter;
    }
    /**
     * Sets the fallback vm allocation policy.
     *
     * @param fallbackVmAllocationPolicy the new fallback vm allocation policy
     */
    public void setFallbackVmAllocationPolicy(
            PowerVmAllocationPolicyMigrationAbstract fallbackVmAllocationPolicy) {
        this.fallbackVmAllocationPolicy = fallbackVmAllocationPolicy;
    }
}
