Checking String Beginnings and Endings in PHP
Often when working with strings in PHP, you’ll need to determine if a string starts with or ends with a specific substring. This is a common task in data validation, parsing, and text manipulation. This tutorial will cover various techniques to accomplish this, ranging from PHP 8.0’s built-in functions to compatible solutions for older versions.
PHP 8.0 and Later: str_starts_with()
and str_ends_with()
PHP 8.0 introduced dedicated functions for checking string prefixes and suffixes, making the code cleaner and more readable.
str_starts_with(string $haystack, string $needle): bool
: Returnstrue
if thehaystack
string starts with theneedle
substring, andfalse
otherwise.str_ends_with(string $haystack, string $needle): bool
: Returnstrue
if thehaystack
string ends with theneedle
substring, andfalse
otherwise.
These functions are case-sensitive.
<?php
$string = '|apples}';
if (str_starts_with($string, '|')) {
echo "Starts with '|'\n"; // Output: Starts with '|'
}
if (str_ends_with($string, '}')) {
echo "Ends with '}'\n"; // Output: Ends with '}'
}
?>
These functions are generally the most efficient and preferred method when working with PHP 8.0 or later.
Compatibility with Older PHP Versions
If you need to support PHP versions older than 8.0, you’ll need to implement these checks manually. Here are a few common approaches:
1. Using substr()
and Comparison
This method extracts a substring from the beginning or end of the haystack
and compares it to the needle
.
<?php
function startsWith(string $haystack, string $needle): bool {
$length = strlen($needle);
return substr($haystack, 0, $length) === $needle;
}
function endsWith(string $haystack, string $needle): bool {
$length = strlen($needle);
if (!$length) { //Handle empty needle
return true;
}
return substr($haystack, -$length) === $needle;
}
$string = '|apples}';
if (startsWith($string, '|')) {
echo "Starts with '|'\n";
}
if (endsWith($string, '}')) {
echo "Ends with '}'\n";
}
?>
2. Using substr_compare()
The substr_compare()
function is designed for string comparisons and can be used to check for prefixes and suffixes.
<?php
function startsWith(string $haystack, string $needle): bool {
return substr_compare($haystack, $needle, 0, strlen($needle)) === 0;
}
function endsWith(string $haystack, string $needle): bool {
return substr_compare($haystack, $needle, -strlen($needle)) === 0;
}
$string = '|apples}';
if (startsWith($string, '|')) {
echo "Starts with '|'\n";
}
if (endsWith($string, '}')) {
echo "Ends with '}'\n";
}
?>
3. Using strpos()
and strrpos()
These functions find the position of a substring within a string. We can leverage them to check for prefixes and suffixes.
<?php
function startsWith(string $haystack, string $needle): bool {
return strpos($haystack, $needle, 0) === 0;
}
function endsWith(string $haystack, string $needle): bool {
$expectedPosition = strlen($haystack) - strlen($needle);
return strrpos($haystack, $needle, 0) === $expectedPosition;
}
$string = '|apples}';
if (startsWith($string, '|')) {
echo "Starts with '|'\n";
}
if (endsWith($string, '}')) {
echo "Ends with '}'\n";
}
?>
Performance Considerations
While all these methods are functional, performance can vary. Generally:
str_starts_with()
andstr_ends_with()
(PHP 8.0+) are the most efficient due to their optimized implementation.substr_compare()
is often faster thansubstr()
based solutions.strpos()
andstrrpos()
can be efficient but might involve more overhead than dedicated prefix/suffix checks.
If performance is critical, it’s recommended to benchmark different approaches with your specific use case to determine the most efficient solution. However, for most typical applications, the difference will likely be negligible.
Case-Insensitive Checks
If you need to perform case-insensitive checks, you can use the strcasecmp()
function within a similar startsWith()
or endsWith()
implementation, or use stripos()
and strripos()
instead of their case-sensitive counterparts. For example:
<?php
function startsWithCaseInsensitive(string $haystack, string $needle): bool {
return strcasecmp(substr($haystack, 0, strlen($needle)), $needle) === 0;
}
?>