Lesson 32 of 6820 min read

Merge Conflicts: What Causes Them and How to Read Conflict Markers

Understand exactly why merge conflicts happen and learn to read Git's conflict markers confidently instead of fearing them.

Author: CodersNexus

Merge Conflicts: What Causes Them and How to Read Conflict Markers

Merge conflicts are one of the most anxiety-inducing moments for Git beginners, often appearing as a wall of unfamiliar symbols inserted directly into your code. In reality, a conflict is simply Git being honest that it can't automatically decide between two competing changes to the exact same content — and once you understand the conflict marker format, resolving them becomes a completely manageable, routine part of collaborative development.

Learning Objectives

  • Explain precisely what causes a merge conflict to occur.
  • Identify the three-way merge context in which conflicts arise.
  • Read and interpret Git's conflict markers: <<<<<<<, =======, and >>>>>>>.
  • Understand what git status reports during an unresolved conflict.

Key Terms to Know Before Learning Merge Conflicts

  • Merge conflict: A situation where Git cannot automatically combine changes from two branches because they modified the same lines (or closely related content) in incompatible ways.
  • Conflict markers: Special text Git inserts directly into a file to delineate the two competing versions of conflicting content, using <<<<<<<, =======, and >>>>>>>.
  • 'Ours' (HEAD): In the conflict markers, the version of the content from your current branch (the one you ran git merge from).
  • 'Theirs': In the conflict markers, the version of the content from the branch being merged in.
  • Unmerged path: A file git status reports as having unresolved conflict markers still present, requiring manual resolution before the merge can be completed.

How Merge Conflicts Actually Works

A merge conflict occurs specifically during a **three-way merge** (previous lesson) when both branches being merged have made changes to the *same* lines of the *same* file since their common ancestor — and those changes are different from each other. Git's automatic merging is quite capable of combining changes that touch *different* parts of a file without any issue at all; a conflict only arises when it genuinely cannot decide which of two competing, overlapping edits should 'win'.

When this happens, `git merge` pauses partway through and inserts special **conflict markers** directly into the affected file(s), showing you both competing versions side by side:

```
<<<<<<< HEAD
const greeting = "Hello there!";
=======
const greeting = "Welcome!";
>>>>>>> feature/dark-mode
```

This format has three distinct parts:

- `<<<<<<< HEAD` marks the start of **your current branch's version** (often called 'ours', since HEAD represents where you currently are).
- `=======` is a divider separating the two competing versions.
- Everything between `=======` and `>>>>>>> feature/dark-mode` is the version from the **branch being merged in** (often called 'theirs'), with the branch name shown explicitly so you know exactly which side is which.

In this example, your current branch defined the greeting as `"Hello there!"`, while `feature/dark-mode` defined it as `"Welcome!"` — since both branches changed the exact same line, Git cannot automatically decide which one is correct, so it leaves both versions in place, clearly marked, for a human to decide.

Running `git status` during an unresolved conflict clearly reports the situation:

```
Unmerged paths:
(use "git add <file>..." to mark resolution)
both modified: app.js
```

This tells you exactly which file(s) contain unresolved conflicts, and hints at the next step — the following lesson covers exactly how to resolve them.

A few important things to understand about conflicts as a concept, to reduce the anxiety many beginners feel:

1. **Conflicts are not errors or bugs** — they are Git correctly recognizing genuine ambiguity that only a human can resolve, and behaving safely by pausing rather than guessing incorrectly.
2. **A file can have multiple separate conflict blocks** if several unrelated sections were edited differently by both sides — each needs its own resolution.
3. **Your working directory is left in a temporary, in-progress state** with conflict markers physically present in the file's content — the file will not compile or run correctly until these markers are removed and the content is resolved.
4. **The merge is paused, not failed** — Git is waiting for you to finish it by resolving each conflict and then staging and committing the result.

Merge Conflicts: Visual Walkthrough

Show a single code file split by a horizontal divider. Above the divider, a highlighted block labeled '<<<<<<< HEAD' containing 'const greeting = "Hello there!";' — captioned 'YOUR current branch's version'. A dashed line labeled '=======' in the middle. Below the divider, a highlighted block labeled '>>>>>>> feature/dark-mode' containing 'const greeting = "Welcome!";' — captioned 'THEIR branch's version (the one being merged in)'. Add a callout: 'Both changed the SAME line since their common ancestor — Git cannot guess which is correct, so it shows you both.'

