使用“The Tortoise and the Hare”算法来检测循环。

原型

wp_find_hierarchy_loop_tortoise_hare( callable $callback, int $start, array $override = array(), array $callback_args = array(), bool $_return_loop = false )

描述

对于算法的每一步,兔子都需要两个步骤而龟子需要两个步骤。如果野兔曾经舔过乌龟,就必须有一个循环。

参数

$callback (callable) (Required) 接受(ID,callback_arg,…)并输出parent_ID的函数。

$start (int) (Required) 启动循环检查的ID。

$override (array) (Optional)  要使用的数组(ID => parent_ID,…)而不是$ callback。

$callback_args (array) (Optional)  要发送到$ callback的其他参数。

$_return_loop (bool) (Optional)  返回循环成员还是只检测循环的存在?如果你已经知道给定的$ start是循环的一部分,则仅设置为true(否则返回的数组可能包含分支)。

返回值

(mixed)  循环的某个任意成员的标量ID,或者循环的所有成员的ID数组(如果$ _return_loop)

源文件

路径:wp-includes/functions.php

<?php
...
function wp_find_hierarchy_loop_tortoise_hare( $callback, $start, $override = array(), $callback_args = array(), $_return_loop = false ) {
	$tortoise = $hare = $evanescent_hare = $start;
	$return = array();
	// Set evanescent_hare to one past hare
	// Increment hare two steps
	while (
		$tortoise
	&&
		( $evanescent_hare = isset( $override[$hare] ) ? $override[$hare] : call_user_func_array( $callback, array_merge( array( $hare ), $callback_args ) ) )
	&&
		( $hare = isset( $override[$evanescent_hare] ) ? $override[$evanescent_hare] : call_user_func_array( $callback, array_merge( array( $evanescent_hare ), $callback_args ) ) )
	) {
		if ( $_return_loop )
			$return[$tortoise] = $return[$evanescent_hare] = $return[$hare] = true;
		// tortoise got lapped - must be a loop
		if ( $tortoise == $evanescent_hare || $tortoise == $hare )
			return $_return_loop ? $return : $tortoise;
		// Increment tortoise by one step
		$tortoise = isset( $override[$tortoise] ) ? $override[$tortoise] : call_user_func_array( $callback, array_merge( array( $tortoise ), $callback_args ) );
	}
	return false;
}
...
?>

其他

英文文档:https://developer.wordpress.org/reference/functions/wp_find_hierarchy_loop_tortoise_hare/