VerifiedarXiv:1707.0634728 min
Reinforcement learning · Policy gradients

PPO: Proximal Policy Optimization Algorithms

Clipping the probability ratio lets a policy train on each batch of experience for several epochs.

A plain policy gradient takes one step per batch, because further steps on the same data can push the policy somewhere much worse. PPO limits how much reward the objective gives for changing any single action's probability, so many minibatch steps on one batch stay close to the policy that collected it.

Explaining the paperProximal Policy Optimization AlgorithmsSchulman, Wolski, Dhariwal, Radford, Klimov · OpenAI · 2017 · arXiv:1707.06347 ↗

TRPO kept each update small with a KL constraint and a second-order solver. PPO gets similar behavior from a min and a clip, a change of a few lines to a vanilla policy gradient, and OpenAI later used it to fine-tune InstructGPT from human feedback.

Data the agent pays for

A supervised model trains on a dataset that already exists. A reinforcement-learning agent has to produce its own data by acting: it runs its current behavior in an environment (a physics simulator, an Atari game), records what happened, and learns from that record. Every batch costs simulator time or real-world interaction, and only a reasonably good policy produces useful batches. Algorithms are therefore compared by sample efficiency, how much the policy improves per timestep of experience.

Standard policy-gradient methods collect a batch, take one gradient step, and throw the batch away. PPO, published by Schulman, Wolski, Dhariwal, Radford and Klimov at OpenAI in July 2017, changes the objective so that the same batch supports several epochs of minibatch updates. It comes out of a line of work on one question, how far a policy may move in one update: conservative policy iteration (2002) posed it, and TRPO (2015) answered it with a KL-divergence constraint solved by second-order optimization. PPO keeps the goal and replaces the machinery with a clipped ratio that ordinary gradient ascent can optimize.

The page builds it in order: the policy gradient and the advantage that weights it; why a batch is normally used once; the trust region TRPO uses to prevent that; the clipped objective; the KL-penalty alternative the paper tested; and the full algorithm with its hyperparameters and results.

The policy gradient

The trained object is a policy πθ\pi_\theta, a neural network with parameters θ\theta that takes the current state ss (joint angles and velocities, or a stack of game frames) and outputs a probability distribution over actions aa. In the paper's MuJoCo experiments it is a two-hidden-layer MLP with 64 tanh units per layer whose output is the mean of a Gaussian over torques, with learned standard deviations. The agent samples its action from that distribution, receives a reward, and moves to a new state. The return is the discounted sum of rewards from a point onward, and training adjusts θ\theta to raise the expected return.

The return depends on θ\theta only through which actions get sampled, and the environment in between is not differentiable, so there is no computation graph from θ\theta to the return to backpropagate through. The score-function identity gets around this. Since ∇θπ=π ∇θlog⁡π\nabla_\theta \pi = \pi\,\nabla_\theta \log \pi, the gradient of an expectation over sampled actions becomes an expectation of ∇θlog⁡π\nabla_\theta \log \pi times the outcome, which a batch of samples can estimate. The paper writes the estimator as

g^=E^t ⁣[ ∇θlog⁡πθ(at∣st) A^t ]\hat{g} = \hat{\mathbb{E}}_t\!\left[\, \nabla_\theta \log \pi_\theta(a_t \mid s_t)\, \hat{A}_t \,\right]
(1)

For each action ata_t taken in the batch, ∇θlog⁡πθ(at∣st)\nabla_\theta \log \pi_\theta(a_t \mid s_t) is the direction in parameter space that makes that action more likely in that state. It is scaled by A^t\hat{A}_t, an estimate of how much better the action was than usual, and E^t\hat{\mathbb{E}}_t is the empirical average over the batch. This is REINFORCE (Williams, 1992) with a baseline. The update is gradient ascent: θ←θ+αg^\theta \leftarrow \theta + \alpha \hat{g}, because the aim is to maximize return. Autodiff frameworks get g^\hat{g} by differentiating an objective whose gradient is (1):

LPG(θ)=E^t ⁣[ log⁡πθ(at∣st) A^t ]L^{PG}(\theta) = \hat{\mathbb{E}}_t\!\left[\, \log \pi_\theta(a_t \mid s_t)\, \hat{A}_t \,\right]
(2)

The paper calls LPGL^{PG} a "loss", following autodiff habit, but it is maximized; code that expects a loss to minimize is handed −LPG-L^{PG}.

The weight A^t\hat{A}_t estimates the advantage:

Aπ(s,a)=Qπ(s,a)−Vπ(s)A^\pi(s,a) = Q^\pi(s,a) - V^\pi(s)

Vπ(s)V^\pi(s) is the expected return from state ss when following the policy, and Qπ(s,a)Q^\pi(s,a) is the expected return when taking action aa first and following the policy after. The difference measures how much better than average the action was in that state. Weighting by the raw return would also give a correct gradient on average, but a noisier one. If every action in some state earns a return near 100, raw returns push up every action taken there, including mediocre ones, and only the small differences between them carry information about which action to prefer. Subtracting a baseline b(s)b(s) that depends only on the state leaves the expected gradient unchanged, because the baseline term sums to zero over the policy's actions:

