Open this document in the playground · Download source
A loop builds a comparison, not a simulation
Part B · L08 · 5–10 minutes · Prerequisite: L07
The situation and question
For the same D&D 2014 ordinary ability check, keep DC 15 fixed and compare total bonuses +2 through +6. Which bonuses give at least a 50% success chance? Five useful rows are easier to read than a large grid of every imaginable DC.
Predict
Will each +1 help by the same amount here? What might happen when the chance reaches 0% or 100%?
Build
rows = [] starts an empty list. A for loop repeats its indented instructions
once for each value supplied by range. range(2, 7) supplies 2, 3, 4, 5, 6:
the starting value is included, but the ending value 7 is excluded.
The colon starts the loop body. Indentation (the spaces at the start of a line)
marks which instructions belong to it. Each repetition assigns a new value to
bonus. rows.append(...) adds one pair to the existing list: lists can be
changed. str(bonus) converts a whole number to text so "Bonus +" + str(bonus)
can make an accurate label. Here + joins two pieces of text, rather than adding
numbers. The final unindented output runs once, after the list is complete.
dc = 15
rows = []
for bonus in range(2, 7):
check = d(20) + bonus
label = "Bonus +" + str(bonus)
rows.append((label, check.p_ge(dc)))
output("Success by bonus at the chosen DC", prob_table(rows))
Success by bonus at the chosen DC · Table
| outcome | % | frac | X |
|---|---|---|---|
| Bonus +2 | 40.0 | 2/5 | 0.400 |
| Bonus +3 | 45.0 | 9/20 | 0.450 |
| Bonus +4 | 50.0 | 1/2 | 0.500 |
| Bonus +5 | 55.0 | 11/20 | 0.550 |
| Bonus +6 | 60.0 | 3/5 | 0.600 |
Run and read
The five rows are 40%, 45%, 50%, 55%, 60%. Bonuses +4, +5, and +6 reach at least half. Each step adds one successful natural face here, or five percentage points. This does not continue beyond certainty: success probabilities stay in 0–1 even when bonuses keep rising.
The loop performs five deterministic distribution calculations. It does not roll five random dice and estimate a success rate from that tiny sample.
Change one thing
Use range(0, 5) for bonuses +0 through +4. Check: the rows become 30%,
35%, 40%, 45%, 50%. Keep the range short enough that every row answers a useful
question. Moving output into the loop would produce multiple reports instead
of the single comparison we want.
Part B checkpoint: try it yourself
Starting from a blank script, compare skill values 40, 41, 42, 43, and 44 for one Call of Cthulhu 7e regular-difficulty check. Reuse L05's scope. Produce one labelled table and a sentence identifying which choices reach at least 42%.
Solution reasoning: use range(40, 45), calculate d(100).cdf(skill) for
each skill, append a labelled pair, then output the table after the loop. The
rows are 40% through 44%; 42, 43, and 44 meet the stated objective. There is no
need for functions, a second loop, or a simulated trial count.
What you now know
A loop automates a repeated calculation while keeping the question and labels clear. You can now construct a comparison report from inputs, not just edit a die size in a finished script.
Rules and model notes
D&D Basic Rules 2014, Using Ability Scores, Ability Checks, checked 2026-09-15. Bonuses include all applicable modifiers; this is not an attack, passive check, or a model of future character progression. The checkpoint uses Chaosium's 7th-edition Quick-Start Rules, Skill Rolls and Difficulty Levels, under L05's stated restrictions.
Where next
Previous: probability tables · Next: named outcomes. Part C asks which information a rule needs before you reduce its dice to a total. For a self-contained application, see the regular-check recipe.
Content ID: L08 · Review status: pilot
Prerequisites: L07
Rules review: source checked 2026-09-15; human review pending