Most scalable way to choose something based on chance

In my game my NPC’s have characteristics like obese, strong, weak, religious etc…
I know how to add these characteristics to a NPC at random but what if i wanted there to be a 20% chance that the NPC spawns obese? I could use random integer in range between 1-100 and have 1-20 be obese but that creates problems once i want to add a new characteristic and have to manually scew the numbers to make Place for a new characteristic.

I understand if this is the only real solution besides weighted bool but ideally I would want to be able to set some characteristics to have locked numbers, and the ones that doesn’t share the percentages that hasn’t been taken.
So if i had 4 characteristics each having 20% chance to be chosen i want the rest to share the 20% that’s been left over equally. I also need to be able to change these numbers at runtime.

Basicaly what i’m looking for is the most scalable way to do this.

Edit: After some thinking, Could I use float inRange and through variables for example remove 10% from the first item and add that to other items without it being extremely complicated? Or if it would become really complicated have that math in a function like “increase chance” and have that take x number of characteristics to increae and 1 characteristic to decrease?

Edit2: While discussing this with a friend I said something that i realize could be the exact functionality that i need. A pie diagram. When you increase a value all other values shrink. I just need to be able to lock values as well.

My way might not be the best but it seems easier to make quick changes and additions both at design time and run time:

Create a struct or object class and name it NPCStats.

for each character stat like strength, religiousness etc, you create a 2Vector which is a pair of floats. The first component float is the lower range and the second is the upper range of your random number for that stat.

Each NPC has an NPCStats var they own, which cna be initialized how you want in the Constructor or maybe even at design time.

when you create the character, it loops through the Struct keys and accesses each one to find out the range of random float to use, and this way you only need on loop in one function to initialize them all with those semi random weights.

later during gameplay you
can modify the 2Vector of any struct key on any NPC. At least I think you can. I think I remember there being a blueprint node that does that.

Just keep track of whether youre using the struct for generating stats or using it as the stats themselves. I guess you could either way or even both with a little modification to my design.

1 Like

The problem that I see with weighted bool is that the things first in the “list” of characteristics will have a bigger chance than the things further down. A NPC can max have 3 unique characteistics so to reach further down it has to “survive” multiple 20% nodes and at that point that characteristic’s chance has been influenced by the ones above if you understand what I mean.

I’m sorry but you missunderstood me. They are characteristics not stats, they don’'t hold a value but simply a string/name. There’s no value to assign how obese the NPC is they are simply obese or they’re not. Thanks for the help anyway :slight_smile:

check out random bool with weight its basically what you need here. there is another method that allows multiple outcomes but i cant remember how its done off hand at the moment.

This math seems to be the what I need, where I can decide which characteristic to throw in and what percentage i want to increase it with. Just need an array for locked characteristics and not include them

I ended up using an array with 1000 elements where i can add and swap elements to change their chance. This way i can easily change something from 20% to 30% chance and choose which elements to decrease in chance.

Just got a easy way to do something like that, with any number of items, with different chances and any total chance. Example:

  • 1 item has 40% chance, the result is 1 to 40.

  • 1 item has 40% chance, the result is 41 to 80.

  • 1 item has 10% chance, the result is 81 to 91

Sum all the chance, total is 91. Make a random of 1 to 100 (or to 91 if you want 100% chance) and see what item is in the range of the number sorted.