∑ab(s) ∇θπ(a∣s)=b(s) ∇θ∑aπ(a∣s)=b(s) ∇θ1=0\sum_a b(s)\,\nabla_\theta \pi(a \mid s) = b(s)\,\nabla_\theta \sum_a \pi(a \mid s) = b(s)\,\nabla_\theta 1 = 0

The expectation is unchanged and the variance drops, since each sample's weight is now centered near zero. Figure 1 runs this on a one-dimensional action. The amber curve is the return for each action, which the agent cannot see; the teal bell is the policy. Each step samples a few actions, compares each return to the baseline, and pushes the policy toward the actions above it. Press Play and watch the bell move toward the peak of the amber curve:

Figure 1 · the policy gradient
0%
The return R(a) over actions is fixed and unknown to the agent. The policy samples actions and weights each by its advantage: actions above the baseline V get an up arrow (make more likely), those below it a down arrow. Averaged over the samples this is ∇logπ·A, and the policy climbs toward higher return. Play, or scrub the steps.

Estimating the advantage

The agent never observes AπA^\pi; it has one trajectory of rewards and a learned value network VV. PPO uses generalized advantage estimation (GAE), built from the one-step residual

δt=rt+γ V(st+1)−V(st)\delta_t = r_t + \gamma\, V(s_{t+1}) - V(s_t)
(12)

δt\delta_t compares what the value network predicted at step tt with the reward received plus the discounted prediction one step later. A positive δt\delta_t means the step went better than predicted. The discount γ\gamma (0.99 in every experiment in the paper) makes rewards further ahead count for less. GAE sums the residuals from tt to the end of the collected segment of TT steps, with weights that shrink by γλ\gamma\lambda per step:

A^t=∑l=0T−t−1(γλ)l δt+l\hat{A}_t = \sum_{l=0}^{T-t-1} (\gamma\lambda)^{l}\, \delta_{t+l}
(11)

λ\lambda sets how far the estimate looks ahead. At λ=0\lambda = 0 only δt\delta_t counts: low variance, but the estimate inherits every error in VV. At λ=1\lambda = 1 the sum telescopes to the discounted return actually collected (bootstrapped with V(sT)V(s_T) at the end of the segment) minus V(st)V(s_t). That estimate depends on VV only through the final bootstrap and has high variance. The paper uses λ=0.95\lambda = 0.95, so a residual 11 steps later gets about half the weight of δt\delta_t.

Figure 2 works an 8-step segment. The value network predicts 0.55 at step 0 and 0.60 at step 1, and the step-0 reward is 0, so δ0=0+0.99×0.60−0.55=0.044\delta_0 = 0 + 0.99 \times 0.60 - 0.55 = 0.044. A reward of +1 arrives at step 5 that the network underpredicted. With λ=0\lambda = 0, A^0=0.044\hat{A}_0 = 0.044 and step 0 barely registers as good. With λ=1\lambda = 1, A^0=0.482\hat{A}_0 = 0.482, the Monte Carlo value. The paper's λ=0.95\lambda = 0.95 gives 0.384. Drag λ\lambda and watch the bright bars, the weighted residuals that sum to A^t\hat{A}_t, grow toward the step-5 reward:

Figure 2 · generalized advantage estimation
λ = 0.95
t = 0

Â0 = 0.384 · λ=0 (one step): 0.044 · λ=1 (Monte Carlo): 0.482
weight halves every 11.3 steps

Top: rewards and the learned value of each state; the hollow dot is the bootstrap V(sT). Bottom: each residual δ (faint) and, for the selected step, its weighted contribution (γλ)lδ (bright). The bright bars sum to Ât. Drag λ from 0 (one-step) to 1 (Monte Carlo), and click a column or use the step slider to move t. Toy numbers, γ = 0.99.

GAE with λ<1\lambda < 1 is biased on purpose. The baseline argument above shows that subtracting the exact Vπ(s)V^\pi(s) costs nothing in bias; bootstrapping from a learned VV inside the residuals introduces some wherever VV is wrong, and GAE accepts it for lower variance. None of what follows depends on how A^t\hat{A}_t was computed.

Why a batch is used once

Equation (1) averages over actions sampled from the current policy. After one gradient step, θ\theta has changed, and the batch now comes from a policy that no longer exists. A second step on the same batch computes the gradient of the new policy from actions the new policy would sample with different frequencies, so the estimate is biased, and each further step makes the mismatch larger. The paper puts it directly: multiple steps on LPGL^{PG} with the same trajectory are "not well-justified" and "often [lead] to destructively large policy updates". In its experiments that setting scored similar to or worse than the no-clipping baseline of Section 6.1, the worst row in Table 1.

The standard correction for samples from the wrong distribution is importance sampling: reweight each sample by how much more or less likely the current policy is to take that action than the policy that collected it. The weight is the probability ratio

