Skip to content

Commit

Permalink
fixed topness calculation for negative weights
Browse files Browse the repository at this point in the history
  • Loading branch information
cadon committed Feb 4, 2024
1 parent 8e4d97b commit de1fffb
Show file tree
Hide file tree
Showing 6 changed files with 99 additions and 71 deletions.
23 changes: 8 additions & 15 deletions ARKBreedingStats/BreedingPlanning/BreedingPlan.cs
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ public partial class BreedingPlan : UserControl
private bool[] _enabledColorRegions;
private TimeSpan _incubationTime;
private Creature _chosenCreature;
private BreedingMode _breedingMode;
private BreedingScore.BreedingMode _breedingMode;
public readonly StatWeighting StatWeighting;
public bool BreedingPlanNeedsUpdate;
private bool _speciesInfoNeedsUpdate;
Expand All @@ -76,7 +76,7 @@ public BreedingPlan()
for (int i = 0; i < Stats.StatsCount; i++)
_statWeights[i] = 1;

_breedingMode = BreedingMode.TopStatsConservative;
_breedingMode = BreedingScore.BreedingMode.TopStatsConservative;

_breedingPairs = new List<BreedingPair>();
pedigreeCreatureBest.SetIsVirtual(true);
Expand Down Expand Up @@ -289,7 +289,7 @@ private void DoCalculateBreedingScoresAndDisplayPairs()

