LeetCode ยท #875

Koko Eating Bananas Solution

Find the minimum eating speed k such that Koko can eat all bananas within h hours.

01
Section One ยท Problem

Problem Statement

๐Ÿท๏ธ

Difficulty

Medium

๐Ÿ”—

LeetCode

Problem #875

๐Ÿ—๏ธ

Pattern

Binary Search โ€” search on answer

There are n piles of bananas with piles[i] bananas each. Guards return in h hours. Koko eats at speed k bananas/hour. Each hour she picks a pile and eats k bananas (if fewer remain, she eats them all and waits). Find the minimum integer k such that she can eat all bananas within h hours.

Example
Input: piles = [3,6,7,11], h = 8 Output: 4 // At speed 4: ceil(3/4)+ceil(6/4)+ceil(7/4)+ceil(11/4) = 1+2+2+3 = 8 โ‰ค 8 โœ“ // At speed 3: 1+2+3+4 = 10 > 8 โœ—
Constraints
โ€ข 1 โ‰ค piles.length โ‰ค 10โด โ€ข piles.length โ‰ค h โ‰ค 10โน โ€ข 1 โ‰ค piles[i] โ‰ค 10โน
02
Section Two ยท Approach 1

Brute Force โ€” O(n ยท max)

Try every speed from 1 upward. For each speed, compute total hours needed. Return the first speed that works.

Problem: max(piles) can be 10โน. Testing each speed linearly is far too slow. The answer space [1, max(piles)] is monotonic โ€” if speed k works, all speeds > k also work. Binary search on this monotonic space gives O(n log max).
MetricValue
TimeO(n ยท max(piles))
SpaceO(1)
03
Section Three ยท Approach 2

Binary Search on Answer โ€” O(n log max)

Binary search the speed k in range [1, max(piles)]. For each candidate speed, compute total hours = ฮฃ ceil(piles[i] / k). If total โ‰ค h, try a smaller speed (go left). Otherwise, try a larger speed (go right).

๐Ÿ’ก Mental model: Imagine turning a speed dial from 1 to max. At some threshold, the total time drops from "too slow" to "fast enough." You're binary searching for that threshold โ€” the minimum dial setting where Koko finishes on time.
Algorithm
  • Step 1: left = 1, right = max(piles).
  • Step 2: Compute mid = (left + right) / 2.
  • Step 3: Compute total hours at speed mid: ฮฃ ceil(piles[i] / mid).
  • Step 4: If total โ‰ค h โ†’ speed might be too high (or just right), try lower: right = mid.
  • Step 5: If total > h โ†’ speed too slow: left = mid + 1.
  • Step 6: Return left.
๐ŸŽฏ "Search on answer" pattern:
  • When the problem asks for the minimum/maximum value that satisfies a condition, and you can write a feasibility check function, binary search the answer space.
  • The check must be monotonic: if speed k works, all k' > k also work.
  • This pattern appears in LC 875, LC 1011 (Ship Within D Days), LC 410 (Split Array Largest Sum), and LC 774 (Minimize Max Distance to Gas Station).
Ceiling division without float:
  • ceil(a / b) = (a + b - 1) / b using integer arithmetic. Avoids floating-point precision issues.
  • In Python you can also use -(-a // b).
04
Section Four ยท Trace

Visual Walkthrough

Trace through piles = [3, 6, 7, 11], h = 8:

Binary Search on speed โ€” feasibility check at each mid
Search range: [1, 11] h=8 Step 1: L=1,R=11,mid=6 โ†’ hours=1+1+2+2=6 โ‰ค 8 โ†’ R=6 Step 2: L=1,R=6,mid=3 โ†’ hours=1+2+3+4=10 > 8 โ†’ L=4 Step 3: L=4,R=6,mid=5 โ†’ hours=1+2+2+3=8 โ‰ค 8 โ†’ R=5 Step 4: L=4,R=5,mid=4 โ†’ hours=1+2+2+3=8 โ‰ค 8 โ†’ R=4 L=4, R=4 โ†’ L==R โ†’ answer = 4 Answer: 4 โœ“
05
Section Five ยท Implementation

Code โ€” Java & Python

Java โ€” Binary Search on Answer
class Solution { public int minEatingSpeed(int[] piles, int h) { int left = 1, right = 0; for (int p : piles) right = Math.max(right, p); while (left < right) { int mid = left + (right - left) / 2; long hours = 0; for (int p : piles) hours += (p + mid - 1) / mid; // ceil division if (hours <= h) right = mid; // feasible โ€” try smaller else left = mid + 1; // too slow โ€” need faster } return left; } }
Python โ€” Binary Search on Answer
import math class Solution: def minEatingSpeed(self, piles: list[int], h: int) -> int: left, right = 1, max(piles) while left < right: mid = (left + right) // 2 hours = sum(math.ceil(p / mid) for p in piles) if hours <= h: right = mid # feasible โ€” try smaller else: left = mid + 1 # too slow return left
06
Section Six ยท Analysis

Complexity Analysis

ApproachTimeSpaceTrade-off
Brute ForceO(n ยท max)O(1)Try every speed linearly
Binary Search on Answer โ† optimal O(n ยท log(max)) O(1) log(max) candidates ร— O(n) feasibility check
Where max = max(piles): logโ‚‚(10โน) โ‰ˆ 30. So we do at most 30 ร— n operations โ€” very fast even for n = 10โด.
07
Section Seven ยท Edge Cases

Edge Cases & Pitfalls

CaseInputWhy It Matters
h == n[3,6,7,11], h=4Exactly one hour per pile โ†’ k = max(piles) = 11.
h very large[3,6,7,11], h=10โนk=1 works โ€” plenty of time. Binary search converges to 1.
Single pile[30], h=5Need ceil(30/k) โ‰ค 5 โ†’ k โ‰ฅ 6.
All piles size 1[1,1,1], h=3k=1 โ†’ 3 hours exactly. Minimum speed.
Integer overflowLarge piles, small kSum of hours can exceed int range. Use long in Java.
โš  Common Mistake: Using left โ‰ค right instead of left < right. This is a "find minimum feasible" search โ€” the answer converges when L==R. With โ‰ค and right = mid, the loop never terminates when L==R.

โ† Back to Binary Search problems