rt(θ)=πθ(at∣st)πθold(at∣st),rt(θold)=1r_t(\theta) = \frac{\pi_\theta(a_t \mid s_t)}{\pi_{\theta_\text{old}}(a_t \mid s_t)}, \qquad r_t(\theta_\text{old}) = 1

θold\theta_\text{old} is the parameter vector frozen at collection time. Suppose the old policy chose some action with probability 0.30 and, after a few gradient steps, the new policy gives it 0.39. Then rt=1.30r_t = 1.30: the new policy takes that action 30% more often. Every ratio starts at 1 at the beginning of an update. Weighting the advantages by the ratio gives the surrogate objective

LCPI(θ)=E^t ⁣[ πθ(at∣st)πθold(at∣st) A^t ]=E^t ⁣[ rt(θ) A^t ]L^{CPI}(\theta) = \hat{\mathbb{E}}_t\!\left[\, \frac{\pi_\theta(a_t \mid s_t)}{\pi_{\theta_\text{old}}(a_t \mid s_t)}\, \hat{A}_t \,\right] = \hat{\mathbb{E}}_t\!\left[\, r_t(\theta)\, \hat{A}_t \,\right]
(6)

The superscript stands for conservative policy iteration (Kakade and Langford, 2002), where this objective was proposed. At θold\theta_\text{old} its gradient equals (1), since ∇θrt=rt∇θlog⁡πθ\nabla_\theta r_t = r_t \nabla_\theta \log \pi_\theta and every rt=1r_t = 1 there. The TRPO paper showed a related property: this surrogate matches the true expected return to first order around θold\theta_\text{old}, so for small steps, improving it improves the policy.

For large steps nothing in (6) limits the optimizer. Take the action above with A^t=+2\hat{A}_t = +2. Its term rtA^tr_t \hat{A}_t grows linearly in rtr_t: 2.0 at the start, 2.6 at rt=1.3r_t = 1.3, 6.0 at rt=3r_t = 3, with the same slope throughout. Gradient ascent keeps raising the probability of the few actions with large positive advantages far past the range where the batch's estimate of their advantage is reliable. The paper: "Without a constraint, maximization of LCPIL^{CPI} would lead to an excessively large policy update."

TRPO's trust region

TRPO makes "do not move far" an explicit constraint. It measures how different the new policy is from the old one with the KL divergence, a standard score of how different two probability distributions are (zero when they are identical, larger as they separate), averaged over the states in the batch:

max⁡θ E^t ⁣[ rt(θ) A^t ]subject toE^t ⁣[ KL[πθold(⋅∣st), πθ(⋅∣st)] ]≤δ\max_\theta\ \hat{\mathbb{E}}_t\!\left[\, r_t(\theta)\, \hat{A}_t \,\right] \quad\text{subject to}\quad \hat{\mathbb{E}}_t\!\left[\, \mathrm{KL}\big[\pi_{\theta_\text{old}}(\cdot \mid s_t),\, \pi_\theta(\cdot \mid s_t)\big] \,\right] \le \deltamax⁡θ E^t ⁣[ rt(θ) A^t ]subject toE^t ⁣[ KL[πθold(⋅∣st), πθ(⋅∣st)] ]≤δ\begin{aligned} \max_\theta\ & \hat{\mathbb{E}}_t\!\left[\, r_t(\theta)\, \hat{A}_t \,\right] \\ \text{subject to}\quad & \hat{\mathbb{E}}_t\!\left[\, \mathrm{KL}\big[\pi_{\theta_\text{old}}(\cdot \mid s_t),\, \pi_\theta(\cdot \mid s_t)\big] \,\right] \le \delta \end{aligned}
(3)–(4)

The set of policies within the KL budget δ\delta is the trust region: the neighborhood of θold\theta_\text{old} where the surrogate is trusted as a stand-in for the return. The KL is written with the old policy first, KL[πθold,πθ]\mathrm{KL}[\pi_{\theta_\text{old}}, \pi_\theta], and the order matters because KL is not symmetric. For two Gaussians over one action with the same standard deviation σ\sigma, it reduces to

KL=(μnew−μold)22σ2\mathrm{KL} = \frac{(\mu_\text{new} - \mu_\text{old})^2}{2\sigma^2}

so TRPO's δ=0.01\delta = 0.01 allows the mean to move by 0.02 σ≈0.14 σ\sqrt{0.02}\,\sigma \approx 0.14\,\sigma. In Figure 3 the amber curve is the old policy; drag the new policy's mean and watch the KL bar cross δ\delta at the edge of the shaded band:

Figure 3 · the trust region
KL = 0.10

within the trust region, surrogate still trustworthy

The old policy is fixed; shifting the new policy raises the KL divergence between them. The shaded band is the trust region, the new policies with KL ≤ δ. TRPO accepts any step inside it and rejects the rest. (δ is enlarged here for legibility; TRPO used δ = 0.01.)

TRPO's theory calls for a penalty rather than a constraint, that is, maximizing

