Data AnalyticsIndustry analytics playbooks

Warehouse pick rate: lines per hour without punishing hard zones

PK
Pankit Kumar
Sr. Data Scientist at Parexel (a Goldman Sachs–backed company) · 27 September 2026 · 5 min read
In this article (6 sections)

Related programme: the Data Analytics with Generative AI course (3–4 months; ₹90,000 (inclusive of GST) · EMI from ₹4,000/month).

The short answer

Warehouse pick rate is usually reported as order lines picked per hour, but raw lines per hour only compares people fairly if they pick the same kind of work. A fairer measure is performance against an engineered standard: standard hours earned (lines × agreed seconds per line for that zone) divided by the direct hours the picker actually had work available. Report both, and never rank people on the raw number alone.

Why the raw number ranks the wrong person last

Picture a mid-sized fulfilment centre on the outskirts of an Indian metro serving e-commerce and modern trade. The forward-pick zone holds fast-moving eaches in flow racks at waist height. The bulk zone needs a reach truck or pallet jack and full cases. The cold room needs jackets and has a door protocol. A picker in forward pick can clear a line in well under a minute; a bulk pick can take three.

If the shift manager's dashboard shows lines per logged hour, the bulk pickers look lazy every day. They are rotated out, the better ones ask for forward pick, and the bulk backlog grows. The metric has changed behaviour in a way nobody intended.

The operations head's actual question is: given the work each person was given, how productive were they, and where are we losing hours?

What the WMS and time system give you

SourceColumns you needWatch for
WMS pick taskstask_id, picker_id, zone, location, sku, lines, units, task_start, task_endone task can cover several lines; confirm-scan time, not assignment time
Attendance / biometricpicker_id, shift_date, clock_in, clock_outincludes breaks unless netted out
Indirect activity logpicker_id, activity (replenishment, cycle count, training, housekeeping), minutesoften self-reported on paper
WMS task queuereleased_at per wave, picker assignedgaps where no task was released
Engineered standardszone, seconds_per_line, seconds_per_unit, travel allowanceowned by industrial engineering; date-stamped

The three measures, defined

  • Raw pick rate = lines ÷ logged hours
  • Direct pick rate = lines ÷ direct hours, where direct hours = logged hours − indirect hours − no-work hours
  • Performance % = standard hours earned ÷ direct hours × 100, where standard hours earned = Σ (lines in zone × standard seconds per line for that zone) ÷ 3,600

Performance is what lets a bulk picker and a forward picker be compared. 100% means the person worked at exactly the engineered pace for the work they received.

A shift worked through in pandas

Synthetic data: four pickers, one eight-hour shift, standards of 45 seconds per line in forward pick, 180 in bulk and 110 in cold. P4 waited 3.5 hours because the evening wave was released late.

python
import pandas as pd

# Synthetic: one shift, four pickers, three zones
picks = pd.DataFrame({
    "picker_id": ["P1"]*3 + ["P2"]*2 + ["P3"]*3 + ["P4"]*2,
    "zone":      ["FWD","FWD","BULK", "BULK","BULK", "FWD","FWD","FWD", "COLD","FWD"],
    "lines":     [180, 150, 20,  60, 45,  210, 190, 170,  70, 40],
    "units":     [420, 380, 160, 510, 400, 450, 400, 390, 140, 90],
})
hours = pd.DataFrame({
    "picker_id": ["P1","P2","P3","P4"],
    "logged_hours": [8.0, 8.0, 8.0, 8.0],
    "indirect_hours": [0.5, 0.5, 1.5, 0.5],   # replenishment, cycle count, training
    "no_work_hours":  [0.0, 0.0, 0.0, 3.5],   # WMS shows no task released to picker
})
# Engineered standard seconds per line, agreed per zone
std_sec = {"FWD": 45, "BULK": 180, "COLD": 110}

