Optimise resource allocation across programmes
The problem
You run multiple programmes and need to decide how to allocate limited staff time, budget, and other resources. Currently allocation is based on historical precedent or gut feel, but you're not sure if you're maximising impact. Which programmes should get more resources? Which should scale back?
The solution
Use optimisation algorithms to model different allocation scenarios based on your constraints (budget, staff capacity) and objectives (maximising beneficiaries reached, impact per £, strategic priorities). The model helps you explore trade-offs systematically and find allocations you wouldn't have considered intuitively.
What you get
A recommended resource allocation across programmes that maximises your defined objective (e.g., total impact score, beneficiaries reached) within constraints (budget, staff time). Scenario comparison showing trade-offs. Sensitivity analysis showing how allocation changes if constraints or priorities shift. Decision support, not autopilot - human judgement still required.
Before you start
- Clear data on resource requirements for each programme (staff time, budget)
- Measurable outputs or outcomes for each programme (beneficiaries, impact metrics)
- Defined constraints (total budget, total staff capacity, minimum levels)
- Agreement on what "better allocation" means for your organisation
- Basic understanding of linear programming concepts (or willingness to learn)
When to use this
- Running 3+ programmes competing for limited resources
- Resource allocation decisions have significant impact on total reach
- Current allocation feels sub-optimal but unclear how to improve it
- Need to model impact of budget cuts or new funding on programme mix
- Want to explore scenarios systematically rather than one-at-a-time
When not to use this
- Programmes are fully ring-fenced (no flexibility to reallocate)
- Impact across programmes is not comparable (apples and oranges)
- Political or strategic reasons override optimization (some programmes untouchable)
- Resource requirements and outcomes are highly unpredictable
- Only 1-2 programmes (simple enough to evaluate manually)
Steps
- 1
Define your objective function
What are you trying to maximise? Options: (a) Total beneficiaries reached, (b) Impact score per £ spent, (c) Weighted combination of strategic priorities, (d) Contribution to specific outcomes. Be explicit. This will drive the optimisation. Get leadership agreement on what success looks like mathematically.
- 2
Gather data on each programme
For each programme, collect: (1) Resource requirements (staff FTE, budget), (2) Outputs/outcomes delivered per resource unit (e.g., beneficiaries per £10k), (3) Current allocation levels, (4) Minimum viable levels (can't go below this), (5) Maximum scalable levels (can't go above this). Historical data is fine for initial model.
- 3
Define your constraints
List all constraints: (1) Total budget available, (2) Total staff capacity (FTE), (3) Minimum allocation per programme (strategic commitments), (4) Maximum allocation per programme (capacity limits), (5) Other constraints (geographic coverage, funder restrictions). Constraints define what's feasible.
- 4
Build optimisation model (Python PuLP)
Define decision variables (allocation to each programme), objective function (what to maximise), and constraints (what must be satisfied). Use PuLP to solve. The solver finds the allocation that maximises objective while satisfying all constraints. Start simple - you can add complexity later.
- 5
Build optimisation model (Excel Solver)(optional)
Set up spreadsheet with: programmes in rows, current allocation and optimised allocation in columns, objective function calculation, constraint formulas. Use Solver add-in to optimise. Easier for non-programmers but less flexible than Python for complex scenarios.
- 6
Validate results make sense
Review recommended allocation. Does it make strategic sense? Are there obvious issues? Check edge cases: What if a constraint is slightly different? Is the model exploiting loopholes in how you defined things? Adjust objective or constraints if needed. Optimisation finds what you asked for, not necessarily what you meant.
- 7
Run scenario analysis
Model key scenarios: (1) 10% budget cut - what gives?, (2) New £50k grant - where to allocate?, (3) Lose key staff member - impact on mix?, (4) Change strategic priorities - new allocation?. Show leadership trade-offs. This is where optimisation adds real value - exploring scenarios quickly.
- 8
Present recommendations with caveats
Present: (1) Current allocation, (2) Optimised allocation, (3) Impact difference, (4) Key trade-offs, (5) Scenario results. Emphasise: This is decision support showing what's mathematically optimal given assumptions. Human judgement needed on strategic fit, feasibility, stakeholder impact. Don't outsource the decision to the algorithm.
Example code
Resource allocation optimisation with PuLP
Linear programming model to find optimal resource allocation across programmes that maximises total impact within budget and staff constraints.
import pulp
# Define programmes and their characteristics
programmes = ['Youth Mentoring', 'Skills Training', 'Counselling', 'Outreach']
# Resource required per unit (e.g., per 10 beneficiaries)
budget_per_unit = {
'Youth Mentoring': 5000,
'Skills Training': 8000,
'Counselling': 12000,
'Outreach': 3000
}
staff_time_per_unit = { # FTE months per unit
'Youth Mentoring': 0.5,
'Skills Training': 1.0,
'Counselling': 1.5,
'Outreach': 0.3
}
# Impact score per unit (higher is better)
impact_per_unit = {
'Youth Mentoring': 8,
'Skills Training': 10,
'Counselling': 12,
'Outreach': 5
}
# Constraints
total_budget = 150000 # £150k available
total_staff_capacity = 15 # FTE months
min_units = {p: 1 for p in programmes} # At least 1 unit of each
max_units = {p: 10 for p in programmes} # Maximum 10 units of each
# Create optimisation problem
prob = pulp.LpProblem("Programme_Allocation", pulp.LpMaximize)
# Decision variables: how many units to allocate to each programme
allocation = {
p: pulp.LpVariable(f"units_{p}", lowBound=min_units[p], upBound=max_units[p], cat='Integer')
for p in programmes
}
# Objective: Maximise total impact
prob += pulp.lpSum([allocation[p] * impact_per_unit[p] for p in programmes]), "Total_Impact"
# Budget constraint
prob += pulp.lpSum([allocation[p] * budget_per_unit[p] for p in programmes]) <= total_budget, "Budget_Limit"
# Staff capacity constraint
prob += pulp.lpSum([allocation[p] * staff_time_per_unit[p] for p in programmes]) <= total_staff_capacity, "Staff_Limit"
# Solve
prob.solve()
# Display results
print(f"Status: {pulp.LpStatus[prob.status]}")
print(f"\nOptimized Allocation:")
print(f"Total Impact: {pulp.value(prob.objective):.0f}")
print()
for p in programmes:
units = allocation[p].varValue
print(f"{p}: {units:.0f} units")
print(f" Budget: £{units * budget_per_unit[p]:,.0f}")
print(f" Staff: {units * staff_time_per_unit[p]:.1f} FTE months")
print(f" Impact: {units * impact_per_unit[p]:.0f}")
print()
# Check constraint usage
total_budget_used = sum(allocation[p].varValue * budget_per_unit[p] for p in programmes)
total_staff_used = sum(allocation[p].varValue * staff_time_per_unit[p] for p in programmes)
print(f"Budget used: £{total_budget_used:,.0f} / £{total_budget:,.0f}")
print(f"Staff used: {total_staff_used:.1f} / {total_staff_capacity} FTE months")Tools
Resources
Official documentation for the PuLP optimisation library.
Introduction to linear programmingtutorialBeginner-friendly introduction to optimisation with Python.
Excel Solver tutorialtutorialHow to use Excel Solver for optimisation problems.
Resource allocation in nonprofitspaperAcademic perspective on quantitative approaches to charity resource allocation.
At a glance
- Time to implement
- days
- Setup cost
- free
- Ongoing cost
- free
- Cost trend
- stable
- Organisation size
- small, medium, large
- Target audience
- operations-manager, ceo-trustees, program-delivery
All tools are free. Time cost: 2-3 days initial model build, then 2-4 hours per planning cycle to update and run scenarios.