max⁡θ E^t ⁣[ rt(θ) A^t−β KL[πθold(⋅∣st), πθ(⋅∣st)] ]\max_\theta\ \hat{\mathbb{E}}_t\!\left[\, r_t(\theta)\, \hat{A}_t - \beta\, \mathrm{KL}\big[\pi_{\theta_\text{old}}(\cdot \mid s_t),\, \pi_\theta(\cdot \mid s_t)\big] \,\right]
(5)

because a version of this surrogate that uses the maximum KL over states, rather than the mean, is a lower bound on the policy's true performance. Raising a lower bound guarantees that the true return does not fall, which gives monotonic improvement. The practical algorithm gives up that guarantee twice: it replaces the maximum KL with the mean in (4), and it swaps the penalty for a hard constraint. It uses a constraint because, per the PPO paper, no single fixed β\beta works across different problems, "or even within a single problem, where the characteristics change over the course of learning".

TRPO solves (3)–(4) approximately with the conjugate gradient algorithm, using a linear approximation of the objective and a quadratic approximation of the constraint, followed by a line search. Conjugate gradient with a line search is a second-order method, and the PPO paper lists its costs: TRPO is "relatively complicated" and does not fit architectures with noise such as dropout, or with parameters shared between the policy and value function. PPO's goal is TRPO's data efficiency and reliability "while using only first-order optimization".

The clipped objective

The failure in (6) was that rtA^tr_t \hat{A}_t keeps growing as the ratio moves further from 1. PPO removes that growth outside a band around 1. It clips the ratio to [1−ϵ, 1+ϵ][1-\epsilon,\ 1+\epsilon] and takes the minimum of the clipped and unclipped terms:

LCLIP(θ)=E^t ⁣[ min⁡ ⁣(rt(θ) A^t,  clip(rt(θ), 1−ϵ, 1+ϵ) A^t) ]L^{CLIP}(\theta) = \hat{\mathbb{E}}_t\!\left[\, \min\!\Big( r_t(\theta)\, \hat{A}_t,\ \ \mathrm{clip}\big(r_t(\theta),\, 1-\epsilon,\, 1+\epsilon\big)\, \hat{A}_t \Big) \,\right]
(7)

ϵ\epsilon is a hyperparameter; the paper's example value is 0.2, which is also the best value in its sweep. The first term inside the min is LCPIL^{CPI}. The clipped term, in the paper's words, "removes the incentive for moving rtr_t outside of the interval". Which clip matters depends on the sign of the advantage.

Positive advantage. The gradient raises the action's probability, so rtr_t grows. The term follows rtA^tr_t \hat{A}_t up to rt=1+ϵr_t = 1+\epsilon and then stays flat at (1+ϵ)A^t(1+\epsilon)\hat{A}_t. Past that point this sample's gradient is exactly zero. The lower clip 1−ϵ1-\epsilon never binds for a positive advantage.

Negative advantage. The gradient lowers the action's probability, so rtr_t shrinks. Now the lower clip binds: the term is flat at (1−ϵ)A^t(1-\epsilon)\hat{A}_t for rt<1−ϵr_t < 1-\epsilon and follows rtA^tr_t \hat{A}_t everywhere above that. Written per sign, the term is

min⁡(rt, 1+ϵ) A^t  if A^t≥0,max⁡(rt, 1−ϵ) A^t  if A^t<0\min(r_t,\ 1+\epsilon)\,\hat{A}_t \ \ \text{if } \hat{A}_t \ge 0, \qquad \max(r_t,\ 1-\epsilon)\,\hat{A}_t \ \ \text{if } \hat{A}_t < 0

The min becomes a max in the second case because multiplying by a negative A^t\hat{A}_t reverses the order.

With the numbers from before and ϵ=0.2\epsilon = 0.2: the action with A^t=+2\hat{A}_t = +2 at rt=1.30r_t = 1.30 has an unclipped term of 2.60 and a clipped term of 1.2×2=2.401.2 \times 2 = 2.40. The min is 2.40, the flat branch, so the objective no longer rewards raising that action's probability. Figure 4 plots one sample's term against rr. Switch the sign of the advantage, move rr past each edge of the band, and read dL/drdL/dr in the line under the plot:

Figure 4 · the clipped objective
r = 1.00

ε = 0.20 · L = 1.00 · dL/dr = +1 · inside [1−ε, 1+ε]: gradient active

One timestep's term versus the ratio r, with |A| = 1. The clipped objective follows the unclipped r·A until r crosses the binding edge of [1−ε, 1+ε], then goes flat (amber zone, zero gradient). On the opposite side the min keeps r·A (violet zone), so the gradient stays on. The red dot is r = 1, where every update starts. Toggle the sign of A, drag r and ε.

Keeping each update near the old policy is what proximal refers to. There is no KL computation in (7), no Fisher matrix, no conjugate gradient and no line search: the objective is a min, a clip and one hyperparameter, and any autodiff framework differentiates it. Because it only changes the objective, it works unchanged with a network that shares layers between the policy and the value function, which TRPO's constraint made difficult.

