Problem 449119 · easy · Level 04 Non-Linear Data Structures

Slopes of a Black Box

numerical gradient · partial derivative · loss function · finite differences

A wind-tunnel simulator gives the drag of a model wing, f(params), for a list of shape parameters. Nobody has a formula for it: you can only call it. Before tuning the shape you want to know how the drag changes when each parameter moves a little.

Write numerical_gradient(f, params, h) that returns a list of floats, one per parameter. Entry i is the estimate

(f(params with params[i] + h) - f(params with params[i] - h)) / (2 * h)

where every other parameter keeps its value. Call f with a list of the same length as params. The list params itself must not be changed.

Examples

Input:  f = lambda p: p[0] ** 2 + 3 * p[1], params = [1.0, 2.0], h = 1e-4
Output: [2.0, 3.0]
Explanation: the slope of p0² at p0 = 1 is 2 and the slope of 3·p1 is 3 (up to rounding).

Input:  f = lambda p: p[0] ** 3, params = [1.0], h = 0.1
Output: [3.01]
Explanation: (1.1³ - 0.9³) / 0.2 = 3.01. The true slope is 3; you return the estimate.

Constraints

  • 0 <= len(params) <= 50, 1e-6 <= h <= 1
  • f returns a float for any list of floats of the right length
  • floats are compared with a tolerance of 1e-6

Goals

  • Estimate every partial derivative of a function you can only evaluate
  • Nudge one parameter at a time, in both directions, and leave the others unchanged
  • Never modify the caller's parameter list
Starting Python…