php 递归搜索数组中的键

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3975585/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-25 11:36:57  来源:igfitidea点击:

Search for a key in an array, recursively

phparrayssearchrecursion

提问by Marreman

private function find($needle, $haystack) {
    foreach ($haystack as $name => $file) {
        if ($needle == $name) {
            return $file;
        } else if(is_array($file)) { //is folder
            return $this->find($needle, $file); //file is the new haystack
        }               
    }

    return "did not find";
}

Hey, this method searches for a specific key in an associative array and returns the value associated with it. There's some problem with the recursion. Any clue?

嘿,此方法在关联数组中搜索特定键并返回与其关联的值。递归有问题。有什么线索吗?

回答by xPheRe

Maybe it's overkill, but it's funny to use RecursiveIterators :)

也许这有点矫枉过正,但使用 RecursiveIterators 很有趣:)

UPDATE:Maybe it was overkill with old versions of PHP, but with >=5.6 (specially with 7.0) I would totally use this without doubt.

更新:也许旧版本的 PHP 有点过头了,但是对于 >=5.6(特别是 7.0)我会毫无疑问地完全使用它。

function recursiveFind(array $haystack, $needle)
{
    $iterator  = new RecursiveArrayIterator($haystack);
    $recursive = new RecursiveIteratorIterator(
        $iterator,
        RecursiveIteratorIterator::SELF_FIRST
    );
    foreach ($recursive as $key => $value) {
        if ($key === $needle) {
            return $value;
        }
    }
}

UPDATE:Also, as of PHP 5.6, with generators you can easily iterate over all elements which pass the filter, not only the first one:

更新:此外,从 PHP 5.6 开始,使用生成器,您可以轻松迭代通过过滤器的所有元素,而不仅仅是第一个:

function recursiveFind(array $haystack, $needle)
{
    $iterator  = new RecursiveArrayIterator($haystack);
    $recursive = new RecursiveIteratorIterator(
        $iterator,
        RecursiveIteratorIterator::SELF_FIRST
    );
    foreach ($recursive as $key => $value) {
        if ($key === $needle) {
            yield $value;
        }
    }
}

// Usage
foreach (recursiveFind($haystack, $needle) as $value) {
    // Use `$value` here
}

回答by Haim Evgi

function array_search_key( $needle_key, $array ) {
  foreach($array AS $key=>$value){
    if($key == $needle_key) return $value;
    if(is_array($value)){
      if( ($result = array_search_key($needle_key,$value)) !== false)
        return $result;
    }
  }
  return false;
} 

this will work !

这会工作!

you need to stop the recursive deep search, by return false and then check it in the function.

您需要通过 return false 停止递归深度搜索,然后在函数中检查它。

you can find more examples of functions (like using RecursiveArrayIterator and more) in this link : http://php.net/manual/en/function.array-search.php

您可以在此链接中找到更多函数示例(例如使用 RecursiveArrayIterator 等):http: //php.net/manual/en/function.array-search.php

回答by Ben Conley

The answer provided by xPheRe was extremely helpful, but didn't quite solve the problem in my implementation. There are multiple nested associative arrays in our data structure, and there may be multiple occurrences of any given key.

xPheRe 提供的答案非常有帮助,但并没有完全解决我的实现中的问题。我们的数据结构中有多个嵌套的关联数组,并且任何给定的键都可能多次出现。

In order to suit our purposes, I needed to implement a holder array that was updated while traversing the entire structure, instead of returning on the first match. The real work was provided by another poster, but I wanted to say thanks and share the final step that I had to cover.

为了满足我们的目的,我需要实现一个在遍历整个结构时更新的持有者数组,而不是在第一次匹配时返回。真正的工作是由另一张海报提供的,但我想说声谢谢并分享我必须涵盖的最后一步。

public function recursiveFind(array $array, $needle)
{
    $iterator  = new RecursiveArrayIterator($array);
    $recursive = new RecursiveIteratorIterator($iterator, RecursiveIteratorIterator::SELF_FIRST);
    $aHitList = array();
    foreach ($recursive as $key => $value) {
        if ($key === $needle) {
            array_push($aHitList, $value);
        }
    }
    return $aHitList;
}

回答by Ashish Awasthi

try this:

尝试这个:

array_walk_recursive(
    $arrayToFindKey, 
    function($value, $key, $matchingKey){
        return (strcasecmp($key, $matchingKey) == 0)? true : false;
    }
    , 'matchingKeyValue'
);

回答by Aditya Mittal

The best solution above misses the case if the key is repeated and only returns the first value, here I get all the values in an array instead:

如果键重复并且只返回第一个值,上面的最佳解决方案会错过这种情况,这里我改为获取数组中的所有值:

function recursiveFind(array $array, $needle) {
  $iterator = new RecursiveArrayIterator($array);
  $recursive = new RecursiveIteratorIterator($iterator, RecursiveIteratorIterator::SELF_FIRST);
  $return = [];
  foreach ($recursive as $key => $value) {
    if ($key === $needle) {
      $return[] = $value;
    }
  } 
  return $return;
}

回答by Parry Huang

I recently encounter the same issue, when dealing with Yii2 query object.

我最近在处理 Yii2 查询对象时遇到了同样的问题。

The reason your function didn't work is that the return action doesn't work here. Just pass a reference parameter to store the value, and do whatever you want afterwards.

您的函数不起作用的原因是返回操作在这里不起作用。只需传递一个引用参数来存储值,然后做任何你想做的事。

As you can see, this is a simple PHP function doesn't rely on any library. So I think its worth to mention with all the answer listed above.

如您所见,这是一个简单的 PHP 函数,不依赖于任何库。所以我认为上面列出的所有答案都值得一提。

function array_search_by_key_recursive($needle, array $haystack, &$return)
{
   foreach ($haystack as $k => $v) {
      if (is_array($v)) {
        array_search_by_key_recursive($needle, $v, $return);
      } else {
        if($k === $needle){
           $return = $v;
        }
      }
   }
}

array_search_by_key_recursive($needle, array $haystack, $return);

print_r($return);