The clip approximates the trust region and does not reproduce it. TRPO bounds the average KL of the whole update. The clip acts on each sample separately: once a sample's ratio leaves the band on the improving side, that sample stops contributing gradient, so the samples still pulling the parameters are those still inside the band or pushed out on the worsening side (next section). Nothing bounds how far the shared parameters move the other samples in the meantime, and the paper states no KL guarantee for LCLIPL^{CLIP}.

Why the objective takes a minimum

Clipping alone would flatten a good action's term past 1+ϵ1+\epsilon, but it would also flatten it below 1−ϵ1-\epsilon, where the action has become less likely than before. The min restores the unclipped term there. The paper: "we only ignore the change in probability ratio when it would make the objective improve, and we include it when it makes the objective worse."

Take the bad-action case with numbers. The old policy chose an action with probability 0.30 and it had A^t=−1.5\hat{A}_t = -1.5, but updates driven by other samples have raised it to 0.40, so rt=1.333r_t = 1.333. The unclipped term is 1.333×(−1.5)=−2.001.333 \times (-1.5) = -2.00; the clipped term is 1.2×(−1.5)=−1.801.2 \times (-1.5) = -1.80. The min picks −2.00-2.00, the unclipped branch, so this sample's gradient is still A^t=−1.5\hat{A}_t = -1.5 per unit of ratio and it pulls rtr_t back down. A clip without the min would have used −1.80-1.80, a flat branch with zero gradient, and left the mistake uncorrected. This is the violet zone in Figure 4.

Since the min never exceeds its unclipped argument, LCLIP≤LCPIL^{CLIP} \le L^{CPI} for every θ\theta. The two are equal while every ratio is inside its band, and in particular, as the paper notes, to first order around r=1r = 1. The paper calls LCLIPL^{CLIP} a pessimistic lower bound on the unclipped objective. It bounds the surrogate, not the true return; the bound on the return belongs to TRPO's max-KL theory.

Figure 5 reconstructs the paper's Figure 2, which interpolates the parameters from θold\theta_\text{old} to the result of one PPO update and evaluates the objectives along the way. Here the batch is synthetic. The unclipped LCPIL^{CPI} keeps rising the further the policy moves. LCLIPL^{CLIP} rises, peaks, and then falls, because past the peak the samples on the worse side of their band are still counted at full cost while the samples on the improving side no longer add anything. In the paper the peak sits at the updated policy, whose KL from the old one is about 0.02:

Figure 5 · a lower bound with a built-in penalty
L^CLIP=0.06

KL=0.021 · L^CPI=0.08 · L^CLIP peaks near KL=0.020, then falls

Moving right optimizes one batch harder. The unclipped surrogate L^CPI rises without limit; L^CLIP rises, peaks at a small KL, then declines, so its maximum is a natural stopping point. KL (violet) grows throughout. Drag the distance and switch ε. A reconstruction of the paper's Figure 2 on a synthetic minibatch.

A small calculation connects ϵ\epsilon to a KL. Take the one-action Gaussian from Figure 3 with σ=1\sigma = 1 and move its mean by 0.2. The KL is 0.22/2=0.020.2^2 / 2 = 0.02. The log-ratio for an action aa is 0.2 (a−μold)−0.020.2\,(a - \mu_\text{old}) - 0.02, so an action one standard deviation above the old mean has r=e0.18=1.197r = e^{0.18} = 1.197, right at the 1+ϵ1+\epsilon edge for ϵ=0.2\epsilon = 0.2, and one two standard deviations above it has r=e0.38=1.46r = e^{0.38} = 1.46. In this toy, a clip of 0.2 starts to bind on typical good actions at about the KL the paper reports after one update.

The adaptive KL penalty

The paper also tests the direct alternative: keep TRPO's penalty form (5) and optimize it with SGD, adjusting β\beta so that each update lands near a target KL dtargd_\text{targ}. Each policy update first runs several epochs of minibatch SGD on

LKLPEN(θ)=E^t ⁣[ rt(θ) A^t−β KL[πθold(⋅∣st), πθ(⋅∣st)] ]L^{KLPEN}(\theta) = \hat{\mathbb{E}}_t\!\left[\, r_t(\theta)\, \hat{A}_t - \beta\, \mathrm{KL}\big[\pi_{\theta_\text{old}}(\cdot \mid s_t),\, \pi_\theta(\cdot \mid s_t)\big] \,\right]
(8)

and then measures d=E^t[KL[πθold,πθ]]d = \hat{\mathbb{E}}_t[\mathrm{KL}[\pi_{\theta_\text{old}}, \pi_\theta]] and updates β\beta for the next policy update:

d<dtarg/1.5  ⇒  β←β/2,d>1.5 dtarg  ⇒  β←2βd < d_\text{targ}/1.5 \;\Rightarrow\; \beta \leftarrow \beta/2, \qquad d > 1.5\, d_\text{targ} \;\Rightarrow\; \beta \leftarrow 2\beta

