Claude Code Essential Commands Created: 13 Apr 2026 Updated: 13 Apr 2026

Adding and Editing Memory in Claude Code

In the previous section, we explored how memory works in Claude Code — the different types, where they live, and how Claude discovers and loads them. Now it is time to put that knowledge into practice. This article focuses on how to add and edit memory entries, how to initialize memory for a new project, and how to verify that memory is working as expected.

Adding memory can be done using the hashtag (#) character, which prompts Claude Code to store the information in the appropriate memory file. For more substantial changes, the /memory command opens memory files directly in the code editor so you can review, edit, or reorganize them. These two mechanisms — quick hashtag entries and the full editor view — cover everything from one-line additions to detailed restructuring.

A recommended best practice is to keep memory files concise and specific. Overloading memory with vague or excessive information can waste tokens, introduce confusion, and reduce the quality of results. Using memory reduces the need for repetitive instructions and helps ensure consistent output across sessions. It makes interactions more efficient and focused, while preserving important context over time.

If you have worked with Cursor before, this concept is similar to Cursor rules. Both approaches let you persist instructions that shape AI behavior, but Claude Code's memory system offers multiple scopes (user, project, local) and supports auto memory where Claude saves its own notes.

Adding Memory with the Hashtag (#) Syntax

Quick Memory Entries

The fastest way to add a memory entry in Claude Code is to start your message with the # character. When Claude sees a message beginning with #, it treats the content as something to remember and writes it to the appropriate CLAUDE.md file. This is ideal for quick, one-line additions you want Claude to remember across sessions.

For example, to tell Claude you prefer a specific coding style:

# Always use file-scoped namespaces in C# files

Claude will acknowledge that this has been saved and will apply it in future sessions. You do not need to specify which file to write to — Claude selects the appropriate memory file based on context. If you are working inside a project, the entry typically goes into the project-level CLAUDE.md. If it is a personal preference, Claude may store it in the user-level file at ~/.claude/CLAUDE.md.

Choosing Where the Entry Goes

You can direct Claude to store an entry in a specific memory level by being explicit. For example:

# Store in user memory: I prefer dark mode terminal themes

Or for project-specific memory:

# I like to eat pizza

When Claude processes the hashtag entry, it decides the most appropriate location based on whether the instruction is personal or project-specific. You can also specify the target explicitly by saying something like "add this to my user CLAUDE.md" or "save this in the project CLAUDE.md."

Editing Memory with the /memory Command

Opening the Memory Editor

For more substantial changes — editing existing entries, reorganizing sections, or reviewing what Claude has saved — the /memory command provides a full editing interface. When you type /memory in a Claude Code session, it lists all CLAUDE.md, CLAUDE.local.md, and rules files loaded in your current session.

/memory

This command shows you:

  1. All CLAUDE.md and CLAUDE.local.md files currently loaded
  2. All .claude/rules/ files that apply to the session
  3. A toggle to enable or disable auto memory
  4. A link to open the auto memory folder for browsing

Select any file from the list to open it in your editor. You can then make changes directly — add new instructions, remove outdated entries, or restructure sections.

When to Use /memory vs. Hashtag

Use the hashtag syntax when you want to quickly add a single piece of information without interrupting your workflow. Use /memory when you need to:

  1. Review all memory files loaded in the session
  2. Edit or delete existing entries
  3. Verify that your CLAUDE.md files are being loaded correctly
  4. Toggle auto memory on or off
  5. Browse what auto memory has saved

Initializing Memory with /init

What /init Does

Claude Code provides the /init command, which initializes a new CLAUDE.md file based on the existing codebase. When you run it, Claude analyzes the files in the project — scanning directories, reading configuration files, checking package manifests, and inspecting the overall structure — then generates a CLAUDE.md file containing relevant contextual information.

/init

The generated file typically includes:

  1. Tech stack identification — frameworks, languages, and major libraries
  2. Build and run commands — how to install dependencies, build, and run the project
  3. Project structure — key directories and their purposes
  4. Environment variables — required configuration for running the project
  5. Code conventions — patterns and standards discovered in the codebase

If a CLAUDE.md file already exists, /init suggests improvements rather than overwriting it. This makes it safe to run at any point during the project lifecycle.

Interactive Mode

For a more guided setup experience, you can enable an interactive multi-phase flow by setting an environment variable:

CLAUDE_CODE_NEW_INIT=1

With this enabled, /init asks which artifacts to set up — CLAUDE.md files, skills, and hooks. It then explores your codebase with a subagent, fills in gaps via follow-up questions, and presents a reviewable proposal before writing any files. This is useful for larger or more complex projects where you want more control over what gets generated.

Hands-On Example: Using Memory with an Existing Project

Setting Up the Example Project

To illustrate how memory works in practice, we use an existing repository created for a LangChain project. This project scrapes information from LinkedIn and the X platform and uses it to generate an icebreaker. More details can be found at github.com/emarco177/IceBreaker. It is a practical example built with LangChain agents and works well for demonstrating Claude Code's capabilities.

We begin by cloning the repository into a new directory and opening it in the editor:

git clone https://github.com/emarco177/IceBreaker.git tmp3
cd tmp3
code .

Once the project is open, you can see the full project structure. This is a Python project built using the LangChain stack with Flask as the web framework.

Running /init to Generate Project Memory

Open Claude Code and pin it in the interface. When prompted, approve Claude Code's request to access and analyze the project files. Then run:

/init

Running /init causes Claude to scan all the files in the repository. It identifies the tech stack, installed packages, required environment variables, and overall structure. During this process, Claude lists directories, searches through files, and performs analysis using pattern matching and content inspection.

After reading the files, Claude produces a suggested CLAUDE.md file that includes details such as:

  1. How to install dependencies using pip
  2. How to run the project
  3. An overview of the main components — scraping, summarization, and agent logic
  4. Required environment variables for APIs

Once you approve the generated file, it becomes part of the project's memory. From this point on, every prompt sent to Claude will include the contents of this CLAUDE.md file as part of the context.

Verifying Project Memory

Clearing Context and Testing

To confirm that memory is working, first reset the conversation to eliminate any influence from prior chat history. Use the /clear command to wipe the conversation context:

/clear

Then ask a question that requires project knowledge. For example:

What stack am I using for this project?

Claude should provide an accurate response without needing to invoke any tools — no file reads, no searches. The information was captured during initialization and is now part of the project memory. A typical response would look like:

Based on the codebase analysis, your project uses this tech stack:

Backend Framework: Flask (Python web framework)
AI/LLM Framework: LangChain with OpenAI GPT models
(GPT-4o-mini for agents, GPT-3.5-turbo for content generation)
Data Sources: Scraping (LinkedIn), Twitter API, Tavily (web search)
Package Management: Pipenv
Code Quality: Black (formatting), isort (import sorting), pylint (linting)
Testing: pytest
Output Parsing: Pydantic models
Frontend: HTML templates with Flask templating
Environment: Python 3.10+

The core architecture is a LangChain-powered AI pipeline that combines
social media data scraping with LLM-based content generation.

Claude provided this answer by reading the CLAUDE.md file at session start — not from the chat history. This confirms that stored memory is active and working.

Using /memory to Verify Loaded Files

As an additional verification step, you can run /memory to inspect which files are loaded:

/memory

This lists every CLAUDE.md and rules file in the session. If your project's CLAUDE.md is not in the list, Claude cannot see it, and you need to check the file's location (see the official memory documentation for expected file paths).

Adding and Using Memory Entries

A Simple Example: Personal Preferences

Let us demonstrate how to add new memory entries. At this point, if we ask a question such as "What do I like to eat?", Claude generates a response like:

> what do i like to eat?

I don't have any information about what you like to eat.
I can only see your codebase files and project structure,
but there's no personal information about your food preferences
in this ice breaker application repository.

This is expected — Claude only knows what is in its context (the codebase and memory files). To enable Claude to answer this question, we add a memory entry using the hashtag syntax:

# I like to eat pizza

This entry is stored in the project memory (the project's CLAUDE.md). Now clear the conversation and ask the same question again:

/clear

what do i like to eat?

Claude will now answer correctly:

Pizza

Adding to Different Memory Levels

We can add another entry, this time storing it in user memory (which lives at ~/.claude/CLAUDE.md). User memory applies across all projects:

# Store in user memory: I also like to eat hamburgers

After clearing the conversation and asking the same question again, Claude will recall both preferences:

> what do i like to eat?

Based on your CLAUDE.md files, you like to eat both
Hamburger (from your global preferences) and
Pizza (from your project-specific memory).

This demonstrates how Claude merges memory from multiple levels. The user-level CLAUDE.md provided the hamburger preference, while the project-level CLAUDE.md provided the pizza preference. Both are loaded at session start and concatenated into context.

Practical Memory Entries for Real Projects

The food preference example is deliberately simple to show how memory works. In practice, you would store far more useful information. Here are examples of entries that improve real coding workflows:

# Always use minimal APIs in ASP.NET Core, never use controllers
# Use xUnit with FluentAssertions for all test projects
# Database migrations use Entity Framework Core — run: dotnet ef database update
# Commit messages must follow conventional commits format: feat:, fix:, docs:
# Never use var — always use explicit types

Each of these entries will be loaded into every future session, ensuring Claude follows your conventions without being reminded.

Working with Multiple Memory Files

Why Multiple Files?

As projects grow, a single CLAUDE.md file can become large and difficult to manage. The official documentation recommends keeping CLAUDE.md files under 200 lines — longer files consume more context and reduce adherence. Claude Code supports using multiple CLAUDE.md files distributed across a repository. Claude recursively traverses the directory structure and loads all relevant memory files into the context.

Organizing Memory by Directory

This allows memory to be organized in a structured way. For example, in an ASP.NET Core solution with a clean architecture layout:

my-solution/
├── CLAUDE.md # Top-level project instructions
├── src/
│ ├── MyApp.Api/
│ │ └── CLAUDE.md # API-specific conventions
│ ├── MyApp.Application/
│ │ └── CLAUDE.md # Business logic rules
│ └── MyApp.Infrastructure/
│ └── CLAUDE.md # Data access conventions
└── tests/
└── CLAUDE.md # Testing conventions

Each subdirectory CLAUDE.md loads lazily — only when Claude reads files in that subdirectory. This keeps the initial context lean while still providing targeted instructions when needed.

Using .claude/rules/ for Topic-Based Organization

For even more granular control, use the .claude/rules/ directory to split instructions by topic. Each file covers one area:

my-solution/
├── .claude/
│ ├── CLAUDE.md
│ └── rules/
│ ├── code-style.md # Formatting and naming rules
│ ├── testing.md # Test conventions
│ ├── api-design.md # API endpoint standards
│ └── security.md # Security requirements
├── src/
└── tests/

Rules without a paths frontmatter are loaded at launch. Rules with path-scoping only load when Claude works with matching files — for example, a rule scoped to src/api/**/*.cs only activates when Claude reads API controllers.

Combining Memory with Hooks for Dynamic Context

When combined with hooks, this setup enables more advanced behavior. Different memory files can be attached depending on the type of work being done. A context-switching hook can attach database-related memory when working with database code, frontend context when working on UI components, or API-related memory when handling backend logic.

This level of control allows memory to be tailored dynamically based on user input and workflow needs, opening the door to more advanced and flexible context management patterns. We will explore hooks and context-switching in detail in a later section.

Best Practices for Memory Management

Keep Memory Concise

Every CLAUDE.md file is loaded into the context window at the start of every session, consuming tokens. The official documentation recommends targeting under 200 lines per CLAUDE.md file. If your instructions are growing beyond that, split them using @ imports or .claude/rules/ files.

Be Specific, Not Vague

Specific instructions produce more reliable behavior. Compare:

  1. Vague: "Format code properly"
  2. Specific: "Use 4-space indentation, file-scoped namespaces, and primary constructors"
  3. Vague: "Test your changes"
  4. Specific: "Run dotnet test before committing. Use xUnit with FluentAssertions."

Review and Prune Regularly

Memory files should be treated like code — they need maintenance. Remove stale entries that no longer apply, resolve conflicting instructions between files, and consolidate related instructions. Run /memory periodically to audit what is loaded.

Commit Project Memory to Version Control

Your project's CLAUDE.md and .claude/rules/ files should be committed to Git. This ensures every team member — and every CI/CD pipeline running Claude — gets the same instructions. Use CLAUDE.local.md (which is gitignored) for personal project-specific overrides.

Summary

Adding and editing memory in Claude Code is straightforward. The # syntax provides a quick way to add entries during a session. The /memory command gives you full control to review, edit, and manage all loaded memory files. The /init command bootstraps project memory by analyzing the codebase automatically.

As projects grow, memory can be organized across multiple CLAUDE.md files in subdirectories, modularized with .claude/rules/, and dynamically composed using hooks. The key principle remains the same: keep memory specific, concise, and up to date — like a briefing document that helps Claude deliver consistent, high-quality results from the very first prompt in every session.


Share this lesson: