Greedy Choice and Proof
Lesson 41Advanced58 minAssessment-backed

Greedy Choice and Proof

Use local choices only when an exchange argument or invariant proves they cannot block the optimal answer.

What you will be able to do

Explain when greedy is valid and when it is just wishful thinking.
Use exchange arguments and invariants to defend local choices.
Solve canonical greedy problems across intervals, jumps, and resource allocation.
Reject greedy when future constraints require DP or search.
Communicate greedy correctness in assessment-grade language.

Greedy algorithms make the locally best-looking choice and never revisit it. That is powerful only when you can prove the local choice is safe.

Safe Local Choice

A greedy choice is valid when any optimal solution can be transformed to include that choice without making the result worse. That proof shape is called an exchange argument.

Greedy exchange argument
Greedy is not a vibe. It needs a safety proof.

Scenario: Rate-Limit Budget

An API gateway has limited retry budget. Choosing the cheapest recovery action first can be valid if every action has independent benefit and no future dependency. If actions unlock each other, greedy can fail and stateful optimization may be required.

QuestionGreedy signalRisk
Activity selectionEarliest finish leaves maximum roomSorting by start fails.
Jump game reachabilityTrack farthest reachable indexDo not simulate every path.
Fractional allocationBest value per unit is safe0/1 allocation is different.
Dependent choicesNo safe exchangeLikely DP/backtracking.
Local choice leading to global optimum
A local choice is useful only when it preserves global optimality.

Same Pattern in Java, Python, and JavaScript

Activity selection: choose the meeting that ends earliest, then repeat among compatible meetings.

import java.util.*;

class ActivitySelection {
    static int maxMeetings(int[][] intervals) {
        Arrays.sort(intervals, Comparator.comparingInt(a -> a[1]));
        int count = 0, end = Integer.MIN_VALUE;
        for (int[] in : intervals) {
            if (in[0] >= end) { count++; end = in[1]; }
        }
        return count;
    }
}

Assessment trap

Never answer 'sort and greedily choose' without proving why the chosen ordering is safe.

Interview signalFrequently Asked Interview Questions

These are canonical interview patterns for this topic, phrased as concrete problem statements. They avoid vague theory questions and prepare you for the exact reasoning interviewers expect: invariant, edge cases, complexity, and trade-off.

  • Return the maximum number of non-overlapping intervals.
  • Return whether the last index is reachable.
  • Return a station index that completes the circuit, or -1.

Production practiceCompany-Style Practice Examples

These are not claimed as exact company-specific questions. They are the interview patterns repeatedly used by product companies to test whether you can move from brute force to a defensible implementation.

ExampleBrute-force approachStronger solutionProduction notes
Ad-slot allocationPick highest price first blindly.Use greedy only when exchange proof holds for the objective.Dependencies or quotas may require DP/flow.
Maintenance schedulingSort by earliest finish for max compatible windows.Earliest finish preserves maximum future capacity.Tie policy must be deterministic.
Retry budgetSpend budget on largest request first.Use ratio/priority only when partial or independent choices make it safe.0/1 choices often break greedy.

Solved modelInterview Question Solutions

Question 1: Activity Selection

Return the maximum number of non-overlapping intervals. Sort by finish time. The exchange proof is that choosing the earliest compatible finish never leaves fewer future options than any later-finishing compatible choice.

import java.util.*;

class ActivitySelection {
    static int maxMeetings(int[][] intervals) {
        Arrays.sort(intervals, Comparator.comparingInt(a -> a[1]));
        int count = 0, end = Integer.MIN_VALUE;
        for (int[] in : intervals) {
            if (in[0] >= end) { count++; end = in[1]; }
        }
        return count;
    }
}

Question 2: Jump Game

Return whether the last index is reachable. Track the farthest reachable index while scanning. If the scan reaches an index beyond farthest, there is a gap no previous choice can cross.

class JumpGame { static boolean canJump(int[] nums) { int farthest = 0; for (int i = 0; i < nums.length; i++) { if (i > farthest) return false; farthest = Math.max(farthest, i + nums[i]); } return true; } }

Question 3: Gas Station

Return a station index that completes the circuit, or -1. If total gas is below total cost, no answer exists. When the running tank becomes negative at i, every candidate since the last start also fails, so restart at i + 1.

class GasStation { static int canCompleteCircuit(int[] gas, int[] cost) { int total = 0, tank = 0, start = 0; for (int i = 0; i < gas.length; i++) { int diff = gas[i] - cost[i]; total += diff; tank += diff; if (tank < 0) { start = i + 1; tank = 0; } } return total >= 0 ? start : -1; } }

Solved modelWorked Interview Answer

Select the maximum number of non-overlapping meetings. Sort by finish time. The earliest finishing compatible meeting leaves the most room for all future choices, which is the exchange argument.

import java.util.*;

class ActivitySelection {
    static int maxMeetings(int[][] intervals) {
        Arrays.sort(intervals, Comparator.comparingInt(a -> a[1]));
        int count = 0, end = Integer.MIN_VALUE;
        for (int[] in : intervals) {
            if (in[0] >= end) { count++; end = in[1]; }
        }
        return count;
    }
}

Hands-on drillTry It Yourself

Practice task

For five intervals, sort by start, duration, and finish. Identify which ordering is safe for maximum non-overlapping meetings and prove it.

Failure patternsCommon Mistakes to Avoid

  • Using greedy without proof.
  • Sorting by intuitive but unsafe keys.
  • Confusing local optimum with global optimum.
  • Using greedy for 0/1 choices that need DP.
  • Not stating exchange argument.

Execution guardrailQuick-Start Checklist

  • Name local choice.
  • State invariant.
  • Prove exchange safety.
  • Show progress.
  • Handle ties.
  • State complexity.

Recall drillKnowledge Check

QuestionStrong answer
What is exchange argument?A proof that an optimal solution can be transformed to include the greedy choice.
When does greedy fail?When local choice can block a better future combination.
Why earliest finish for activities?It leaves the most remaining timeline.

VocabularyKey Terms

TermMeaning
Greedy choiceIrrevocable local decision.
InvariantCondition preserved after each choice.
Exchange argumentProof replacing part of an optimal solution safely.
CounterexampleInput showing a greedy rule fails.

Next practiceFurther Reading

  • Practice activity selection, jump game, gas station, and task scheduler.
  • Compare greedy with DP on knapsack variants.
  • Write proof before code.