With dtarg=0.01d_\text{targ} = 0.01, an update that reaches a KL below 0.0067 halves the penalty and one above 0.015 doubles it. The factors 1.5 and 2 were "chosen heuristically", and the paper reports the algorithm is not very sensitive to them or to the initial β\beta. Figure 6 runs the rule on a toy model in which the KL an update reaches is proportional to 1/β1/\beta times a pull that drifts 25-fold over training. Compare adaptive β\beta against a fixed β=1\beta = 1, and count the updates that land in the band:

Figure 6 · adapting the KL penalty
update 60

β = 0.250 · d = 0.0180 · d > 1.5·d_targ → β doubles to 0.500

Top: the KL each update reaches (log scale); teal points fall inside [dtarg/1.5, 1.5 dtarg], amber ones outside. Bottom: the penalty β, with a marker at each halving or doubling. With β fixed at 1 the KL follows the drift; the adaptive rule pulls it back within an update or two. A toy model of the Section 4 rule. Switch the rule and the target, then play or scrub.

At dtarg=0.01d_\text{targ} = 0.01 the adaptive rule keeps 37 of the toy's 60 updates in the band against 8 for the fixed penalty, which misses because the pull drifts during training, the change "within a single problem" that the paper gives as the reason a fixed β\beta is not enough. On the real benchmark the penalty variants work but trail the clip: the best adaptive setting (dtarg=0.01d_\text{targ} = 0.01) scores 0.74 and the best fixed one (β=3\beta = 3) 0.72, against 0.82 for clipping at ϵ=0.2\epsilon = 0.2. The paper keeps the penalty as "an important baseline" and recommends the clip.

The full algorithm

A practical PPO objective adds two terms to the clip. When the policy and value function share a network, the shared layers also need the value network's error signal, so a value loss enters the objective. An entropy bonus SS rewards the policy for keeping its action distribution spread out, which keeps it exploring:

LtCLIP+VF+S(θ)=E^t ⁣[ LtCLIP(θ)−c1 LtVF(θ)+c2 S[πθ](st) ]L_t^{CLIP+VF+S}(\theta) = \hat{\mathbb{E}}_t\!\left[\, L_t^{CLIP}(\theta) - c_1\, L_t^{VF}(\theta) + c_2\, S\big[\pi_\theta\big](s_t) \,\right]
(9)
LtVF(θ)=(Vθ(st)−Vttarg)2L_t^{VF}(\theta) = \big(V_\theta(s_t) - V_t^{\text{targ}}\big)^2

Expression (9) is maximized, "approximately", once per iteration. The value error is subtracted because it should be small; the entropy is added because it should be large. Code that minimizes a loss negates all of (9), which flips all three signs. The paper does not define VttargV_t^{\text{targ}}; the official code uses A^t+V(st)\hat{A}_t + V(s_t), the GAE advantage plus the old value prediction, which at λ=0.95\lambda = 0.95 is a mix of observed rewards and bootstrapped values. On MuJoCo the paper uses separate policy and value networks, so c1c_1 has no effect, and no entropy bonus. On Atari the networks share parameters, with c1=1c_1 = 1 and c2=0.01c_2 = 0.01.

The loop (Algorithm 1): each iteration, NN actors run the frozen policy πθold\pi_{\theta_\text{old}} in parallel for TT timesteps each and compute advantages. The objective is then optimized on those NTNT samples for KK epochs (an epoch is one pass over all of them) with minibatches of size M≤NTM \le NT, using minibatch SGD or, "usually for better performance", Adam. Finally θold←θ\theta_\text{old} \leftarrow \theta and the next batch is collected. The paper's three settings give different amounts of reuse:

In Figure 7, drag KK to change how many epochs each collected batch supports:

Figure 7 · one PPO iteration
K = 10

