ReAct: reasoning and acting — a complete guide
A model reasoning in a vacuum will happily invent a fact, a date, or a quote. ReAct fixes that by letting the model interleave its thinking with real actions — search, calculate, query a database — and feed each result back into the next thought. The idea comes from "ReAct: Synergizing Reasoning and Acting in Language Models" (Yao et al., 2022, Princeton and Google Research). On the interactive benchmarks ALFWorld and WebShop, ReAct beat imitation- and reinforcement-learning baselines by 34% and 10% absolute success rate, while using only one or two in-context examples.
See it work
Ask a plain model a question that needs current, external facts and it guesses from memory:
Question: What is the current temperature in the city where the Eiffel Tower is located?
Answer: It's around 15°C in Paris right now.
[The model has no live weather access. This number is invented.]
Same question, ReAct style. The model thinks, acts, observes, and only then answers:
Question: What is the current temperature in the city where the Eiffel Tower is located?
Thought: I need the city first, then its current weather.
Action: search("Eiffel Tower location")
Observation: The Eiffel Tower is located in Paris, France.
Thought: Now I get the live weather for Paris.
Action: get_weather("Paris, France")
Observation: Paris: 18°C, partly cloudy.
Thought: I have what I need.
Final Answer: It's currently 18°C and partly cloudy in Paris.
The answer is now grounded in two real tool results instead of the model's parametric memory. Same model, very different reliability.
The mental model
Think of a careful detective. A guesser blurts out a theory. A detective reasons about what to check, goes and checks it, reads what came back, and updates the theory before speaking. ReAct turns the model into the detective: every claim it commits to has an observation behind it.
Reasoning decides what to do next; acting grounds that reasoning in reality. Neither alone is as strong as the loop between them.
How it works
ReAct runs a loop. Each turn is a Thought (reasoning), an optional Action (a tool call), and the Observation that comes back. The loop repeats until the model decides it can answer.
- Thought — the model reasons about the current state: plan a step, pick a tool, shape the parameters, or interpret the last observation.
- Action — it emits a structured call like
search("query")orget_weather("Paris"). Your system parses and executes it. - Observation — the tool's result is fed back into the context as plain text. Successes, errors, and empty results all return here.
- Loop — the new observation seeds the next thought. The cycle continues until the model writes a Final Answer.
The feedback loop is what makes it self-correcting. When an action fails, the error shows up as an observation, and the next thought can adapt:
Action: get_weather("London")
Observation: Error - multiple cities named London. Specify a country.
Thought: The API needs more detail. I'll assume London, UK.
Action: get_weather("London, UK")
Observation: 15°C, rainy.
Why it works
| Factor | What it buys you |
|---|---|
| Grounding through action | Facts come from live, verifiable sources, not the model's training cutoff. This directly cuts hallucination. |
| Reasoning as scaffolding | Thoughts handle planning, tool selection, parameter construction, and result interpretation — the glue a bare tool call lacks. |
| Feedback loop | Observations let the model detect and recover from errors mid-task instead of compounding them. |
| Task decomposition | Complex questions get broken into ordered sub-steps the model can solve one at a time. |
| Transparency | The thought/action/observation trace is human-readable, so you can see exactly where reasoning went wrong. |
Where it shines
ReAct fits any task that needs information or actions the model can't supply from memory: multi-hop question answering, fact verification, data analysis, code execution, and multi-step planning. The interactive, decision-making tasks — navigating an environment, completing a transaction — are where it pulls furthest ahead of pure reasoning.
Reported production deployments give a feel for the payoff (figures are from real-world case studies, illustrative of typical gains rather than a single controlled study):
- Customer support — autonomous agents with access to order databases and shipping APIs resolve around 70% of tier-1 queries, with average resolution dropping to roughly 2 minutes from 15 with a human agent.
- Code debugging — agents that run code, search docs, and propose fixes handle about 60% of common bugs, cutting average debug time from 45 minutes to about 10.
- Research — literature-review agents run roughly 10x faster, analyzing 100-plus papers and synthesizing them with citations.
- Data analysis — natural-language-to-SQL agents cut routine analyst workload by about 80%, turning days of waiting into minutes.
- Travel planning — multi-tool agents assemble a full budget-bound trip in about 5 minutes, with user-satisfaction ratings near 4.8 out of 5.
- Legal research — case-law agents surface relevant precedents roughly 5x faster.
When to use it (and when not)
Reach for ReAct when:
- The task needs up-to-date or verifiable information the model can't hold in its weights.
- It takes several dependent steps, where each action depends on the last result.
- You want a transparent, auditable trace of how the answer was reached.
- The information need is uncertain and the agent must explore.
Skip it when:
- The task is pure reasoning (math, logic) with no external facts needed — chain of thought is cheaper and just as good.
- A single retrieval step answers the question — plain RAG is simpler.
- Latency or cost is critical and a direct generation suffices.
Every cycle is an LLM call. A 10-step ReAct task can mean roughly 20-30 model calls (a thought and an action per step, plus observation handling), pushing latency to about 2-10 seconds versus under 1 second for direct generation. Tool selection also degrades once you pass roughly 50 tools, and even a 200K-token context window can be exhausted by very long trajectories. Budget for the round trips before you ship.
Model fit. ReAct is a prompting pattern, so it runs on any capable instruction-following model. Modern models (Claude, GPT-4, Gemini) add native tool use / function calling, which is the cleanest way to implement it — see the comparison below. Small models tend to fumble the thought/action format and tool selection.
Escalation. Start with chain of thought; move to RAG when you need one external lookup; adopt ReAct when the task becomes multi-step and adaptive; layer on Reflexion or multi-agent patterns when single-trajectory ReAct stalls.
| Variant / alternative | When to choose it |
|---|---|
| Chain of thought | Pure reasoning, no external info needed. |
| RAG | A single, known retrieval covers the information need. |
| Few-shot prompting | The task is pattern-matching with no external actions. |
| Function calling API | The native mechanism to implement ReAct cleanly with structured calls. |
| Reflexion | ReAct plus self-reflection and memory, for tasks that need retries. |
| Self-consistent ReAct | Run several trajectories and vote, when robustness matters more than cost. |
Anatomy of a ReAct prompt
Four building blocks repeat through every trajectory:
- Thought traces — planning, tool selection, parameter construction, observation analysis, error handling, and final synthesis. These are the reasoning steps that connect actions.
- Actions — structured tool calls of the form
tool_name(param="value"). Common categories: information retrieval (search,lookup,database_query), computation (calculate,python), external APIs (get_weather,get_stock_price), knowledge bases (wikipedia,document_search), and environment actions (send_email,create_calendar_event). - Observations — the text returned from an action: success-with-data, error messages, partial results, or empty results. All of them flow back into context.
- Final answer — the synthesized response, built strictly from observations.
A workable prompt template wires these together and shows the model the format:
You are an agent that solves tasks with reasoning and actions.
Available tools:
- search(query): search the web
- calculate(expression): do math
- get_weather(location): current weather
- wikipedia(topic): look up a topic
Format:
Thought: your reasoning about what to do next
Action: tool_name(parameters)
Observation: result from the action (filled in by the system)
... (repeat Thought/Action/Observation as needed)
Final Answer: your final response
Guidelines:
1. Always start with a Thought to plan.
2. Use only the listed tools; never invent tool names.
3. If an action fails, try a different approach.
4. Base the Final Answer only on Observations, not assumptions.
Question: {question}
Thought:
The loop in code
The mechanism is small. Generate a thought, decide whether you're done, otherwise execute an action and append the observation:
def react_loop(question, tools, max_iterations=10):
"""Minimal ReAct reasoning-and-acting loop."""
context = f"Question: {question}\n"
for _ in range(max_iterations):
thought = llm.generate(context + "Thought:")
if "final answer" in thought.lower():
return llm.generate(context + "Final Answer:")
action = llm.generate(context + f"Thought: {thought}\nAction:")
name, params = parse_action(action) # e.g. ('search', {'query': '...'})
if name not in tools:
observation = f"Error: unknown tool '{name}'. Available: {list(tools)}"
else:
try:
observation = tools[name](**params)
except Exception as e: # surface failures as observations
observation = f"Error executing {name}: {e}"
context += f"Thought: {thought}\nAction: {action}\nObservation: {observation}\n"
return "Unable to complete the task within the iteration limit."
Two details carry most of the robustness: a hard max_iterations cap so a stuck agent can't loop forever, and routing tool failures back as observations so the model can recover instead of crashing.
Configuration that matters
| Parameter | Guidance |
|---|---|
max_iterations | Hard ceiling on thought/action cycles (a common default is 10). Prevents runaway loops. |
| Temperature | Low for deterministic tool use; raise to about 0.7 only when running multiple trajectories to vote. |
| Stop sequences | Stop generation at Observation: so the system, not the model, fills in real results. |
| Tool count | Keep the set focused; selection accuracy drops past roughly 50 tools. Categorize or filter when you have more. |
| Context budget | Summarize or trim old cycles as the trajectory grows so long tasks don't blow the window. |
Implementation workflow
- Define tools — give each a clear name, description, and parameter schema. The description is how the model decides when to call it.
- Write the prompt — state the format, list the tools, and add guidelines (plan first, only use listed tools, recover from failures, answer from observations).
- Parse actions — extract the tool name and parameters from each
Action:line; validate before executing. - Execute and observe — run the tool, format the result (or error) as an observation, append it.
- Manage the loop — enforce
max_iterations, detect completion, and trim context when it grows. - Test and measure — evaluate on held-out tasks against the metrics below.
Do: keep thoughts specific and purposeful, name the tool you'll use and why, analyze each observation before the next action, and stop as soon as you have enough.
Don't: let the model invent tools, repeat a failed action verbatim, add facts that aren't in an observation, or keep acting after the answer is complete.
Debugging: anti-patterns and fixes
Most ReAct failures fall into a handful of recognizable shapes.
| Symptom | Root cause | Fix |
|---|---|---|
| Premature conclusion | Answers before gathering required facts. | Force a planning thought that lists every sub-question first. |
| Tool spam | Re-checks an answer it already has with redundant calls. | Reward stopping; instruct the model to use the simplest sufficient tool once. |
| Weak thoughts | Vague reasoning ("let me search for stuff") leads to junk queries. | Require specific thoughts that name the goal and the tool choice. |
| Observation ignored | Re-searches for something an earlier observation already answered. | Instruct the model to read prior observations before acting. |
| Infinite loop | Repeats the same failing action. | Track repeated actions; force an alternative after a failure. |
| Hallucination in thoughts | Adds detail not present in any observation. | Constrain the final answer to observed facts; verify thoughts against observations. |
| No-stop | Keeps acting after the task is done. | Add explicit completion criteria and a recognizable stop signal. |
Testing and metrics
Final-answer accuracy alone hides a lot. Track the trajectory too:
- Task success rate — correct, complete answers over total tasks.
- Action efficiency — minimum actions needed over actions actually taken.
- Tool selection accuracy — appropriate tool calls over total tool calls.
- Recovery rate — errors successfully recovered over total errors.
- Observation utilization — observations actually used in the answer, a check against redundant actions.
A simple harness runs the agent over a labeled set and aggregates these:
def evaluate_react_agent(agent, test_cases):
results = {"success": 0, "actions": [], "tool_accuracy": []}
for case in test_cases:
trajectory, answer = agent.solve(case["question"])
results["success"] += evaluate_answer(answer, case["answer"])
results["actions"].append(count_actions(trajectory))
results["tool_accuracy"].append(evaluate_tool_selection(trajectory))
n = len(test_cases)
return {
"success_rate": results["success"] / n * 100,
"avg_actions": sum(results["actions"]) / n,
"tool_accuracy": sum(results["tool_accuracy"]) / n,
}
Benchmarks. The original paper evaluated ReAct (on PaLM-540B) across four datasets: HotpotQA (multi-hop QA), FEVER (fact verification), ALFWorld (text-based embodied tasks), and WebShop (online shopping). With access to a Wikipedia API, ReAct beat plain action-only generation on the knowledge tasks; it outperformed chain of thought on FEVER and lagged it on HotpotQA, with the strongest results coming from a method that combines and switches between ReAct and CoT (self-consistency). On the interactive tasks it led imitation- and RL-based methods by 34% (ALFWorld) and 10% (WebShop) absolute success rate. Later agent benchmarks like InterCode (code execution) and AgentBench extended the evaluation to broader tool-use settings.
Why HotpotQA and FEVER are the headline pair. They isolate ReAct's core claim: interacting with a Wikipedia API lets the model overcome the hallucination and error-propagation that plague chain-of-thought reasoning, and it produces human-readable trajectories you can actually inspect — interpretability that pure reasoning chains lack.
Advanced patterns
Single-trajectory ReAct is the floor. Several extensions push further:
- Self-consistency — run multiple trajectories at a higher temperature and vote on the final answer; more robust to a single bad path, at the cost of more calls.
- Planning first — have the model write an explicit numbered plan before it starts acting, then follow it step by step.
- Memory — short-term working memory within an episode, and long-term storage of successful trajectories to reuse on similar future questions.
- Reflexion — ReAct plus a self-reflection step: after a trajectory, the model critiques its own answer and retries with the lessons learned.
- Multi-agent ReAct — a coordinator delegates sub-tasks to specialist agents (flights, hotels, itinerary), each running its own loop, then synthesizes results.
- Parallel actions — when steps are independent, fire the tool calls concurrently and merge the observations instead of going one at a time.
- Budget-aware ReAct — cap the number of actions or the spend, and return the best partial answer when the budget is hit, for cost-sensitive deployments.
Tool quality is a hard dependency, and observations are untrusted input. A bad tool result feeds a wrong thought, which drives a bad next action — errors cascade. Worse, observations come from outside your prompt, so a malicious search result or document can carry a prompt injection straight into the model's reasoning. Validate and sanitize tool outputs, add fallback tools and result verification, and in high-stakes domains (medical, financial, legal) keep a human in the loop and ship explicit disclaimers — these systems are decision support, not the decision-maker.
Ecosystem and how it relates to other techniques
ReAct became the backbone of the modern agent stack. LangChain shipped a ReAct agent as a core component; AutoGPT used ReAct-style loops for autonomous runs; Toolformer taught models when to call tools; HuggingGPT orchestrated multiple models through it; and AgentBench standardized evaluation. The native function calling APIs from major providers are now the cleanest way to implement the pattern.
How it compares to its neighbors:
| Aspect | Chain of thought | RAG | Function calling | ReAct |
|---|---|---|---|---|
| Knowledge source | Model parameters | One-time retrieval | Tool outputs | Tools plus model |
| Retrieval timing | None | Before generation | On call | Iterative, during reasoning |
| Reasoning traces | Central | After retrieval | Optional | Explicit and central |
| Grounding | None | Retrieved docs | Tool results | Observations |
| Best for | Math and logic | Single known lookup | Structured calls | Multi-step, adaptive tasks |
These aren't mutually exclusive. Use chain-of-thought-style reasoning inside ReAct thoughts; make RAG one tool in the toolkit; implement the whole loop on top of a function calling API; and supply few-shot examples that are themselves ReAct trajectories. To adopt it, start from a working RAG or CoT pipeline, wrap the retrieval as a tool, add the thought/action/observation format, and grow the tool set from there.
The result that anchors the technique. On ALFWorld and WebShop — tasks that require navigating an environment and acting, not just answering — ReAct beat purpose-built imitation- and reinforcement-learning agents by 34% and 10% absolute success rate, using just one or two in-context examples. That an interleaved reason-and-act prompt outperformed trained policies is why ReAct became the default pattern for tool-using agents.
Future directions
The open problems are concrete. Learned tool selection (reinforcement learning over which tool works for which task) aims to cut unnecessary actions by an estimated 30-40%. Hierarchical ReAct splits a high-level planner from low-level executors for better strategy and parallelism. Continuous-learning agents improve from stored trajectories and user feedback. Multimodal ReAct adds vision, audio, and image-generation actions. Neurosymbolic ReAct pairs the LLM with a symbolic reasoner for provably correct steps. And explainable ReAct moves beyond showing thoughts to explaining them, with confidence scores and counterfactuals.
Summary
- ReAct interleaves Thought → Action → Observation, so reasoning guides actions and observations ground reasoning — the loop is stronger than either half alone (Yao et al., 2022, on PaLM-540B).
- It cuts hallucination by sourcing facts from live tools, and the readable trace makes decisions auditable.
- Headline results: on ALFWorld and WebShop it beat imitation- and RL-based methods by 34% and 10% absolute success rate; it beat chain of thought on FEVER and lagged on HotpotQA, with the best results from combining ReAct with CoT self-consistency.
- Reach for it on multi-step tasks needing live or verifiable information; skip it for pure reasoning or single-lookup tasks where CoT or RAG is cheaper.
- Budget for the cost: a 10-step task is roughly 20-30 LLM calls and 2-10 seconds of latency; tool selection degrades past about 50 tools.
- Robustness lives in the details — cap iterations, route errors back as observations, keep thoughts specific, stop when done, and sanitize tool outputs against injection.
- Extend with self-consistency, planning, memory, Reflexion, and multi-agent patterns; implement it cleanly on native function calling, and treat RAG and CoT as components inside the loop.
Read Next
Start reading to get personalized recommendations
Explore Unread
Great job! You've read all available articles