Interview guides · Hertz
Hertz Data Scientist Interview Questions & Guide 2026
A two-week prep plan for Hertz data scientist candidates: write your answer before reading the solution, revisit misses three days later.
The 60-second brief
At Hertz, a Data Scientist is more than just a model builder; you are a strategic architect of the modern travel experience. Operating at the intersection of logistics, technology, and consumer behavior, the data science team is responsible for transforming massive datasets into actionable intelligence. This role is central to Hertz's mission of optimizing its massive global fleet, predicting market demand with surgical precision, and enhancing the digital journey of millions of customers worldwide.
Scope your preparation by the data you would actually touch, because the title will not tell you. A seat that lives in event logs and weekly readouts rewards fluency in aggregation and metric definitions; a seat that owns a model in production rewards fluency in train/serve skew, retraining cadence and drift monitoring. The fastest way to find out which one you are interviewing for is to ask what the team shipped last quarter and what it gets paged about.
Focus areas
- Separate true demand from censored, stocked-out sales
- Price a service-level change in working capital
- Size safety stock under variable lead times
Overview
You will work on high-impact problems that directly influence the company's bottom line. Whether it is developing dynamic pricing algorithms, optimizing vehicle maintenance schedules, or refining customer segmentation for marketing, your work ensures that Hertz remains a leader in the competitive mobility sector. The complexity of managing a physical fleet alongside a digital marketplace provides a unique challenge that requires both technical depth and a strong business intuition.
This position is ideal for those who thrive on variety. One day you might be collaborating with directors to streamline rental operations, and the next, you could be presenting a machine learning prototype to executive leadership. You are expected to be a self-starter who can navigate the nuances of global data structures, especially as the company integrates its international data operations between the and.
The Hertz interview process
Hertz candidates report 4 rounds · ≈ 3-5 weeks. The stages below are what candidates describe, not a published process.
Recruiter Screening
A screening call is a matching exercise run by someone who will not evaluate your statistics. They are checking that the work described on your resume is work you personally did, and that its scope matches the level the role is written for. Logistics get settled in the same half hour so nobody spends an interviewer's afternoon on a mismatch. The answer that fails is the one narrated in the plural. If every sentence is 'we built' and 'the team decided', there is nothing specific to write down about you. Name the piece that was yours, the decision you made inside it, and what changed after.
What to demonstrate
- Whether the ownership implied by your resume survives one round of follow-up about who actually did which part
- Whether your described scope (data size, stakeholders, what shipped) matches the seniority the role is written at
- Whether timeline, location and compensation expectations make the rest of the loop worth scheduling
How to prepare
- Rewrite your top three resume bullets in the first person singular, each with the decision you made and what moved afterwards, then say them out loud once so the 'we' does not return under pressure
- Attach one number to each project: the baseline, the change, and the window it was measured over. Where impact was never measured, say that plainly rather than inventing a figure
- Settle your compensation range before the call and give it as a range with a reason behind it, such as current total comp or a competing timeline, instead of deflecting the question twice
Hiring Manager Conversation
Underneath the questions about your past work sits a resourcing question. Given four things worth doing and one of you, which gets done and what happens to the rest? Managers ask because that is the daily texture of the job, and because the answer shows whether you rank work by effort or by what it changes. The weak version sorts by personal interest or by whoever asked most insistently. The strong version ties each candidate piece of work to a decision somebody downstream is waiting on, and then names the one you would drop and who you would tell.
What to demonstrate
- Whether you rank work by the decision it unblocks or by how interesting the method is
- How you describe a request you declined, and whether you can say who you said it to
- Whether your sense of how long something takes survives one follow-up question about the messy part
- How you decide something is good enough to hand over unfinished
How to prepare
- Write out your current queue and, next to each item, the decision that stays stalled until it lands. Anything with no waiting decision becomes your example of work you would cut
- Rehearse turning down a plausible stakeholder request out loud, including the smaller alternative you offered instead
- Have one case where you shipped a rough answer early and one where you refused to, with the reason that separated them
Technical Evaluation
Before anything else, this round is a reading test. You are given a small schema and a question phrased in business language, and most of the difficulty sits in the gap between them. Who counts as an active user, does a refunded order still count as an order, is that date column an event time or a load time. Weak answers start typing immediately and compute something precise about the wrong population. Strong ones pin the definition in one sentence, name the column that encodes it, then write the query. On a timed assessment with nobody to tell, write the definition in a comment anyway.
What to demonstrate
- Whether an ambiguous term becomes a specific column and filter before any computation happens
- Whether you read the schema for keys and cardinality rather than only for column names
- Whether the result answers the question at the grain it was asked at, per user or per session or per day
How to prepare
- Take three metrics you already use and write down the exact filter and exact grain behind each, then practise stating one of them in a single sentence out loud
- On a schema you have never seen, spend the first minute writing what one row of each table means and which key it is unique on, then predict which joins can duplicate rows
- Rehearse a version where the definition changes halfway through, and edit the query you have instead of starting over
Project Presentation
An extra round usually exists because something is still open after the standard loop: a skill the earlier interviews did not sample, a level decision, or two interviewers who disagreed. It is rarely a rerun of what you already did well. Ask the recruiter who you are meeting, what function they sit in, and how long the session runs. That is an ordinary scheduling question, and the answer changes what you should prepare. What separates a strong candidate here is treating the round as a fresh evaluation with its own bar, rather than assuming earlier performance carries you through or sinks you.
What to demonstrate
- Whether you can answer well on ground the earlier rounds did not cover, without leaning on what you already said to someone else
- Consistency of the facts in your stories: the same sample size, timeframe, team size and scope of your own role as in earlier conversations
- How you handle an unfamiliar format live, including whether you ask what kind of answer is wanted before producing one
How to prepare
- Ask the recruiter for the interviewer's function, the length, and whether to expect a coding surface, a discussion, or a presentation. Preparing for a 30 minute conversation with a partner team is not the same work as preparing for a 60 minute technical block.
- Write out what each earlier round actually covered, then list the two or three areas nobody probed. That gap is the most likely subject of the extra round.
- Re-read the numbers in the project stories you have already told, so a second telling does not quietly contradict the first.
Where candidates lose points
Scoring intermittent demand with MAPE
MAPE is undefined whenever the actual is zero, which is most days for a C-class item at a forward-stocking location, and it is asymmetric even where it is defined: under-forecasting is bounded at 100 percent error while over-forecasting is unbounded. Optimising it therefore drives systematic under-forecasting on exactly the items whose stockouts are most expensive, and the bias is invisible in the headline because the zero-actual rows were dropped before averaging. Use WMAPE (sum of absolute errors over sum of actuals), a scaled error such as RMSSE, or a pinball loss at the service quantile the policy targets, and always state the aggregation level and forecast lag, because the same series scores very differently at daily SKU-store level and weekly SKU-region level.
Computing average inventory from period-end snapshots
Shipments cluster before period close, so the month-end on-hand position is systematically the lowest point of the month; turns computed against it are biased high and days of supply biased low, frequently by ten to twenty percent, and the bias grows precisely when close-period push is strongest. The same shape of error appears when a daily snapshot is joined to shipment events on date equality: a SKU with several legs on one day fans the snapshot out and multiplies the valued inventory. Average across every daily snapshot in the window for the denominator, and join snapshots to events with an explicit as-of condition and a row-count check at each grain before aggregating.
Reporting a mean for a heavy-tailed metric without saying what it hides
For spend, session length or items per order, a small fraction of units carries most of the total, so the mean has a wide standard error and one account can move it. Fix the handling before you see the result: cap or winsorise at a pre-declared percentile, and report the median or the share above a threshold next to the mean. Capping changes the estimand, so say which question the capped number answers, and check how much of any difference comes from the top 0.1 percent of units.
Accepting a metric definition without asking about the denominator
Pin down the denominator, the eligibility filter and the time window before computing anything: conversion rate per session, per user, per eligible user and per new user are four different numbers with different behaviour. Restate the definition in one sentence and get agreement before you analyse.
Questions & practice
What feature selection techniques do you prefer when dealing with hundreds of potential variables?
Medium · machine learning and modelling
Approach
- Pick an evaluation metric that matches the cost of each error type, not a default.
- Set a baseline first, so any model has something honest to beat.
- Frame the prediction: the label, the moment of prediction, and the action it triggers.
Follow-up
- Where could label leakage enter this setup?
- How would you choose the decision threshold, and who owns that choice?
"On page 2, you mentioned using a Random Forest for [Project X]. Why didn't you use a Gradient Boosted Tree?"
Medium · machine learning and modelling
Approach
- Frame the prediction: the label, the moment of prediction, and the action it triggers.
- Check what information would not exist at prediction time, and exclude it.
- Pick an evaluation metric that matches the cost of each error type, not a default.
Follow-up
- How would you choose the decision threshold, and who owns that choice?
- Where could label leakage enter this setup?
What are the advantages of using Python over R for production-level machine learning?
Medium · machine learning and modelling
Approach
- Frame the prediction: the label, the moment of prediction, and the action it triggers.
- Check what information would not exist at prediction time, and exclude it.
- Pick an evaluation metric that matches the cost of each error type, not a default.
Follow-up
- How would you choose the decision threshold, and who owns that choice?
- Where could label leakage enter this setup?
Recover unconstrained demand from stockout-censored history
Hard · censoring · maximum likelihood · em algorithm
A legacy extract has only inventory_date, sku_id, location_id, shipped_qty and stockout_flag; demand_qty was not populated before a cutover date. On a stockout day, shipped_qty is a lower bound on that day's demand. Model daily demand per sku-location as Poisson and fit its mean by maximum likelihood, treating stockout days as right-censored observations. Return the fitted mean per cell alongside the naive mean of shipped_qty and the censored share. Then validate against the post-cutover window where demand_qty exists.
Approach
- Write the likelihood before any code. Uncensored days contribute the Poisson pmf at the observed count; stockout days contribute the survival probability P(X >= y), because all you learned is that demand was at least what you managed to ship.
- Solve it as an EM fixed point rather than reaching for a general optimiser: the censored MLE equals the complete-data mean with each censored observation replaced by its conditional expectation, so iterate lambda_next = (sum of uncensored y + sum of E[X | X >= y, lambda]) / n until it stops moving.
- Use the closed form for the conditional expectation rather than truncating an infinite sum: for a Poisson, sum over k >= y of k*p(k) equals lambda times P(X >= y-1), so E[X | X >= y] = lambda * P(X >= y-1) / P(X >= y) for y >= 1. That removes the tail-truncation error entirely.
- Refuse to fit cells with too little signal. A sku-location with three non-zero days or with every day censored has no identifiable mean; return the naive figure with a flag rather than a confident number.
- Validate on the post-cutover window where demand_qty is populated: fit the estimator on shipped_qty and stockout_flag alone, and compare both the censored estimate and the naive mean against the true mean of demand_qty.
Worked solution (45 min)
- Split each cell's days into censored (stockout_flag true) and uncensored, and record the censored share.
- Initialise lambda at the mean of shipped_qty over all days, which is a strict lower bound on the answer.
- Iterate the EM update using scipy.stats.poisson.sf for the survival terms, stopping when the change in lambda falls below 1e-8 or after 500 iterations.
- Assemble a per-cell frame with lambda_hat, naive_mean, censored_share, n_days and a converged flag; mark thin cells rather than fitting them.
- On the post-cutover window, compute the true mean of demand_qty per cell and report the absolute error of lambda_hat against the absolute error of naive_mean.
Expected result: Per-cell lambda_hat that is greater than or equal to the naive mean of shipped_qty in every cell, with equality exactly when the cell has no censored days. The uplift grows with censored share. On the validation window, lambda_hat has lower mean absolute error against the true demand_qty mean than the naive figure does.
Verify it yourself
- Assert lambda_hat >= mean(shipped_qty) for every cell; the EM fixed point guarantees this because E[X | X >= y] >= y, so any violation is an implementation bug.
- Re-solve one cell by directly minimising the negative log-likelihood with a one-dimensional optimiser and confirm it agrees with the EM answer to at least six decimal places.
- Simulate a cell with known lambda, censor it artificially at a known threshold, and confirm the estimator recovers lambda within Monte Carlo error while the naive mean does not.
- Confirm cells with zero censored days return lambda_hat exactly equal to the sample mean, since the likelihood reduces to the ordinary Poisson case.
Follow-up
- The fitted mean is 18 percent above the naive mean for A-class items and 2 percent above for C-class. Why would you expect that ordering?
- The residual variance is three times the fitted mean. What does that break and what distribution would you move to?
- A stockout is often caused by a demand spike that day. What does that do to your estimate and can you correct it?
Describe how you would automate a weekly reporting dashboard in Tableau.
Medium · sql and data manipulation
Approach
- Check whether any join is one-to-many before aggregating, or the sums inflate.
- Say which table is the grain you start from, and join outward from it.
- Handle the rows that do not match: a LEFT JOIN with a NULL check is usually the question.
Follow-up
- How would you verify this result without re-running the same query?
- How does the query change if the join becomes one-to-many?
Explain the difference between a left join and an inner join in the context of merging customer and transaction tables.
Medium · sql and data manipulation
Approach
- State the window function and its partition and ordering out loud before writing it.
- Say which table is the grain you start from, and join outward from it.
- Handle the rows that do not match: a LEFT JOIN with a NULL check is usually the question.
Follow-up
- How does the query change if the join becomes one-to-many?
- How would you verify this result without re-running the same query?
Write a SQL query to find the top 3 most popular car models in each city.
Medium · sql and data manipulation
Approach
- Check whether any join is one-to-many before aggregating, or the sums inflate.
- Say which table is the grain you start from, and join outward from it.
- Handle the rows that do not match: a LEFT JOIN with a NULL check is usually the question.
Follow-up
- How does the query change if the join becomes one-to-many?
- What breaks if events arrive late or out of order?
Lag-7 forecast accuracy and bias at weekly grain
Easy · forecast accuracy · null handling · aggregation grain
fct_inventory_daily has one row per sku_id x location_id x inventory_date carrying demand_qty, forecast_qty_lag7 (the forecast for that date as published seven days earlier, NULL before the series existed) and stockout_flag. Compute trailing eight-week WMAPE and signed weighted bias at the sku x location x week grain the ordering decision uses: aggregate demand and forecast to the week first, then form errors on the weekly totals. Exclude any week containing a NULL forecast day and report how many cell-weeks that removed. Return one accuracy row per ABC class.
Approach
- Roll daily rows to sku-location-week with SUM(demand_qty) and SUM(forecast_qty_lag7), carrying COUNT(*) FILTER (WHERE forecast_qty_lag7 IS NULL) so a partial week is visible rather than quietly summing to an artificially low forecast.
- Drop cell-weeks with any NULL forecast day and emit the dropped count as a column: an accuracy figure without its exclusion count cannot be checked by anyone.
- WMAPE = SUM(ABS(weekly_demand - weekly_forecast)) / NULLIF(SUM(weekly_demand), 0). Bias = SUM(weekly_forecast - weekly_demand) / NULLIF(SUM(weekly_demand), 0), signed, with cancellation as the whole point of reporting it next to WMAPE.
- Join dim_sku for abc_class and group there by re-summing both sides. Averaging per-SKU WMAPE gives a number weighted by nothing in particular.
- Report the share of retained cell-weeks containing a stockout day beside the result, because demand_qty on those days is censored at what could be supplied and the error is being scored against a truncated actual.
Worked solution (25 min)
- CTE one: GROUP BY sku_id, location_id, DATE_TRUNC('week', inventory_date) with SUM(demand_qty), SUM(forecast_qty_lag7) and the NULL-day count.
- CTE two: split the cell-weeks into retained (null_days = 0) and excluded, and keep COUNT(*) of each.
- Join dim_sku on sku_id for abc_class, then aggregate the retained set per class with the two ratio formulas.
- Compute the stockout exposure share over the same retained set and attach it to each class row.
- Print retained count, excluded count and window bounds alongside every ratio.
Expected result: One row per abc_class with wmape as a non-negative ratio, bias as a signed ratio, both over the same SUM(weekly_demand) denominator, plus retained and excluded cell-week counts and the stockout exposure share.
Verify it yourself
- WMAPE is always at least the absolute value of bias, because the sum of absolute errors dominates the absolute sum of signed errors. A violation means the two are not computed over identical rows.
- Substituting forecast_qty_lag7 := 1.1 * demand_qty on the retained cell-weeks yields bias exactly +0.10 and WMAPE exactly 0.10, provided weekly demand is non-negative and sums above zero. Scaling the real forecast by 1.1 proves nothing: that gives bias = 1.1 * SUM(forecast) / SUM(demand) - 1, which reaches +0.10 only where the forecast already totals demand, and leaves WMAPE at no fixed value.
- Retained cell-weeks plus excluded cell-weeks equals the total number of sku-location-weeks in the window.
Follow-up
- Why is MAPE unusable on a C-class item at a forward-stocking location, and what do you score it with instead?
- WMAPE improves sharply when you move from sku-location-week to sku-region-week. Which of the two belongs in the planning review, and why?
- Bias is +6 percent and WMAPE is 45 percent. What does that pair tell you to investigate first?
Recover the effect of expediting from an automatic threshold rule
Hard · regression discontinuity · fuzzy rd · late · manipulation test
The transport system upgrades service_level to 'expedite' whenever projected slack at tender falls below 12 hours, and charges expedite_premium_cents for it. Projected slack is promised_delivery_at_utc minus the planned arrival implied by planned_transit_hours, and it is recoverable from two years of fct_shipment_leg. Finance wants to know what the premium buys. No randomised holdout is possible, and the rule has run unchanged throughout. Estimate the causal effect on on-time delivery, state which shipments your estimate applies to, and give the checks that would invalidate it.
Approach
- Recognise the design: treatment is a deterministic function of an observed continuous running variable with a known cutoff, so a regression discontinuity identifies the effect at that cutoff with no randomisation, provided nothing other than the expedite rule changes at 12 hours.
- Estimate with local linear regression on each side of the cutoff, a triangular kernel and an MSE-optimal data-driven bandwidth, reporting robust bias-corrected confidence intervals. Do not fit a global high-order polynomial: it imports weight from observations far from the cutoff and manufactures jumps that are artefacts of the functional form.
- Test manipulation, because planners can edit the promise date and that moves slack directly. Run a density test of the running variable at the cutoff and inspect the histogram for heaping just below 12 hours. If slack is recorded to the whole hour, treat the running variable as discrete, cluster by its value, and consider a donut estimate that drops the bins adjacent to the cutoff.
- Test continuity of everything that is not the treatment: weight_kg, cube_m3, mode, stop_count, lane and carrier should not jump at 12 hours. Add placebo cutoffs at 8 and 16 hours, where the effect should be indistinguishable from zero.
- Handle overrides. If dispatchers sometimes expedite above the cutoff or decline below it, the design is fuzzy: estimate the jump in the probability of expediting and divide the outcome jump by it, equivalently two-stage least squares with the below-cutoff indicator as the instrument, and report the first-stage jump, because a weak first stage makes the ratio unstable.
- Finish with the arithmetic Finance asked for: the jump in on-time probability at the cutoff against mean expedite_premium_cents per unit inside the bandwidth, expressed as cost per incremental on-time delivery and labelled as applying only near 12 hours of slack.
Follow-up
- The jump is 4 points at the cutoff. What would you need before recommending the threshold move to 18 hours?
- Slack is recorded to the whole hour and 9% of legs sit exactly at 12. What does that heaping do to the estimate, and how do you handle it?
Success metric for opening one forward-stocking node
Medium · synthetic control · risk pooling · power
The network will open one forward-stocking location at echelon 3, replenished by an existing regional DC. There is one treated node and about thirty candidate comparison nodes. Using fct_order_line (ordered_at_utc, actual_delivery_at_utc, ship_from_location_id, line_status), fct_inventory_daily (on_hand_qty, standard_cost_cents) and fct_shipment_leg (direction, shipped_units, linehaul_cost_cents, accessorial_cost_cents, delivered_at_utc), define the primary metric, the guardrail that catches the working-capital cost of de-pooling, and the readout design. Say what this sample cannot detect.
Approach
- Anchor the primary on what the node is for: P90 order cycle time for the lines it serves, taken over the pooled line-level distribution rather than as a mean of daily percentiles, with never-delivered lines reported as a censored count instead of dropped.
- Make the inventory guardrail network-wide, not node-local. Splitting one pooled stock into two locations raises total safety stock at the same service level; under independent demand, equal service and equal lead times the square-root law puts the factor at sqrt(2) on the safety component, so measure parent and new node combined at cost.
- Add a freight guardrail across both the new inbound interfacility leg and the outbound legs, because the opening adds a movement that any node-local outbound cost metric will miss entirely.
- Choose a design suited to one treated unit: a synthetic control or matched-pair comparison built from donor nodes on pre-period cycle time, volume, SKU mix and lane structure, with the donor pool and matching variables frozen before the readout.
- Set the burn-in at two full replenishment cycles, and book the fill-and-build inventory into the cost side rather than letting it contaminate the service read.
- State the limit rather than implying precision: with one treated unit there is no cross-unit variance, so a placebo distribution over the donors is the only inferential statement available, and effects smaller than the donor spread cannot be distinguished from node noise.
Worked solution (35 min)
- Build a weekly node panel covering at least 26 pre-period weeks: P90 cycle time, line volume, fill rate, on-hand at cost, delivered cost per unit.
- Screen the donor pool, dropping nodes that opened, closed or changed parent_location_id inside the window, then fit synthetic weights on pre-period P90 and volume only.
- Check pre-period fit, then run placebo assignments across every donor to build the distribution of pseudo-effects.
- Estimate the post-period effect from the burn-in end, and compute the working-capital series as parent plus new node combined.
- Report the effect against the placebo distribution together with the minimum effect this design could have detected.
Expected result: A readout design where the primary is P90 order cycle time for lines shipped from the treated node, estimated against a synthetic control fitted on pre-period P90 and volume; guardrails are combined parent-plus-node on-hand at cost and delivered cost per unit across the added interfacility leg plus outbound; a two-replenishment-cycle burn-in is excluded from the service read and charged to cost; and inference is stated to rest on a placebo distribution over roughly thirty donors, so effects inside the donor spread are declared undetectable.
Verify it yourself
- Pre-period fit: the synthetic series tracks the treated node's P90 within the donor-to-donor spread before the opening, otherwise the estimate is not usable and no amount of post-period data repairs it.
- The working-capital guardrail is computed on parent plus node combined; computed node-only it always shows an increase and carries no information.
- Computing P90 as a mean of daily P90s produces a different and generally flatter series than the pooled line-level percentile; show both once to prove which one the readout uses.
Follow-up
- A donor node runs a promotion during the post period. What do you do, and at what point did you have to decide it?
- The service gain is real and the cost guardrail is also up. Who decides, and on which number?
Plant schedule instability generated two echelons downstream
Hard · bullwhip · echelon attribution · variance
A plant reports that the replenishment orders it receives swing far more than end-customer demand, and asks for a larger finished-goods buffer. You have fct_order_line for customer demand at store and forward-stock nodes, fct_inventory_daily (on_order_qty, demand_qty per sku-location-date), dim_location (echelon, parent_location_id) and dim_sku (units_per_case, cases_per_pallet). Measure amplification at each echelon, identify the node whose ordering rule generates it, and price the buffer request against fixing that rule. Deliverable: a per-echelon amplification table and a recommendation.
Approach
- Build two series per node at a fixed weekly bucket per SKU: the quantity the node ordered from its parent_location_id, and the demand it received from its children or from customers. Both series must cover the same SKU, the same weeks and the same node set, or the ratio between them means nothing.
- Compute amplification per node as Var(orders placed) / Var(demand received), and report the squared coefficient-of-variation form alongside it. Mean volumes differ by an order of magnitude between echelons, so a raw variance ratio is not comparable across nodes of different size while the CV-squared ratio is scale-free.
- Read the table echelon by echelon and find where the ratio steps up. The generating node is where it first exceeds one by a wide margin, not the node that feels the pain: amplification observed at the plant is the product of every ratio below it along that chain.
- Name the mechanism at that node rather than asserting bullwhip generically. Minimum order quantity and lot-size multiple, the review period, batching up to a full truckload, and forecast-driven ordering that reacts to its own safety stock recalculation each leave a distinct signature in the order-size histogram.
- Price both options rather than choosing one. The buffer request converts to units, then to cost at standard_cost_cents and to carrying cost at the applicable cost of capital. The rule change converts to more frequent, smaller replenishment and therefore more freight per unit. Present the trade with both numbers attached.
Follow-up
- Orders cluster on exact truckload multiples. Would you break the batching rule, and what does that cost in freight per unit?
- How would you test an ordering-rule change when there are twelve nodes, they draw on the same stock and the same outbound loads, and one replenishment cycle is three weeks?
- Part of the plant's variance is its own production batching. How do you separate inbound amplification from what the plant creates for itself?
Suggested practice checklist
For someone who can already write the query and train the model but stalls when asked what to measure or whether a change is worth making. Metric definition and case structure come first; the technical work is kept as maintenance rather than the centre of the week.
Day 1 — Metric anatomy
- For three products you use daily, write one primary metric, two input metrics that plausibly move it, and one guardrail that would catch a cheap way of moving the primary at the cost of the product.
- For one of them, specify the metric precisely enough that two analysts would return the same number: numerator, denominator, unit of observation, time window, and how returning and deleted accounts are treated.
- Pick a ratio metric and write what happens to it when the denominator shrinks for reasons unrelated to the numerator, with a concrete example of that happening.
Deliverable: A one-page metric tree for one product, with the primary metric written as an unambiguous spec.
Day 2 — Diagnosing a drop without guessing
- Take the prompt "weekly active users fell 8 percent week over week" and write the segmentation plan before proposing any cause: platform, region, tenure cohort, acquisition channel, and whether the movement sits in the numerator or in a changed denominator.
- List the instrumentation failures that manufacture fake drops (a client release that stopped firing an event, a bot filter change, a shifted date boundary or timezone) and write the query that rules out each one.
- Rehearse stating the boring explanations first, seasonality and day-of-week composition, before reaching for a product cause.
Deliverable: A drop-diagnosis checklist short enough to recite from memory in under a minute.
Day 3 — Should we build it
- Take a feature idea and write it as a bet: what you believe is true, what would have to be true for it to pay off, the metric that would confirm it, and the effect size that would justify the engineering cost.
- Size the opportunity top-down and bottom-up, then reconcile the two numbers in writing instead of quoting whichever is friendlier.
- Write the counter-metric that would make you kill the feature even if it wins on the primary metric.
Deliverable: A one-page product memo ending in a decision rather than a list of considerations.
Day 4 — The places aggregate numbers lie
- Construct a Simpson's paradox numerically: two segments where the treatment wins within each segment yet loses overall, and identify the shift in segment weights that causes it.
- Take a heavy right-tailed quantity such as revenue per user and write why the mean is the wrong summary, which percentile you would report instead, and what a moving mean with a stable median tells you.
- Write your definition of a session for the product from day one, then name two real behaviours it misclassifies.
Deliverable: One page holding a worked Simpson's paradox table and a session definition with its two known failure cases.
Day 5 — Technical maintenance, aimed at metrics
- Solve four timed SQL prompts that all end in a ratio metric, so the question of grain stays live in every answer.
- Compute a 95 percent confidence interval for a proportion on a small sample, and state why the normal approximation is unreliable when either np or n(1 minus p) falls below roughly 10, along with which interval you would use instead.
- Take one metric from your day-one tree, write the query that computes it correctly, then write the query that computes it wrong in the most plausible way and explain how you would notice.
Deliverable: Four solved prompts plus a matched correct and plausible-wrong query for one metric.
Day 6 — Turning engineering work into data science stories
- Write three project stories as situation, decision, trade-off, outcome, each carrying one number and one thing you got wrong.
- For the story you will lead with, prepare an answer to "what would you do differently" that names a decision you made, not a constraint you were handed.
- Practise the sentence that reframes a systems project as a question project: the question the work answered, ahead of the pipeline it shipped.
Deliverable: Three written stories with the lead story delivered aloud and timed under four minutes.
Day 7 — Mock case and gap list
- Run a 40-minute mock case with someone playing a product manager who pushes back on your metric choice, and record it.
- Listen back and mark every moment you proposed a solution before the success metric existed.
- Rewrite those moments as the question you should have asked, and rehearse the first 90 seconds of the case until scoping comes before solving.
Deliverable: A recorded case plus a rewritten opening 90 seconds.
Explaining a method to someone who will not follow the maths
Half of this section is about translation. Be ready to describe how you explained a result to someone who did not want the method, only the implication, and what you did when the simplified version started being repeated in a way that overstated it. Correcting your own simplification is a strong beat.
Give an example of a time you had to learn a new tool or technology on the fly to complete a project.
Medium · behavioural and stakeholder questions
Approach
- Name the disagreement or constraint, and how you resolved it with evidence.
- State the situation in two sentences and spend the rest on your reasoning.
- Quantify the outcome, including what you would not claim credit for.
Follow-up
- How did you know the outcome was caused by your change?
- What would you do differently if you ran that project again?
Describe a project where the data was significantly messier than you initially expected.
Medium · behavioural and stakeholder questions
Approach
- Quantify the outcome, including what you would not claim credit for.
- Close with what you would do differently, concretely.
- Pick a story where you drove the decision, not one where you observed it.
Follow-up
- What would you do differently if you ran that project again?
- What did you decide not to do, and why?
Prioritise transport, plant and commercial in one week
Medium · prioritisation · stakeholder management · decision value
Three requests land in the same week. Transport wants landed cost per delivered unit split by lane and mode from fct_shipment_leg for a carrier bid that closes in nine days. A plant manager wants OEE on two work centres decomposed into availability, performance and quality from fct_production_run for a capital request due next month. Commercial wants a fill-rate root cause from fct_order_line for an account review on Thursday. You are the only data scientist and have about four working days. Give your order, the rule that produced it, and what you say to the two who wait.
Approach
- Rank by the decision each request feeds and by whether your input can still change it, not by seniority or by who asked loudest: a bid closing in nine days is a live decision with a large irreversible spend attached, a capital request due next month has slack, and an account review has a fixed date but a smaller reversible decision.
- Check reversibility and blast radius: carrier rates lock for a contract period across every lane, so an error or an absence there is expensive for a year, while the fill-rate story can be revised next week.
- Look for the cheap partial that unblocks someone else: the fill-rate cut by node, by short_reason_code and by week is a few hours of work and covers most of what commercial needs on Thursday, so it does not have to wait behind the bid.
- Sequence with explicit time boxes: the commercial cut first because it is short and date-locked, the lane and mode cost analysis next with the allocation basis for multi-stop loads stated up front, and the OEE decomposition scheduled into the following week with a date the plant manager can hold you to.
- Tell the plant manager directly and early, with a date rather than a maybe, and say what you need from him in the meantime so the delay produces something.
- Escalate the trade-off rather than absorbing it silently: your manager should know a capital request slipped a week, because that is a business choice and not yours alone to make.
Follow-up
- The plant manager escalates and his director asks you to reorder. What do you do?
- Which of the three would you push back on entirely, and what would you offer instead?