# `Monty.Frameworks.Models.MotorPolicies.InformedPolicyRandomWalk`
[🔗](https://github.com/d-led/ex.tbp.monty/blob/v0.1.0/packages/ex_tbp_monty_core/lib/monty/frameworks/models/motor_policies/informed_policy_random_walk.ex#L1)

The random walk `InformedPolicy` does, on its own.

Mirrors `tbp/monty/frameworks/models/motor_policies.py::InformedPolicyRandomWalk`.
`InformedPolicy` is a walk *with* a recovery rule: sample while the sensor is
on the object, and step back while it is not. This policy is that rule without
the rest of `InformedPolicy`, which is what the distant agent's motor-system
configs ask for as their selector's default (`distant_2`, `distant_5`): the
selector routes goals to `JumpToGoal` and `LookAtGoal`, and between goals the
body wanders.

There is no momentum here, whatever the word "random walk" suggests: every
step is an independent draw from the sampler. Monty's own docstring says as
much — this reproduces what `InformedPolicy` did rather than proposing a
better walk — and the `alpha` momentum belongs to `SurfacePolicy`'s tangential
direction, not to this policy.

The remembered action is inverted every time it is used, so a sensor that keeps
leaving the object walks back and forth across the edge instead of away.

# `t`

```elixir
@type t() :: %Monty.Frameworks.Models.MotorPolicies.InformedPolicyRandomWalk{
  action_sampler: Monty.Frameworks.Actions.ActionSamplers.ActionSampler.t(),
  agent_id: atom() | String.t(),
  rng: :rand.state() | nil,
  undo_action: Monty.Frameworks.Actions.Action.t() | nil
}
```

# `call`

```elixir
@spec call(
  t(),
  Monty.Context.t(),
  map() | nil,
  Monty.Frameworks.Models.MotorSystemState.t(),
  Monty.Cmp.Message.t() | nil,
  Monty.Cmp.Goal.t() | nil
) :: {Monty.Frameworks.Models.MotorPolicies.MotorPolicyResult.t(), t()}
```

A sampled step on the object, the step back off it, or nothing at all.

The goal and the motor-system state are ignored: this policy is input-driven,
and the only input it reads is whether the sensor is still on the object.

# `new`

```elixir
@spec new(keyword()) :: t()
```

A walk for `:agent_id`, sampling from `:action_sampler`.

# `reset`

```elixir
@spec reset(t()) :: t()
```

Starts the next episode with nothing to step back to.

# `state_dict`

```elixir
@spec state_dict(t()) :: map()
```

The action it would step back with, which is all it knows.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