picks["std_hours"] = picks["zone"].map(std_sec) * picks["lines"] / 3600
p = picks.groupby("picker_id")[["lines", "std_hours"]].sum().reset_index()
p = p.merge(hours, on="picker_id")
p["direct_hours"] = p["logged_hours"] - p["indirect_hours"] - p["no_work_hours"]
p["raw_lines_per_hr"] = (p["lines"] / p["logged_hours"]).round(1)
p["lines_per_direct_hr"] = (p["lines"] / p["direct_hours"]).round(1)
p["performance_pct"] = (100 * p["std_hours"] / p["direct_hours"]).round(1)
print(p[["picker_id","lines","raw_lines_per_hr","lines_per_direct_hr","std_hours","performance_pct"]]
      .round(2).to_string(index=False))

Output:

text
picker_id  lines  raw_lines_per_hr  lines_per_direct_hr  std_hours  performance_pct
       P1    350              43.8                 46.7       5.12             68.3
       P2    105              13.1                 14.0       5.25             70.0
       P3    570              71.2                 87.7       7.12            109.6
       P4    110              13.8                 27.5       2.64             66.0

On raw lines per hour, P2 (bulk) is last at 13.1 and looks a fifth as productive as P3. On performance, P2 is at 70.0%, slightly ahead of P1. P4's raw rate says 13.8; once the 3.5 hours with no released work are removed, P4 performed at 66.0%, close to the others. P4's problem was the wave plan, not the picker.

Readings that need a second look

P3 at 109.6% with 1.5 indirect hours. Above-standard performance is possible, but P3 also logged three times the indirect time of anyone else. If indirect time is self-reported, moving hours from direct to indirect inflates performance. Cross-check indirect entries against the WMS: a cycle count should leave count tasks in the system.

Standards that are years old. If the forward-pick zone was re-slotted with flow racks last quarter, a 45-second standard may now be generous, and everybody in that zone looks good. Keep the standard's effective date with it and review after layout changes.

Units versus lines. A line of 40 units of a small SKU is not the same work as a line of one. Where unit counts vary a lot within a zone, add a seconds-per-unit component to the standard rather than switching the whole report to units per hour, which rewards pickers who get large-quantity lines.

Task timestamps. Some WMS setups stamp the task at assignment, not at confirmation scan. Durations computed from assignment time include queueing, which is not the picker's time.

Pick accuracy. A fast picker with mispicks costs more than a slow accurate one, because each mispick means a return or a customer complaint. Report mispicks per 1,000 lines next to performance, from packing-station or QC scans.

Showing it to the warehouse and operations heads

Separate the two audiences in the report.

For the operations head, the headline is hours lost, not individual rankings: "Across four pickers we logged 32 hours; 3.5 went to waiting for a wave and 3 to indirect work. Released-work delays cost more than any individual productivity gap." That points to a fix in wave planning.

For shift supervisors, show performance % by picker with the zone mix beside it, never raw lines per hour alone. Use a band (for example, a range agreed with the site) rather than a league table, and pair it with accuracy. Individual performance data affects people's jobs; show it only to those who manage them, and make sure the standards are known to the pickers themselves.

This is the same logic as the OTIF playbook: define the denominator before comparing anyone. Building metrics like this from WMS extracts is core practice in the Data Analyst programme.

PK
Pankit Kumar
Lead Instructor, NeuraPath Academy

Pankit Kumar has 10 years in Data Science & AI, building and shipping production systems in regulated pharma and clinical environments. He is a freelance trainer at Boston Institute of Analytics, AnalytixLabs and Scaler, and has taught this material to thousands of working professionals.

This article is part of our Data Analytics with Generative AI programme — 3–4 months. The full analyst stack — Excel, SQL, Power BI and Python pipelines — then a generative-AI layer you can prove is right.

Explore Data Analytics with Generative AI
Counselling is free · no obligation

Not sure which programme fits?

Tell us your background and we will map it to the right entry point — including saying so when a cheaper programme is the better fit. A counsellor replies within one working day.