Marker vs Meaning: Key Differences

MarkerMeaning
<<<<<<< HEADStart of your current branch's ('ours') version of the conflicting content
======= Divider separating the two competing versions
>>>>>>> <branch-name>End marker, labeled with the name of the branch being merged in ('theirs')
Content between <<<<<<< and =======Exactly what your current branch (HEAD) has at this location
Content between ======= and >>>>>>>Exactly what the incoming branch has at this location

Merge Conflicts: Command Syntax and Examples

# Attempt a merge that results in a conflict
git switch main
git merge feature/dark-mode
# Auto-merging app.js
# CONFLICT (content): Merge conflict in app.js
# Automatic merge failed; fix conflicts and then commit the result.

# See which files have unresolved conflicts
git status
# Unmerged paths:
#   both modified:   app.js

# Inspect the actual conflict markers inside the file
cat app.js
# ...
# <<<<<<< HEAD
# const greeting = "Hello there!";
# =======
# const greeting = "Welcome!";
# >>>>>>> feature/dark-mode
# ...

Breaking Down the Merge Conflicts Example

The merge attempt clearly reports 'CONFLICT (content): Merge conflict in app.js' along with instructions to fix conflicts and commit the result — Git is explicit and unambiguous about what happened and what's needed next. `git status` confirms exactly which file(s) are affected, labeling `app.js` as 'both modified' under 'Unmerged paths'. Viewing the file's actual content reveals the conflict markers inserted directly at the exact location of the disagreement, clearly labeling which section came from HEAD (your current branch) and which came from the named incoming branch — giving you everything needed to make an informed decision about how to resolve it, which is the focus of the next lesson.

How Merge Conflicts Is Used on Real Engineering Teams

  • Merge conflicts are an entirely normal, expected part of daily work on any team where multiple people frequently touch overlapping areas of a codebase — experienced engineers view them as routine, not exceptional or alarming.
  • Code review platforms like GitHub explicitly detect and display conflicts directly in the pull request UI before a merge is even attempted, warning reviewers proactively rather than only surfacing the issue at merge time.
  • Teams practicing frequent, small commits and short-lived feature branches (a topic in a later lesson this module) tend to experience smaller, easier-to-resolve conflicts, since less code has diverged between branches.
  • Pair programming and close team communication about which files are being actively worked on is a common informal practice specifically aimed at reducing the frequency of painful, large-scale conflicts.

Merge Conflicts Interview Questions and Answers

Q1. What exactly causes a Git merge conflict?

A conflict occurs during a three-way merge when both branches being merged have changed the same lines of the same file (or otherwise overlapping content) differently since their common ancestor. Git can automatically combine non-overlapping changes just fine, but it cannot automatically decide which of two genuinely conflicting edits should take precedence, so it pauses and asks a human to decide.

Q2. How do you read Git's conflict markers in a file?

The content between <<<<<<< HEAD and ======= represents your current branch's version of that section. The content between ======= and >>>>>>> <branch-name> represents the version from the branch being merged in. The branch name after >>>>>>> tells you exactly which incoming branch that second version came from.

Q3. How does git status report an unresolved merge conflict?

It lists the affected file(s) under an 'Unmerged paths' section, typically labeling them as 'both modified', and explicitly hints that you should use git add <file> once you've resolved the conflict, to mark it as resolved.

Merge Conflicts Quiz: Test Your Understanding

1. During which type of merge can a conflict occur?

  1. Only during a fast-forward merge
  2. Only during a three-way merge
  3. During both fast-forward and three-way merges equally
  4. Conflicts can never actually occur in Git

Answer: B. Only during a three-way merge

Explanation: A three-way merge is the only situation involving genuine reconciliation of divergent changes from two branches, which is the only scenario where a conflict (overlapping incompatible edits) can arise.

2. In a conflict marker block, what does the content between <<<<<<< HEAD and ======= represent?

  1. The version from the branch being merged in
  2. Your current branch's version of that content
  3. A deleted section of the file
  4. An automatically resolved suggestion from Git

Answer: B. Your current branch's version of that content

Explanation: The section immediately following <<<<<<< HEAD and preceding ======= always represents the content as it exists on your current branch (the one you ran git merge from).

3. What does git status typically report during an unresolved merge conflict?

  1. The conflict is automatically resolved and hidden from view
  2. The affected file(s) listed under 'Unmerged paths', often as 'both modified'
  3. A permanent error preventing any further Git commands
  4. The repository is automatically reverted to its state before the merge began