one rollout → 10 epochs over the same data (the paper's MuJoCo setting)

N actors collect T timesteps each into a buffer of NT samples; the same buffer is reused for K epochs of clipped ascent before θold is refreshed and fresh data is collected. Drag K from 1 to 20; the readout names the paper's setting at K = 3, 10 and 15.

The same iteration in code. The ratio is computed as the exponential of a difference of log-probabilities, which avoids dividing small probabilities, and the last lines show the ascent-as-negated-loss convention. The official implementation also standardizes the advantages in each batch to zero mean and unit variance before the epochs start, a detail the paper does not mention.

# one PPO iteration (Algorithm 1, actor-critic style)
data = []
for actor in range(N):                  # N actors, in parallel
    traj = run(pi_old, T)               # T timesteps with the frozen policy
    adv  = gae(traj, V, gamma, lam)     # A_hat_t, eqs (11)-(12)
    ret  = adv + V(traj.s)              # value target (official code)
    data += zip(traj, adv, ret, logp(pi_old, traj))   # keep old log-probs

for epoch in range(K):                  # reuse the SAME data K times
    for mb in minibatches(data, M):     # M <= N*T
        r      = exp(logp(pi, mb) - mb.logp_old)       # ratio r_t, eq (6)
        unclip = r * mb.adv
        clip   = clamp(r, 1 - eps, 1 + eps) * mb.adv
        L_clip = mean(min(unclip, clip))               # eq (7)
        L_vf   = mean((V(mb.s) - mb.ret) ** 2)         # squared error
        L      = L_clip - c1 * L_vf + c2 * mean(ent(pi, mb))  # eq (9)
        loss   = -L                     # frameworks minimize, so negate
        loss.backward(); adam.step()

pi_old = copy(pi)                       # then collect a fresh batch

Figure 8 shows why the repeated epochs stay controlled. It optimizes one fixed minibatch of ten samples twice, once on LCPIL^{CPI} and once on LCLIPL^{CLIP}, and plots each sample's ratio in the strip below the curves. Scrub to epoch 10 and compare where the two rows of dots end up:

Figure 8 · K epochs on one batch
epoch 0.0

mean |r−1|: 0.00 clipped · 0.00 unclipped · ε = 0.2

One fixed minibatch, optimized by plain gradient ascent for 10 epochs under each objective. Under the unclipped L^CPI every ratio keeps moving and the dots in the strip drift far outside the band. Under L^CLIP each sample's gradient stops once its ratio crosses the binding edge of 1±ε, so the ratios collect at the band edges and later epochs change almost nothing. A toy simulation (real formulas, synthetic advantages, independent per-sample ratios, ε = 0.2, K = 10).

In the toy each sample has its own ratio, so a sample that stops is never moved again. In a real network the samples share parameters, and a stopped sample's ratio can still drift because of the others. That residual drift is one reason the clip gives no hard bound on the KL.

Results

The first experiment compares the surrogate objectives on 7 MuJoCo tasks (HalfCheetah, Hopper, InvertedDoublePendulum, InvertedPendulum, Reacher, Swimmer, Walker2d), one million timesteps each, 3 seeds per task. Each run is scored by its average total reward over the last 100 episodes, rescaled per environment so that a random policy scores 0 and the best result scores 1, and the 21 runs are averaged into one number per setting. Select a bar to read its setting:

Figure 9 · which surrogate wins
ε=0.2

ε=0.2 → 0.82 · Clipping with ε=0.2. The winner, and the value the paper reuses for the MuJoCo algorithm comparison (Atari uses 0.1×α).

Average normalized score on 7 MuJoCo tasks (Table 1). Clipping at ε = 0.2 scores highest (0.82). With neither clipping nor a penalty the average is −0.39: on HalfCheetah the policy ends far below the random policy. The KL-penalty variants (adaptive dtarg, fixed β) reach 0.62 to 0.74. Click a bar or use the slider.

ϵ=0.2\epsilon = 0.2 beats 0.1 (0.76) and 0.3 (0.70), and the paper reuses it for the later MuJoCo comparison. The value comes from this sweep in Section 6.1; it is not a row of Table 3. The −0.39-0.39 for "no clipping or penalty" is the unbounded ratio from (6) in practice: repeated epochs on LCPIL^{CPI} drive HalfCheetah to a score far worse than the random initial policy, enough to pull the 7-task average below zero.

Against other algorithms on the same tasks (TRPO, the cross-entropy method, vanilla policy gradient with an adaptive step size, A2C, and A2C with a trust region), PPO with ϵ=0.2\epsilon = 0.2 "outperforms the previous methods on almost all the continuous control environments". On Roboschool it trains a 3D humanoid to run, to steer toward a target that moves every 200 timesteps or when reached, and, in the hardest task, to get up off the ground while being pelted by cubes.

Atari is closer. Over 49 games, with the winner of each game decided by the average of three runs, PPO wins 30 games on average reward over all of training, against 18 for ACER (actor-critic with experience replay, which also learns from stored off-policy samples and adds its own trust-region step) and 1 for A2C (the synchronous version of A3C). That metric rewards learning fast. On average reward over the last 100 episodes, which rewards final performance, ACER wins 28 games, PPO 19, A2C 1, with 1 tie. The paper's own summary is that PPO does significantly better than A2C in sample complexity and similarly to ACER "though it is much simpler".

That simplicity drove adoption: the change to a policy-gradient implementation is a few lines, it runs on Adam with a shared policy-value network, and it has one main hyperparameter, ϵ\epsilon. The human-preference paper of Christiano et al. appeared five weeks before PPO and used A2C and TRPO. Later RLHF work used PPO, including InstructGPT (2022), which fine-tunes GPT-3 against a learned reward model with PPO plus a per-token KL penalty from the supervised model. That penalty does a job similar to the clip's, holding the fine-tuned model near a reference policy, here the supervised model rather than θold\theta_\text{old}. Methods such as DPO later removed the RL loop from preference tuning altogether.

Provenance Verified against primary literatureHow we verify
REINFORCE / PG theoremThe score-function policy gradient ∇log π · A of Eq. (1) (Williams 1992; Sutton et al. 2000). The paper presents it without attribution as "the most commonly used gradient estimator".
CPI (Kakade & Langford 2002)The ratio-times-advantage surrogate L^CPI that PPO clips, and the source of the CPI superscript.
TRPO (Schulman et al. 2015)The KL trust region, and the max-KL lower bound on the return that PPO emulates with a first-order method.
GAE (Schulman et al. 2015)The advantage estimator  that weights every term of the surrogate.
OpenAI baselines, ppo1 (official code)pposgd_simple.py L110-115: ratio = exp(logp_new − logp_old), loss = −mean(min(surr1, surr2)) + value loss − entcoeff·entropy. L78: value target = GAE advantage + V(s). L169: advantages standardized per batch. The paper states none of the last two. run_mujoco.py L16-19 matches Table 3 with one environment and a linearly annealed step size.
correctionL^CLIP is a lower bound on the unclipped surrogate L^CPI (Section 3), not on the policy’s true return. The Introduction’s looser wording ("a pessimistic estimate (i.e., lower bound) of the performance of the policy") conflates the two. The bound on the true return is TRPO’s, it needs the maximum KL over states, and the practical constraint in Eq. (4) already relaxes it to the mean KL; PPO keeps the intuition and carries no monotonic-improvement proof. Separately, Eqs. (10) and (11) print the exponent on the last reward and residual as T−t+1; the pattern requires T−t−1, and this page uses the clean form (γλ)^l.

Questions you might still have

?

Why take many small clipped steps instead of one large gradient step?
The surrogate is only a reliable estimate of improvement near the policy that collected the batch. One large step can leave that neighborhood before anything checks it. Many small steps on the clipped objective each follow a gradient that is still valid, and each sample stops contributing once its ratio leaves the band, so later epochs change the policy less and less.

?

Does clipping keep the KL divergence below a fixed limit?
No. The clip removes the incentive to push any single sample’s ratio past 1 ± ε, but nothing in the objective measures or bounds the KL, and a shared network can still move samples whose own gradients are zero. The paper reports a KL of about 0.02 after one update on Hopper. Many later implementations add an explicit KL check that stops the epochs early; that is later practice, not part of the paper.

?

What does PPO inherit from TRPO?
The idea that an update should stay near the old policy so the surrogate remains trustworthy. It does not inherit the theorem: TRPO’s monotonic-improvement bound needs the maximum KL over states, and PPO replaces the constraint with a clip that a first-order optimizer can handle.

?

Is the clipped objective a lower bound on the true return?
No. It is a lower bound on the unclipped surrogate L^CPI. The lower bound on the return belongs to TRPO’s theory, through a penalty on the maximum KL.

?

Does PPO always run ten epochs per batch?
No. K = 10 is the MuJoCo setting (Table 3). The Atari runs use K = 3 and the Roboschool humanoid runs use K = 15. The paper’s general phrase is "several epochs".

?

Where does the common value-loss coefficient c1 = 0.5 come from?
Not from this paper. Its only stated c1 is 1, for Atari, where the policy and value function share a network. The MuJoCo runs use separate networks, so c1 has no effect there. The value 0.5 is a default in later libraries such as Stable-Baselines.

?

Is PPO on-policy?
Yes. Every batch comes from the current policy, and it is discarded after K epochs. The ratio corrects for the small drift that accumulates within those epochs, and the clip keeps that drift small. Off-policy methods such as soft actor-critic instead keep a replay buffer of old experience.

?

Did the 2017 human-preferences paper by Christiano et al. use PPO?
No. It appeared in June 2017, predates PPO by about five weeks and used A2C and TRPO. PPO became the RL stage of later RLHF work, including InstructGPT (2022), which adds a per-token KL penalty from the supervised model and initializes the value function from the reward model.

Footnotes & further reading

  1. The paper: Schulman, Wolski, Dhariwal, Radford, Klimov, Proximal Policy Optimization Algorithms (OpenAI, 2017; v1 20 July, v2 28 August). Official code: openai/baselines, ppo1. A clear secondary reference is OpenAI's Spinning Up page.
  2. The trust region it descends from: Schulman, Levine, Moritz, Jordan, Abbeel, Trust Region Policy Optimization (2015), with the max-KL lower bound that PPO emulates with a first-order method. See also the TRPO explainer.
  3. The advantage estimator: Schulman, Moritz, Levine, Jordan, Abbeel, High-Dimensional Continuous Control Using Generalized Advantage Estimation (GAE, 2015). The clean GAE weights are γl\gamma^l on rewards and (γλ)l(\gamma\lambda)^l on residuals.
  4. The surrogate's origin: Kakade and Langford, Approximately Optimal Approximate Reinforcement Learning (ICML 2002), the conservative policy iteration that names LCPIL^{CPI}.
  5. The policy gradient itself: Williams, Simple Statistical Gradient-Following Algorithms (REINFORCE, 1992), and Sutton, McAllester, Singh, Mansour, Policy Gradient Methods for RL with Function Approximation (2000).
  6. PPO in RLHF: Ouyang et al., Training language models to follow instructions with human feedback (InstructGPT, 2022), whose RL stage is PPO with a per-token KL penalty from the SFT model. The earlier Deep RL from Human Preferences (Christiano et al., 2017) used A2C and TRPO.