我正在寻找像strpos()这样的函数,它有两个显着的区别:
当然,它必须是一种有效的解决方案,而不仅仅是每根针的循环。我搜索了这个论坛,并且有类似的问题,如:
但是我们正在寻找它们。我使用strpos只是为了更好地说明我的问题,可能有一些完全不同的东西必须用于此目的。
我知道Zend_Search_Lucene并且我感兴趣的是它是否可以用来实现这个以及如何(只是一般的想法)?
非常感谢你的帮助和时间!
答案 0 :(得分:7)
以下是我的策略的一些示例代码:
function strpos_array($haystack, $needles, $offset=0) {
$matches = array();
//Avoid the obvious: when haystack or needles are empty, return no matches
if(empty($needles) || empty($haystack)) {
return $matches;
}
$haystack = (string)$haystack; //Pre-cast non-string haystacks
$haylen = strlen($haystack);
//Allow negative (from end of haystack) offsets
if($offset < 0) {
$offset += $heylen;
}
//Use strpos if there is no array or only one needle
if(!is_array($needles)) {
$needles = array($needles);
}
$needles = array_unique($needles); //Not necessary if you are sure all needles are unique
//Precalculate needle lengths to save time
foreach($needles as &$origNeedle) {
$origNeedle = array((string)$origNeedle, strlen($origNeedle));
}
//Find matches
for(; $offset < $haylen; $offset++) {
foreach($needles as $needle) {
list($needle, $length) = $needle;
if($needle == substr($haystack, $offset, $length)) {
$matches[] = $offset;
break;
}
}
}
return($matches);
}
我在上面实施了一种简单的强力方法,可以使用任何针和干草堆的组合(不仅仅是单词)。对于可能更快的算法,请查看:
其他解决方案
function strpos_array($haystack, $needles, $theOffset=0) {
$matches = array();
if(empty($haystack) || empty($needles)) {
return $matches;
}
$haylen = strlen($haystack);
if($theOffset < 0) { // Support negative offsets
$theOffest += $haylen;
}
foreach($needles as $needle) {
$needlelen = strlen($needle);
$offset = $theOffset;
while(($match = strpos($haystack, $needle, $offset)) !== false) {
$matches[] = $match;
$offset = $match + $needlelen;
if($offset >= $haylen) {
break;
}
}
}
return $matches;
}
答案 1 :(得分:7)
答案 2 :(得分:2)
我知道这不会回答OP的问题但是想发表评论,因为这个页面位于谷歌的顶部,用于多针的strpos。这是一个简单的解决方案(同样,这不是特定于OP的问题 - 抱歉):
$img_formats = array('.jpg','.png');
$missing = array();
foreach ( $img_formats as $format )
if ( stripos($post['timer_background_image'], $format) === false ) $missing[] = $format;
if (count($missing) == 2)
return array("save_data"=>$post,"error"=>array("message"=>"The background image must be in a .jpg or .png format.","field"=>"timer_background_image"));
如果将$ items添加到$ missing数组,这意味着输入不满足$ img_formats数组中的任何图像格式。此时你知道你可以返回错误等。这很容易变成一个小函数:
function m_stripos( $haystack = null, $needles = array() ){
//return early if missing arguments
if ( !$needles || !$haystack ) return false;
// create an array to evaluate at the end
$missing = array();
//Loop through needles array, and add to $missing array if not satisfied
foreach ( $needles as $needle )
if ( stripos($haystack, $needle) === false ) $missing[] = $needle;
//If the count of $missing and $needles is equal, we know there were no matches, return false..
if (count($missing) == count($needles)) return false;
//If we're here, be happy, return true...
return true;
}
回到我们的第一个例子然后使用函数:
$needles = array('.jpg','.png');
if ( !m_strpos( $post['timer_background_image'], $needles ) )
return array("save_data"=>$post,"error"=>array("message"=>"The background image must be in a .jpg or .png format.","field"=>"timer_background_image"));
当然,在函数返回true或false之后你所做的是取决于你。
答案 3 :(得分:1)
您似乎正在搜索整个单词。在这种情况下,这样的事情可能会有所帮助。由于它使用内置函数,它应该比自定义代码更快,但您必须对其进行分析:
$words = str_word_count($str, 2);
$word_position_map = array();
foreach($words as $position => $word) {
if(!isset($word_position_map[$word])) {
$word_position_map[$word] = array();
}
$word_position_map[$word][] = $position;
}
// assuming $needles is an array of words
$result = array_intersect_key($word_position_map, array_flip($needles));
以正确的格式存储信息(如针)将改善运行时间(例如,您不必调用array_flip
)。
请注意str_word_count
文档:
为了这个函数的目的,'word'被定义为一个包含字母字符的语言环境依赖字符串,它也可能包含但不能以“'”和“ - ”字符开头。
因此,请确保将语言环境设置为正确。
答案 4 :(得分:0)
您可以使用正则表达式,它们支持OR运算。然而,与strpos相比,这会使它相当慢。
答案 5 :(得分:0)
使用 array_map()
的简单解决方案怎么样?
$string = 'one two three four';
$needles = array( 'five' , 'three' );
$strpos_arr = array_map( function ( $check ) use ( $string ) {
return strpos( $string, $check );
}, $needles );
作为返回,您将拥有一个数组,其中键是针位置,值是起始位置(如果找到)。
//print_r( $strpos_arr );
Array
(
[0] =>
[1] => 8
)