我如何编写两个函数,如果它以指定的字符/字符串开头或以指定的字符串结尾,那么它们将接受字符串并返回?

例如:

$str = '|apples}';

echo startsWith($str, '|'); //Returns true
echo endsWith($str, '}'); //Returns true

当前回答

substr函数在许多特殊情况下都会返回false,所以这里是我的版本,它处理了这些问题:

function startsWith( $haystack, $needle ){
  return $needle === ''.substr( $haystack, 0, strlen( $needle )); // substr's false => empty string
}

function endsWith( $haystack, $needle ){
  $len = strlen( $needle );
  return $needle === ''.substr( $haystack, -$len, $len ); // ! len=0
}

测试(真表示良好):

var_dump( startsWith('',''));
var_dump( startsWith('1',''));
var_dump(!startsWith('','1'));
var_dump( startsWith('1','1'));
var_dump( startsWith('1234','12'));
var_dump(!startsWith('1234','34'));
var_dump(!startsWith('12','1234'));
var_dump(!startsWith('34','1234'));
var_dump('---');
var_dump( endsWith('',''));
var_dump( endsWith('1',''));
var_dump(!endsWith('','1'));
var_dump( endsWith('1','1'));
var_dump(!endsWith('1234','12'));
var_dump( endsWith('1234','34'));
var_dump(!endsWith('12','1234'));
var_dump(!endsWith('34','1234'));

此外,substra_compare函数也值得一看。http://www.php.net/manual/en/function.substr-compare.php

其他回答

我希望以下答案既有效又简单:

$content = "The main string to search";
$search = "T";
//For compare the begining string with case insensitive. 
if(stripos($content, $search) === 0) echo 'Yes';
else echo 'No';

//For compare the begining string with case sensitive. 
if(strpos($content, $search) === 0) echo 'Yes';
else echo 'No';

//For compare the ending string with case insensitive. 
if(stripos(strrev($content), strrev($search)) === 0) echo 'Yes';
else echo 'No';

//For compare the ending string with case sensitive. 
if(strpos(strrev($content), strrev($search)) === 0) echo 'Yes';
else echo 'No';

简短易懂的一行,没有正则表达式。

startsWith()是直接向前的。

function startsWith($haystack, $needle) {
   return (strpos($haystack, $needle) === 0);
}

endsWith()使用稍微花哨且缓慢的strrev():

function endsWith($haystack, $needle) {
   return (strpos(strrev($haystack), strrev($needle)) === 0);
}

上面的正则表达式函数,但上面还建议了其他调整:

 function startsWith($needle, $haystack) {
     return preg_match('/^' . preg_quote($needle, '/') . '/', $haystack);
 }

 function endsWith($needle, $haystack) {
     return preg_match('/' . preg_quote($needle, '/') . '$/', $haystack);
 }

拉里维尔9.0

如果你正在使用Laravel,那么你可以执行以下操作(如果你没有使用Laraver,那么你真的应该这样做)。

Str::of('a long string')->startsWith('a');
Str::of('a long string')->endsWith('string');

//true
//true

专注于startswith,如果您确定字符串不为空,那么在比较之前,在第一个字符、strlen等上添加一个测试会加快速度:

function startswith5b($haystack, $needle) {
    return ($haystack{0}==$needle{0})?strncmp($haystack, $needle, strlen($needle)) === 0:FALSE;
}

不知怎么的,速度快了(20%-30%)。添加另一个字符测试,如$haystack{1}==$needle{1},似乎并不能加快速度,甚至可能会减慢速度。

==似乎比==条件运算符(a)?b: c似乎比如果(a)b更快;否则c;


对于那些问“为什么不使用strpos?”并称其他解决方案为“不必要的工作”的人


strpos速度很快,但它不是这项工作的正确工具。

为了理解,这里有一个小模拟作为示例:

Search a12345678c inside bcdefga12345678xbbbbb.....bbbbba12345678c

电脑在里面做什么?

    With strccmp, etc...

    is a===b? NO
    return false



    With strpos

    is a===b? NO -- iterating in haysack
    is a===c? NO
    is a===d? NO
    ....
    is a===g? NO
    is a===g? NO
    is a===a? YES
    is 1===1? YES -- iterating in needle
    is 2===3? YES
    is 4===4? YES
    ....
    is 8===8? YES
    is c===x? NO: oh God,
    is a===1? NO -- iterating in haysack again
    is a===2? NO
    is a===3? NO
    is a===4? NO
    ....
    is a===x? NO
    is a===b? NO
    is a===b? NO
    is a===b? NO
    is a===b? NO
    is a===b? NO
    is a===b? NO
    is a===b? NO
    ...
    ... may many times...
    ...
    is a===b? NO
    is a===a? YES -- iterating in needle again
    is 1===1? YES
    is 2===3? YES
    is 4===4? YES
    is 8===8? YES
    is c===c? YES YES YES I have found the same string! yay!
    was it at position 0? NOPE
    What you mean NO? So the string I found is useless? YEs.
    Damn.
    return false

假设strlen不迭代整个字符串(但即使在这种情况下),这一点都不方便。