Table of Contents
Vim Guide
How to Count Lines in Vim (5 Methods, Including the One That Also Counts Words and Bytes)
Count lines in Vim with Ctrl+G, g Ctrl+G, :$, line('$'), and substitution counts. Covers the :%s/pattern//n count, the :%s/\n//gn trap, Visual selection counts, and Vimscript automation.
If you want to count lines in Vim, the fastest answer is usually already built in.
Ctrl+G shows the current file and cursor position. g Ctrl+G shows the line total plus word and byte totals. :$ jumps to the last line. And in scripts, line('$') gives you the total directly.
That is the practical core of vim count lines in file.
If all you need is vim count lines in file, the decision is mostly about whether you want a quick status message, a jump, or a script result.
There is one trap worth calling out early: :%s/pattern//n counts matches without changing the buffer, but it is still a pattern count. It is useful for vim count lines matching pattern, not for every counting job. And :%s/\n//gn is not a file newline byte counter in the way many people assume.
If you searched for vim g ctrl g or vim set number, this guide separates those jobs so you can use the right tool for the right count.
If you are looking for a quick vim show total lines check, start with the status bar methods below. If you need a vim line count script, jump to the Vimscript section.
Quick Method Guide
| Need | Command | Notes |
|---|---|---|
| Fast total line count | Ctrl+G | Shows the current file and cursor position |
| Total lines plus words and bytes | g Ctrl+G | Best quick check for vim count lines |
| Jump to the last line | :$ | Ex address version of the last-line jump |
| Exact total in code | line('$') | Best script-friendly primitive |
| Pattern count | :%s/pattern//n | Reports matches without replacing text |
| Selection count | g Ctrl+G in Visual mode | Or use line("'>") - line("'<") + 1 |
Method 1: Ctrl+G
Ctrl+G is the simplest vim count lines in file check when you do not want to move the cursor.
Typical output looks like this:
"data.txt" line 1 of 42 --2%--
That tells you the current line and the total line count in one glance. It also shows file status, which makes Ctrl+G a good first look when you are editing logs, configs, or source files.
For a plain vim show total lines check, this is usually enough.
Method 2: g Ctrl+G
g Ctrl+G is the version most people miss.
If you searched for vim g ctrl g, this is the command you were looking for.
It reports the current position in five ways: column, line, word, character, and byte. In Visual mode, it switches to the selected region and shows selection totals instead.
Example output:
Col 1 of 80; Line 1 of 42; Word 1 of 315; Byte 1 of 1024
That makes g Ctrl+G the best answer when you want vim count lines plus extra context.
In Visual mode, Vim can show output like:
Selected 5 of 293 Lines; 70 of 1884 Words; 359 of 10928 Bytes
If you only need vim count lines in file, read the line field. If you need more than that, this is the fastest built-in command.
Method 3: G, :$, and line('$')
Normal-mode G and Ex-command :$ both jump to the last line.
That makes them a good fit when you want vim count lines in file by movement rather than by status message. The line number in the status bar is the total.
For scripts, line('$') is better:
:echo line('$')
That returns the last line number directly, so it is the most reliable script-friendly primitive.
If you searched for vim set number, this is the core command:
:set number
:set relativenumber
And if you want the total line count in the statusline, add %L:
set statusline=%f\ %l/%L\ (%p%%)
That makes vim set number and %L a practical always-visible pair when you want vim show total lines information to stay on screen.
Method 4: :%s/pattern//n
:%s/pattern//n reports matches without replacing anything.
If you searched for vim :%s count lines, this is the section you actually want.
That makes it useful for vim count lines matching pattern, but only if you understand the g flag:
:%s/foo//nreports one match per line at most:%s/foo//gnreports every match on every line
For example:
:%s/foo//n
:%s/foo//gn
On a line such as foo foo foo, the first form reports one match, while the second reports three.
This is also where many readers misuse the substitute-count trick.
In Vim, \n in a pattern matches an end-of-line in buffer text. So :%s/\n//gn follows Vim's buffer model, not the physical newline bytes in a file. That is why it is a poor choice if your real goal is a file newline counter.
In local Vim 9.1 testing, a three-line file without a trailing newline still reported 3 matches on 3 lines for :%s/\n//gn. That is the behavior you should expect from Vim's buffer model.
If you need the actual total line count, use Ctrl+G, g Ctrl+G, :$, or line('$') instead.
Method 5: Visual Selections and Vimscript
For a selected block of text, g Ctrl+G is the quickest option.
If you need the count in a script, use the selection marks directly:
:echo line("'>") - line("'<") + 1
That is the clean script-friendly approach for a selection.
If your real job is vim count lines matching pattern inside a selection, use the visual range directly:
:'<,'>s/foo//n
:'<,'>s/foo//gn
That gives you a range-limited version of the substitute count without touching the rest of the buffer.
You can wrap the same logic in a function:
function! CountBufferLines() abort
return line('$')
endfunction
function! CountSelectionLines() abort
return line("'>") - line("'<") + 1
endfunction
That keeps vim count lines automation simple and predictable.
Sources Checked
- Vim help for
CTRL-G,g CTRL-G, and Visual mode selection counts: https://vimhelp.org/editing.txt.html - Vim help for substitute flags, including
nandg: https://vimhelp.org/change.txt.html - Vim help for
\nin patterns matching end-of-line: https://vimhelp.org/pattern.txt.html - Vim help for Ex ranges, including
$as the last line: https://vimhelp.org/cmdline.txt.html - Vim help for
line('$'): https://vimhelp.org/builtin.txt.html - Vim help for the
%Lstatusline item: https://vimhelp.org/options.txt.html
I also verified the substitution behavior locally in Vim 9.1 with files that did and did not end with a trailing newline.
Related Guides and Tools
- Bash
wc -lcommand - C line counting
- C++
ifstreamand iterator patterns - VS Code line count guide
- Line Counter tool
Need to count lines without leaving Vim?
Try the Line Counter. Paste the file, get the number, move on.
Frequently Asked Questions
How do I count lines in Vim?
Use Ctrl+G for a quick status-bar check, g Ctrl+G for line, word, and byte totals, or line('$') in Vimscript when you need the number in code.
What is the difference between Ctrl+G and g Ctrl+G in Vim?
Ctrl+G shows the current file and cursor position. g Ctrl+G shows column, line, word, character, and byte information, and it also works on Visual selections.
How do I count lines matching a pattern in Vim?
Use :%s/pattern//n to report matches without changing the file. Add g if you want every occurrence on each line instead of only the first match per line.
Why does :%s/\n//gn not behave like a file newline counter?
Because Vim counts buffer line boundaries, not physical newline bytes. It is a pattern count, so it is not the same thing as reading the file byte by byte.
How do I count selected lines in Vim?
Select the text in Visual mode and press g Ctrl+G, or use line("'>") - line("'<") + 1 in a script.
How do I show line numbers all the time in Vim?
Use :set number or :set relativenumber. If you also want the total line count visible in a statusline, add %L to your statusline format.
Related Guides
16 min read
How to Count Lines in Bash: The Complete Guide with Edge Cases
Master line counting in Bash: count lines in files, variables, command output, and directories. Covers wc -l pitfalls, empty files, filenames with spaces, and shell script usage.
13 min read
How to Count Lines in a File in C (And Why `fgetc` Is 9x Slower Than `fread`)
Count lines in a file in C — fgets, fread, mmap, and the large performance gap between them. Covers `wc -l` internals, Windows vs Linux portability, long-line traps, and production-ready counting patterns for large files.
12 min read
How to Count Lines in a File in C++ (And Two Classic Traps That Catch Everyone)
Count lines in a file in C++ using ifstream, istreambuf_iterator, fread, and mmap. Covers the while(!eof()) off-by-one trap, the single-pass istreambuf_iterator reset issue, and why newline-byte counters must fix the missing final newline case.
14 min read
How to Count Lines in VS Code: Every Method Explained
Count lines in VS Code without plugins using the status bar, keyboard shortcuts, and terminal. Plus: count lines across an entire project, exclude comments, and compare extensions.