Answer: B. The affected file(s) listed under 'Unmerged paths', often as 'both modified'

Explanation: git status clearly identifies which specific files still contain unresolved conflicts, helping you know exactly where manual resolution is needed.

Merge Conflicts: Common Mistakes Beginners Make

  • Panicking at the sight of conflict markers instead of recognizing them as a normal, expected, and fully resolvable situation.
  • Assuming a conflict means something has gone wrong or been lost — no work is lost; both competing versions are preserved and shown clearly.
  • Forgetting that conflict markers are literal text inserted into the file, meaning the file won't run or compile correctly until they're properly removed as part of resolution.
  • Not running git status during a conflict to get a clear, authoritative list of exactly which files need attention.

Merge Conflicts: Exam-Ready Quick Notes

  • Conflicts only occur during a three-way merge, when both branches changed the same content differently since their common ancestor.
  • Conflict markers: <<<<<<< HEAD (your version) / ======= (divider) / >>>>>>> <branch> (their version).
  • git status labels conflicted files under 'Unmerged paths', typically as 'both modified'.
  • A conflict pauses the merge; it does not fail or lose any work — it awaits human resolution.

Merge Conflicts: Key Takeaways

  • Merge conflicts happen only when both branches have changed the exact same content differently since diverging — Git handles all non-overlapping changes automatically.
  • Conflict markers clearly delineate 'your' version (HEAD) from 'their' version (the incoming branch), giving you full information to make a decision.
  • A conflict is a paused, in-progress state, not a failure — no work is lost, and git status clearly identifies exactly what needs to be resolved.

Frequently Asked Questions About Merge Conflicts

Q1. What exactly causes a merge conflict in Git?

It happens when both branches being merged have changed the exact same lines of the same file (or otherwise overlapping content) in different ways since they last shared a common history point. Git can't automatically decide which change should be kept, so it flags the conflict for you to resolve manually.

Q2. What do the symbols <<<<<<<, =======, and >>>>>>> mean in a conflicted file?

<<<<<<< HEAD marks the beginning of your current branch's version of the conflicting content. ======= separates that from the other version. >>>>>>> followed by a branch name marks the end of the version coming from the branch you're merging in.

Q3. Does a merge conflict mean I've lost any of my work?

No. Both competing versions are preserved and clearly shown within the conflict markers — nothing is deleted or lost. You simply need to decide how to resolve the disagreement between the two versions before completing the merge.

Q4. How do I know which files have conflicts that need fixing?

Run git status during the paused merge. It lists every affected file under an 'Unmerged paths' section, usually labeled as 'both modified', telling you exactly where manual attention is needed.

Q5. Can a single file have more than one conflict at once?

Yes. If both branches independently changed multiple separate, unrelated sections of the same file differently, each of those sections will show up as its own separate conflict block, each needing its own resolution.

Summary

A merge conflict occurs during a three-way merge when both branches being combined have changed the same content differently since their most recent common ancestor, leaving Git unable to automatically decide which version should win. When this happens, Git inserts conflict markers directly into the affected file: `<<<<<<< HEAD` marks the start of your current branch's version, `=======` divides it from the incoming branch's version, and `>>>>>>> <branch-name>` marks the end, explicitly naming the source of that second version. `git status` reports affected files under 'Unmerged paths'. Crucially, a conflict is not an error or a failure — it's Git safely pausing an in-progress merge, preserving both competing versions, and waiting for a human to resolve the ambiguity, which is the focus of the next lesson.

Frequently Asked Questions

It happens when both branches being merged have changed the exact same lines of the same file (or otherwise overlapping content) in different ways since they last shared a common history point. Git can't automatically decide which change should be kept, so it flags the conflict for you to resolve manually.

<<<<<<< HEAD marks the beginning of your current branch's version of the conflicting content. ======= separates that from the other version. >>>>>>> followed by a branch name marks the end of the version coming from the branch you're merging in.

No. Both competing versions are preserved and clearly shown within the conflict markers — nothing is deleted or lost. You simply need to decide how to resolve the disagreement between the two versions before completing the merge.

Run git status during the paused merge. It lists every affected file under an 'Unmerged paths' section, usually labeled as 'both modified', telling you exactly where manual attention is needed.

Yes. If both branches independently changed multiple separate, unrelated sections of the same file differently, each of those sections will show up as its own separate conflict block, each needing its own resolution.