Skip to content

Reflection & Self-Critique: Agent Self-Awareness

Overview

Humans catch their own mistakes by reviewing their work. Agents can do the same.

Self-critique is one of the most effective ways to improve agent quality—simple to implement and powerful in practice.


How Reflection Works

Basic Reflection Loop

class ReflectiveAgent:
    """Agent that critiques its own work"""

    def solve_with_reflection(self, task):
        """Generate solution, then critique it"""

        # Step 1: Initial solution
        solution = self.generate_solution(task)

        # Step 2: Self-critique
        critique = self.self_critique(task, solution)

        # Step 3: Evaluate critique
        if critique.has_errors:
            # Step 4: Revise based on critique
            revised = self.revise_solution(
                task, 
                solution, 
                critique
            )
            return revised

        return solution

    def generate_solution(self, task):
        """Generate initial attempt"""

        prompt = f"""Solve this task: {task}

        Provide your solution."""

        return self.llm.call(prompt)

    def self_critique(self, task, solution):
        """Critique the solution"""

        prompt = f"""
        Task: {task}
        Proposed solution: {solution}

        Critique this solution. What's wrong with it?
        What could be improved?
        """

        critique_text = self.llm.call(prompt)
        return self.parse_critique(critique_text)

    def revise_solution(self, task, solution, critique):
        """Improve solution based on critique"""

        prompt = f"""
        Task: {task}
        Original solution: {solution}
        Critique: {critique.text}

        Provide a revised solution that addresses the critique.
        """

        return self.llm.call(prompt)

Chain-of-Criticism Pattern

Multi-Round Reflection

class ChainOfCriticism:
    """Multiple rounds of critique"""

    def solve_with_iterations(self, task, max_iterations=3):
        """Iteratively improve through critique"""

        solution = self.generate_solution(task)

        for iteration in range(max_iterations):
            # Critique
            critique = self.critique(task, solution)

            # Analyze
            score = self.score_solution(task, solution, critique)

            # Check stopping criterion
            if score > 0.9:  # Good enough
                break

            if critique.is_unsalvageable:
                break

            # Improve
            solution = self.improve(task, solution, critique)

        return solution

    def score_solution(self, task, solution, critique):
        """Rate solution quality"""

        scoring_prompt = f"""
        Task: {task}
        Solution: {solution}
        Critique: {critique}

        Rate solution quality 0-1. Be harsh, not generous.
        """

        score_text = self.llm.call(scoring_prompt)
        return float(score_text.strip())

When to Use: - Complex problems requiring multiple passes - High-stakes decisions - When initial attempts are often wrong

Cost: 3-4x tokens for 3 iterations
Quality Improvement: +20-35% accuracy


Specific Critique Prompts

Code Review Critique

class CodeReviewCritique:
    """Critique code for common issues"""

    def critique_code(self, code, language):
        """Comprehensive code critique"""

        critique_areas = [
            "correctness",        # Does it work?
            "efficiency",         # Is it efficient?
            "readability",        # Is it understandable?
            "security",           # Are there vulnerabilities?
            "maintainability",    # Is it maintainable?
            "edge_cases"          # Does it handle edge cases?
        ]

        critiques = {}

        for area in critique_areas:
            prompt = f"""
            Review this {language} code for {area} issues:

            {code}

            List specific {area} problems. Be thorough.
            """

            critique = self.llm.call(prompt)
            critiques[area] = critique

        return critiques

    def suggest_improvements(self, code, critiques):
        """Generate improved version"""

        prompt = f"""
        Original code:
        {code}

        Issues found:
        {format_critiques(critiques)}

        Provide improved code that addresses all issues.
        """

        return self.llm.call(prompt)

Feedback-Driven Reflection

Learning from External Critique

class FeedbackReflection:
    """Agent learns from human feedback"""

    def solve_and_get_feedback(self, task):
        """Solve, get feedback, improve"""

        solution = self.generate_solution(task)

        # Ask human for feedback
        feedback = self.request_human_feedback(task, solution)

        if feedback.approved:
            # Good! Learn from this
            self.learn_from_success(task, solution, feedback)
            return solution
        else:
            # Not good. Learn from error
            self.learn_from_failure(
                task, 
                solution, 
                feedback.critique
            )

            # Improve and retry
            improved = self.improve_from_feedback(
                task,
                solution,
                feedback.critique
            )

            return improved

    def learn_from_failure(self, task, solution, feedback):
        """Record what went wrong"""

        learning_record = {
            'task': task,
            'failed_solution': solution,
            'feedback': feedback,
            'category': self.categorize_error(feedback)
        }

        self.memory.add_learning(learning_record)

    def improve_from_feedback(self, task, solution, feedback):
        """Generate improved version"""

        prompt = f"""
        Task: {task}
        Failed attempt: {solution}
        Human feedback: {feedback}

        Generate an improved solution that addresses the feedback.
        """

        return self.llm.call(prompt)

Avoiding Over-Critique

When NOT to Critique

class SmartCritique:
    """Only critique when needed"""

    def should_critique(self, task, solution):
        """Decide if critique is worth it"""

        factors = {
            'confidence': solution.confidence,
            'task_difficulty': self.estimate_difficulty(task),
            'expected_error_rate': self.base_error_rate(task),
            'critique_cost': 0.3  # Roughly 30% token cost
        }

        # Only critique if:
        # - Low confidence AND
        # - High difficulty AND
        # - Worth the token cost

        if factors['confidence'] > 0.85:
            return False  # Already confident

        if factors['task_difficulty'] < 0.3:
            return False  # Too easy, not worth it

        if factors['critique_cost'] > self.token_budget:
            return False  # Can't afford

        return True  # Critique is worthwhile

3 Warnings ⚠️

Warning 1: Critique Blindness

# ❌ WRONG
# Agent critiques own work and misses obvious errors
solution = agent.generate()
critique = agent.self_critique(solution)
# Agent doesn't see its own mistakes

# ✅ RIGHT
# Use external critic (different model)
solution = agent.generate()
critic_model = different_model()  # GPT-4 critiques Claude output
critique = critic_model.critique(solution)
# Different perspective catches errors

Warning 2: Infinite Refinement

# ❌ WRONG
while True:
    solution = generate()
    critique = self_critique(solution)
    if critique.perfect:
        break
    solution = improve(critique)

# Never good enough, loops forever
# Wastes tokens

# ✅ RIGHT
for iteration in range(max_iterations):
    solution = generate()
    critique = self_critique(solution)
    score = score_solution(critique)

    if score > 0.9 or iteration == max_iterations - 1:
        break

    solution = improve(critique)

Warning 3: Critiquing Wrong Things

# ❌ WRONG
# Critique code for security in simple script
code = "print('hello')"
security_critique = critique_for_security(code)
# Wastes tokens on non-issue

# ✅ RIGHT
# Critique only relevant aspects
if is_production_code(code):
    security_critique = critique_for_security(code)
elif is_performance_critical(code):
    efficiency_critique = critique_for_efficiency(code)
else:
    readability_critique = critique_for_readability(code)

# Focused critique

Last Updated: August 9, 2026