private void SetComparisonLists(IList <ElectionModel> models)
        {
            for (int i = 0; i < models.Count; i++)
            {
                ElectionModel current = models[i];
                for (int j = i + 1; j < models.Count; j++)
                {
                    ElectionModel other = models[j];

                    bool currentBetter = IsBetter(current, other);
                    bool otherBetter   = IsBetter(other, current);

                    if (currentBetter)
                    {
                        current.SomewhatBetterThan.Add(other);
                        other.SomewhatWorseThan.Add(current);
                        if (!otherBetter)
                        {
                            current.AbsolutelyBetterThan.Add(other);
                            other.AbsolutelyWorseThan.Add(current);
                        }
                    }
                    if (otherBetter)
                    {
                        current.SomewhatWorseThan.Add(other);
                        other.SomewhatBetterThan.Add(current);
                        if (!currentBetter)
                        {
                            current.AbsolutelyWorseThan.Add(other);
                            other.AbsolutelyBetterThan.Add(current);
                        }
                    }
                }
            }
        }
        private bool HasBetterDesiredAbilities(ElectionModel model, ElectionModel other)
        {
            int  compensatedBySots    = 0;
            bool canCompensateBySlots = EnableSkillCompensation;
            var  extraSlots           = other.Equipment.Slots.ToList();

            foreach (int slot in model.Equipment.Slots)
            {
                if (extraSlots.Contains(slot))
                {
                    extraSlots.Remove(slot);
                }
                else
                {
                    canCompensateBySlots = false;
                }
            }

            foreach (IAbility desiredAbility in DesiredAbilities)
            {
                int currentLevels = 0;
                int otherLevels   = 0;

                if (model.DesiredAbilities.TryGetValue(desiredAbility.Skill.Id, out IAbility containedAbility))
                {
                    currentLevels = containedAbility.Level;
                }

                if (other.DesiredAbilities.TryGetValue(desiredAbility.Skill.Id, out IAbility otherContainedAbility))
                {
                    otherLevels = otherContainedAbility.Level;
                }

                int levelsMissing = currentLevels - otherLevels;

                if (levelsMissing > 0)
                {
                    if (canCompensateBySlots)
                    {
                        int currentCompensation = CompensateBySlots(desiredAbility, levelsMissing, extraSlots);
                        compensatedBySots += currentCompensation;
                        if (currentCompensation != 0)
                        {
                            continue;
                        }
                    }

                    return(true);
                }
            }

            if (model.DesiredSkillSum > other.DesiredSkillSum + compensatedBySots)
            {
                return(true);
            }

            return(false);
        }
        private bool HasBetterStats(ElectionModel model, ElectionModel other)
        {
            if (model.Equipment.Type == EquipmentType.Charm)
            {
                return(false);
            }
            var armorPiece = (IArmorPiece)model.Equipment;
            var otherPiece = (IArmorPiece)other.Equipment;

            if (armorPiece.Defense.Augmented > otherPiece.Defense.Augmented)
            {
                return(true);
            }

            if (armorPiece.Defense.Max > otherPiece.Defense.Max)
            {
                return(true);
            }

            if (armorPiece.Defense.Max > otherPiece.Defense.Max)
            {
                return(true);
            }

            if (armorPiece.Resistances.Fire > otherPiece.Resistances.Fire)
            {
                return(true);
            }

            if (armorPiece.Resistances.Thunder > otherPiece.Resistances.Thunder)
            {
                return(true);
            }

            if (armorPiece.Resistances.Dragon > otherPiece.Resistances.Dragon)
            {
                return(true);
            }

            if (armorPiece.Resistances.Ice > otherPiece.Resistances.Ice)
            {
                return(true);
            }

            if (armorPiece.Resistances.Water > otherPiece.Resistances.Water)
            {
                return(true);
            }

            if (armorPiece.Rarity < otherPiece.Rarity)
            {
                return(true);
            }

            return(false);
        }
 private bool HasBetterSlotEfficiency(ElectionModel model, ElectionModel other)
 {
     foreach (KeyValuePair <int, int> efficiencyPair in model.SkillEfficiencies)
     {
         int skillId         = efficiencyPair.Key;
         int efficiency      = efficiencyPair.Value;
         int otherEfficiency = other.SkillEfficiencies[skillId];
         if (efficiency > otherEfficiency)
         {
             return(true);
         }
     }
     return(false);
 }
        private bool IsBetter(ElectionModel model, ElectionModel other)
        {
            if (IsBetterByNonStats(model, other))
            {
                return(true);
            }

            if (!IsBetterByNonStats(other, model))
            {
                if (HasBetterStats(model, other))
                {
                    return(true);
                }
            }

            return(false);
        }
        private bool IsBetterByNonStats(ElectionModel model, ElectionModel other)
        {
            if (!model.FullSet && other.FullSet)
            {
                return(true);
            }

            if (HasBetterSlotEfficiency(model, other))
            {
                return(true);
            }

            if (HasBetterDesiredAbilities(model, other))
            {
                return(true);
            }

            return(false);
        }