// only consider creatures with top stats if breeding for that
Creature[] females, males;
if (_breedingMode == BreedingMode.BestNextGen)
if (_breedingMode == BreedingScore.BreedingMode.BestNextGen)
{
females = _females;
males = _males;
Expand Down Expand Up @@ -538,7 +538,7 @@ private void DoCalculateBreedingScoresAndDisplayPairs()
SetParents(0);

// if breeding mode is conservative and a creature with top-stats already exists, the scoring might seem off
if (_breedingMode == BreedingMode.TopStatsConservative)
if (_breedingMode == BreedingScore.BreedingMode.TopStatsConservative)
{
bool bestCreatureAlreadyAvailable = true;
Creature bestCreature = null;
Expand Down Expand Up @@ -852,7 +852,7 @@ private void SetParents(int comboIndex)
crW.Father = father;
double probabilityBest = 1;
bool totalLevelUnknown = false; // if stats are unknown, total level is as well (==> oxygen, speed)
bool topStatBreedingMode = _breedingMode == BreedingMode.TopStatsConservative || _breedingMode == BreedingMode.TopStatsLucky;
bool topStatBreedingMode = _breedingMode == BreedingScore.BreedingMode.TopStatsConservative || _breedingMode == BreedingScore.BreedingMode.TopStatsLucky;
for (int s = 0; s < Stats.StatsCount; s++)
{
if (s == Stats.Torpidity) continue;
Expand Down Expand Up @@ -996,7 +996,7 @@ private void radioButtonBPTopStatsCn_CheckedChanged(object sender, EventArgs e)
{
if (rbBPTopStatsCn.Checked)
{
_breedingMode = BreedingMode.TopStatsConservative;
_breedingMode = BreedingScore.BreedingMode.TopStatsConservative;
CalculateBreedingScoresAndDisplayPairs();
}
}
Expand All @@ -1005,7 +1005,7 @@ private void radioButtonBPTopStats_CheckedChanged(object sender, EventArgs e)
{
if (rbBPTopStats.Checked)
{
_breedingMode = BreedingMode.TopStatsLucky;
_breedingMode = BreedingScore.BreedingMode.TopStatsLucky;
CalculateBreedingScoresAndDisplayPairs();
}
}
Expand All @@ -1014,7 +1014,7 @@ private void radioButtonBPHighStats_CheckedChanged(object sender, EventArgs e)
{
if (rbBPHighStats.Checked)
{
_breedingMode = BreedingMode.BestNextGen;
_breedingMode = BreedingScore.BreedingMode.BestNextGen;
CalculateBreedingScoresAndDisplayPairs();
}
}
Expand Down Expand Up @@ -1108,13 +1108,6 @@ public bool IgnoreSexInBreedingPlan
set => CbIgnoreSexInPlanning.Checked = value;
}

public enum BreedingMode
{
BestNextGen,
TopStatsLucky,
TopStatsConservative
}

private void cbTagExcludeDefault_CheckedChanged(object sender, EventArgs e)
{
CalculateBreedingScoresAndDisplayPairs();
Expand Down
15 changes: 11 additions & 4 deletions ARKBreedingStats/BreedingPlanning/BreedingScore.cs
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ public static class BreedingScore
/// <param name="anyOddEven">Array for each stat if the higher level should be considered for score: 0: consider any level, 1: consider only if odd, 2: consider only if even.</param>
/// <returns></returns>
public static List<BreedingPair> CalculateBreedingScores(Creature[] females, Creature[] males, Species species,
short[] bestPossLevels, double[] statWeights, int[] bestLevelsOfSpecies, BreedingPlan.BreedingMode breedingMode,
short[] bestPossLevels, double[] statWeights, int[] bestLevelsOfSpecies, BreedingMode breedingMode,
bool considerChosenCreature, bool considerMutationLimit, int mutationLimit,
ref bool creaturesMutationsFilteredOut, int offspringLevelLimit = 0, bool downGradeOffspringWithLevelHigherThanLimit = false,
bool onlyBestSuggestionForFemale = false, byte[] anyOddEven = null)
Expand Down Expand Up @@ -111,7 +111,7 @@ public static List<BreedingPair> CalculateBreedingScores(Creature[] females, Cre
double weightedExpectedStatLevel = statWeights[s] * (Ark.ProbabilityInheritHigherLevel * higherLevel + Ark.ProbabilityInheritLowerLevel * lowerLevel) / 40;
if (weightedExpectedStatLevel != 0)
{
if (breedingMode == BreedingPlan.BreedingMode.TopStatsLucky)
if (breedingMode == BreedingMode.TopStatsLucky)
{
if (!ignoreTopStats && (female.levelsWild[s] == bestLevelsOfSpecies[s] || male.levelsWild[s] == bestLevelsOfSpecies[s]))
{
Expand All @@ -121,7 +121,7 @@ public static List<BreedingPair> CalculateBreedingScores(Creature[] females, Cre
else if (bestLevelsOfSpecies[s] > 0)
weightedExpectedStatLevel *= .01;
}
else if (breedingMode == BreedingPlan.BreedingMode.TopStatsConservative && bestLevelsOfSpecies[s] > 0)
else if (breedingMode == BreedingMode.TopStatsConservative && bestLevelsOfSpecies[s] > 0)
{
bool higherIsBetter = statWeights[s] >= 0;
bestPossLevels[s] = (short)(higherIsBetter ? Math.Max(female.levelsWild[s], male.levelsWild[s]) : Math.Min(female.levelsWild[s], male.levelsWild[s]));
Expand All @@ -140,7 +140,7 @@ public static List<BreedingPair> CalculateBreedingScores(Creature[] females, Cre
}
}

if (breedingMode == BreedingPlan.BreedingMode.TopStatsConservative)
if (breedingMode == BreedingMode.TopStatsConservative)
{
if (topStatsMother < offspringPotentialTopStatCount && topStatsFather < offspringPotentialTopStatCount)
t += offspringExpectedTopStatCount;
Expand Down Expand Up @@ -274,5 +274,12 @@ public static int GetHigherBestLevel(int level1, int level2, byte anyOddEven)
default: return Math.Max(level1, level2);
}
}

public enum BreedingMode
{
BestNextGen,
TopStatsLucky,
TopStatsConservative
}
}
}
121 changes: 74 additions & 47 deletions ARKBreedingStats/Form1.library.cs
Original file line number Diff line number Diff line change
Expand Up @@ -316,8 +316,14 @@ private void CalculateTopStats(List<Creature> creatures)
}
List<Creature>[] bestCreaturesWildLevels = new List<Creature>[Stats.StatsCount];
List<Creature>[] bestCreaturesMutatedLevels = new List<Creature>[Stats.StatsCount];
int usedStatsCount = usedStatIndices.Count;
int usedAndConsideredStatsCount = usedAndConsideredStatIndices.Count;
var statPreferences = new StatWeighting.StatValuePreference[Stats.StatsCount];
for (int s = 0; s < Stats.StatsCount; s++)
{
var statWeight = statWeights.Item1[s];
statPreferences[s] = statWeight > 0 ? StatWeighting.StatValuePreference.High :
statWeight < 0 ? StatWeighting.StatValuePreference.Low :
StatWeighting.StatValuePreference.Indifferent;
}

foreach (var c in speciesCreatures)
{
Expand All @@ -341,77 +347,80 @@ private void CalculateTopStats(List<Creature> creatures)
continue;
}

for (int s = 0; s < usedStatsCount; s++)
foreach (var s in usedStatIndices)
{
int si = usedStatIndices[s];
var statWeight = statWeights.Item1[s];
var statPreference = statWeight > 0 ? StatWeighting.StatValuePreference.High :
statWeight < 0 ? StatWeighting.StatValuePreference.Low :
StatWeighting.StatValuePreference.Indifferent;

if (c.levelsWild[si] >= 0)
if (c.levelsWild[s] >= 0)
{
if (statPreference == StatWeighting.StatValuePreference.Low)
if (statPreferences[s] == StatWeighting.StatValuePreference.Low)
{
if (lowestLevels[si] == -1 || c.levelsWild[si] < lowestLevels[si])
if (lowestLevels[s] == -1 || c.levelsWild[s] < lowestLevels[s])
{
bestCreaturesWildLevels[si] = new List<Creature> { c };
lowestLevels[si] = c.levelsWild[si];
bestCreaturesWildLevels[s] = new List<Creature> { c };
lowestLevels[s] = c.levelsWild[s];
}
else if (c.levelsWild[si] == lowestLevels[si])
else if (c.levelsWild[s] == lowestLevels[s])
{
bestCreaturesWildLevels[si].Add(c);
bestCreaturesWildLevels[s].Add(c);
}

if (c.levelsWild[s] > highestLevels[s])
{
highestLevels[s] = c.levelsWild[s];
}
}
else if (statPreference == StatWeighting.StatValuePreference.High)
else if (statPreferences[s] == StatWeighting.StatValuePreference.High)
{
if (c.levelsWild[si] > highestLevels[si])
if (c.levelsWild[s] > highestLevels[s])
{
// creature has a higher level than the current highest level
// check if highest stats are only counted if odd or even
if ((statWeights.Item2?[s] ?? 0) == 0 // even/odd doesn't matter
|| (statWeights.Item2[s] == 1 && c.levelsWild[si] % 2 == 1)
|| (statWeights.Item2[s] == 2 && c.levelsWild[si] % 2 == 0)
|| (statWeights.Item2[s] == 1 && c.levelsWild[s] % 2 == 1)
|| (statWeights.Item2[s] == 2 && c.levelsWild[s] % 2 == 0)
)
{
bestCreaturesWildLevels[si] = new List<Creature> { c };
highestLevels[si] = c.levelsWild[si];
bestCreaturesWildLevels[s] = new List<Creature> { c };
highestLevels[s] = c.levelsWild[s];
}
}
else if (c.levelsWild[si] == highestLevels[si])
else if (c.levelsWild[s] == highestLevels[s])
{
bestCreaturesWildLevels[s].Add(c);
}
if (lowestLevels[s] == -1 || c.levelsWild[s] < lowestLevels[s])
{
bestCreaturesWildLevels[si].Add(c);
lowestLevels[s] = c.levelsWild[s];
}
}
}

if (c.levelsMutated != null && c.levelsMutated[si] >= 0)
if (c.levelsMutated != null && c.levelsMutated[s] >= 0)
{
if (statPreference == StatWeighting.StatValuePreference.Low)
if (statPreferences[s] == StatWeighting.StatValuePreference.Low)
{
if (c.levelsMutated[si] < lowestMutationLevels[si])
if (c.levelsMutated[s] < lowestMutationLevels[s])
{
bestCreaturesMutatedLevels[si] = new List<Creature> { c };
lowestMutationLevels[si] = c.levelsMutated[si];
bestCreaturesMutatedLevels[s] = new List<Creature> { c };
lowestMutationLevels[s] = c.levelsMutated[s];
}
else if (c.levelsMutated[si] == lowestMutationLevels[si])
else if (c.levelsMutated[s] == lowestMutationLevels[s])
{
if (bestCreaturesMutatedLevels[si] == null)
bestCreaturesMutatedLevels[si] = new List<Creature> { c };
else bestCreaturesMutatedLevels[si].Add(c);
if (bestCreaturesMutatedLevels[s] == null)
bestCreaturesMutatedLevels[s] = new List<Creature> { c };
else bestCreaturesMutatedLevels[s].Add(c);
}
}
else if (statPreference == StatWeighting.StatValuePreference.High
&& c.levelsMutated[si] > 0)
else if (statPreferences[s] == StatWeighting.StatValuePreference.High
&& c.levelsMutated[s] > 0)
{
if (c.levelsMutated[si] > 0 && c.levelsMutated[si] > highestMutationLevels[si])
if (c.levelsMutated[s] > 0 && c.levelsMutated[s] > highestMutationLevels[s])
{
bestCreaturesMutatedLevels[si] = new List<Creature> { c };
highestMutationLevels[si] = c.levelsMutated[si];
bestCreaturesMutatedLevels[s] = new List<Creature> { c };
highestMutationLevels[s] = c.levelsMutated[s];
}
else if (c.levelsMutated[si] == highestMutationLevels[si])
else if (c.levelsMutated[s] == highestMutationLevels[s])
{
bestCreaturesMutatedLevels[si].Add(c);
bestCreaturesMutatedLevels[s].Add(c);
}
}
}
Expand All @@ -427,22 +436,40 @@ private void CalculateTopStats(List<Creature> creatures)

// set topness of each creature (== mean wildLevels/mean top wildLevels in permille)
int sumTopLevels = 0;
for (int s = 0; s < usedAndConsideredStatsCount; s++)
foreach (var s in usedAndConsideredStatIndices)
{
int si = usedAndConsideredStatIndices[s];
if (highestLevels[si] > 0)
sumTopLevels += highestLevels[si];
switch (statPreferences[s])
{
case StatWeighting.StatValuePreference.Indifferent:
continue;
case StatWeighting.StatValuePreference.Low:
if (highestLevels[s] > 0 && lowestLevels[s] != 0)
sumTopLevels += highestLevels[s] - lowestLevels[s];
break;
case StatWeighting.StatValuePreference.High:
if (highestLevels[s] > 0)
sumTopLevels += highestLevels[s];
break;
}
}
if (sumTopLevels > 0)
{
foreach (var c in speciesCreatures)
{
if (c.levelsWild == null || c.flags.HasFlag(CreatureFlags.Placeholder)) continue;
int sumCreatureLevels = 0;
for (int s = 0; s < usedAndConsideredStatsCount; s++)
foreach (var s in usedAndConsideredStatIndices)
{
int si = usedAndConsideredStatIndices[s];
sumCreatureLevels += c.levelsWild[si] > 0 ? c.levelsWild[si] : 0;
switch (statPreferences[s])
{
case StatWeighting.StatValuePreference.Low:
if (c.levelsWild[s] >= 0)
sumCreatureLevels += highestLevels[s] - c.levelsWild[s];
break;
case StatWeighting.StatValuePreference.High:
sumCreatureLevels += c.levelsWild[s] > 0 ? c.levelsWild[s] : 0;
break;
}
}
c.topness = (short)(1000 * sumCreatureLevels / sumTopLevels);
}
Expand Down
1 change: 1 addition & 0 deletions ARKBreedingStats/library/Creature.cs
Original file line number Diff line number Diff line change
Expand Up @@ -419,6 +419,7 @@ public Creature Mother
motherGuid = mother?.guid ?? Guid.Empty;
}
}

public Creature Father
{
get => father;
Expand Down
2 changes: 1 addition & 1 deletion ARKBreedingStats/library/DummyCreatures.cs
Original file line number Diff line number Diff line change
Expand Up @@ -244,7 +244,7 @@ private static List<Creature> BreedCreatures(Creature[] creatures, Species speci
var allCreaturesArray = noGender ? allCreatures.ToArray() : null;
var pairs = BreedingScore.CalculateBreedingScores(noGender ? allCreaturesArray : femalesMales[Sex.Female].ToArray(),
noGender ? allCreaturesArray : femalesMales[Sex.Male].ToArray(), species, bestPossibleLevels, statWeights, bestLevels,
BreedingPlan.BreedingMode.TopStatsConservative, false, false, 0, ref filteredOutByMutationLimit);
BreedingScore.BreedingMode.TopStatsConservative, false, false, 0, ref filteredOutByMutationLimit);

var pairsCount = Math.Min(usePairsPerGeneration, pairs.Count);
for (int i = 0; i < pairsCount; i++)
Expand Down
8 changes: 4 additions & 4 deletions ARKBreedingStats/uiControls/StatWeighting.cs
Original file line number Diff line number Diff line change
Expand Up @@ -392,8 +392,8 @@ private void SetState(byte state)
public enum StatValuePreference
{
Indifferent,
High,
Low
Low,
High
}

/// <summary>
Expand All @@ -402,8 +402,8 @@ public enum StatValuePreference
public enum StatValueEvenOdd
{
Indifferent,
Even,
Odd
Odd,
Even
}
}
}

0 comments on commit de1fffb

Please sign in to comment.