substr()
The substr() function in PHP is used to extract a portion of a string. This function is particularly useful when working with text-based applications where
The substr() function returns a slice of a string — the characters between a starting position and an optional length. It's one of the most-used string tools in PHP: trimming prefixes, taking the first N characters of a label, reading a fixed-width field, or grabbing a file extension all come down to a substr() call. This page covers the syntax, every way the $start and $length arguments behave (including negatives), the edge cases that trip people up, and when to reach for mb_substr() instead.
Syntax
substr(string $string, int $offset, ?int $length = null): string| Parameter | Description |
|---|---|
$string | The input string to extract from. |
$offset | Zero-based start position. Negative counts from the end of the string. |
$length | Optional. How many characters to return. Omit it (or pass null) to read to the end of the string. Negative means "stop this many characters before the end." |
substr() returns the extracted substring. As of PHP 8.0 it always returns a string (an empty string when nothing matches); before PHP 8.0 it returned false on failure, so you may still see that in older code.
A basic example
$offset is 0, so extraction starts at the first character, and $length is 5, so five characters (Hello) are returned. Remember the offset is zero-based: position 0 is H, position 1 is e, and so on.
How the offset works
A positive offset counts from the start; a negative offset counts from the end (where -1 is the last character):
<?php
$string = "Hello World!";
echo substr($string, 6); // World! — from offset 6 to the end
echo "\n";
echo substr($string, -6); // World! — last 6 characters
echo "\n";
echo substr($string, -1); // ! — just the last characterOmitting $length returns everything from the offset onward — handy for stripping a known prefix.
How the length works
A positive $length limits how many characters you take. A negative $length stops that many characters before the end of the string, which is great for chopping off a known suffix:
<?php
$string = "Hello World!";
echo substr($string, 0, -1); // Hello World — drop the trailing "!"
echo "\n";
echo substr($string, -6, 5); // World — start 6 from the end, take 5
echo "\n";
echo substr($string, 4, 0); // (empty) — length 0 returns ""If the requested length runs past the end of the string, substr() simply returns whatever is available — it never errors for being "too long."
Practical use: a file extension
Combining substr() with strrpos() (which finds the last position of a character) is the classic way to read a file extension:
<?php
$filename = "report.final.pdf";
$ext = substr($filename, strrpos($filename, ".") + 1);
echo $ext; // pdfCommon gotchas
- Offset out of range. If
$offsetis greater than the string length, you get an empty string (in PHP 8+). It does not wrap around. - Counts bytes, not characters.
substr()works on bytes. For UTF-8 text with accented letters or emoji, slicing mid-character produces garbage. Usemb_substr()for multibyte-safe extraction. - Off-by-one with length.
$lengthis a count, not an end index.substr($s, 2, 3)returns 3 characters starting at index 2 — not the characters between index 2 and index 3.
Related functions
strlen()— get the length of a string, often used to compute a$length.strpos()— find where a substring begins, to feed intosubstr().explode()— split a string into an array when you have a delimiter.trim()— remove whitespace (or other characters) from both ends.