php:确定从哪里调用函数

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2960805/
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 08:15:37  来源:igfitidea点击:

php: determine where function was called from

phpfunction-calls

提问by pol_b

is there a way to find out, where a function in PHP was called from? example:

有没有办法找出PHP中的函数是从哪里调用的?例子:

function epic()
{
  fail();
}

function fail()
{
  //at this point, how do i know, that epic() has called this function?
}

回答by romac

You can use debug_backtrace().

您可以使用debug_backtrace().

Example:

例子:

<?php

function epic( $a, $b )
{
    fail( $a . ' ' . $b );
}

function fail( $string )
{
    $backtrace = debug_backtrace();

    print_r( $backtrace );
}

epic( 'Hello', 'World' );

Output:

输出:

Array
(
    [0] => Array
        (
            [file] => /Users/romac/Desktop/test.php
            [line] => 5
            [function] => fail
            [args] => Array
                (
                    [0] => Hello World
                )

        )

    [1] => Array
        (
            [file] => /Users/romac/Desktop/test.php
            [line] => 15
            [function] => epic
            [args] => Array
                (
                    [0] => Hello
                    [1] => World
                )

        )

)

回答by BoltClock

Use debug_backtrace():

使用debug_backtrace()

function fail()
{
    $backtrace = debug_backtrace();

    // Here, $backtrace[0] points to fail(), so we'll look in $backtrace[1] instead
    if (isset($backtrace[1]['function']) && $backtrace[1]['function'] == 'epic')
    {
        // Called by epic()...
    }
}

回答by Mariusz Charczuk

Fastest and simplest solution as I found

我发现的最快和最简单的解决方案

public function func() { //function whose call file you want to find
    $trace = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 1);
}

$trace: Array
(
    [0] => Array
        (
            [file] => C:\wamp\www\index.php
            [line] => 56
            [function] => func
            [class] => (func Class namespace)
            [type] => ->
        )

)

I test the speed on Lenovo laptop: Intel Pentiom CPU N3530 2.16GHz, RAM 8GB

我在联想笔记本电脑上测试速度:Intel Pentiom CPU N3530 2.16GHz,RAM 8GB

global $times;
$start = microtime(true);
$trace = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS, 1);
$times[] = microtime(true) - $start;

Results:

结果:

count($times):  97
min:    2.6941299438477E-5
max:   10.68115234375E-5
avg:    3.3095939872191E-5
median: 3.0517578125E-5
sum:  321.03061676025E-5

the same results with notation without E-5
count($times):  97
min:    0.000026941299438477
max:    0.0001068115234375
avg:    0.000033095939872191
median: 0.000030517578125
sum:    0.0032103061676025

回答by marverix

So if you still REALLY don't know how, than here is solution:

因此,如果您仍然真的不知道如何,那么这里是解决方案:

$backtrace = debug_backtrace();
echo 'Mu name is '.$backtrace[1]['function'].', and I have called him! Muahahah!';

回答by Yehonatan

Use the debug_backtrace function: http://php.net/manual/en/function.debug-backtrace.php

使用 debug_backtrace 函数:http://php.net/manual/en/function.debug-backtrace.php

回答by Makwana Ketan

Try below code.

试试下面的代码。

foreach(debug_backtrace() as $t) {              
   echo $t['file'] . ' line ' . $t['line'] . ' calls ' . $t['function'] . "()<br/>";
}

回答by Phillip Weber

If you want to trace the exact origin of the call at the top of the stack you can use the following code:

如果要在堆栈顶部跟踪调用的确切来源,可以使用以下代码:

$call_origin = end(debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS));

This will ignore chained functions and get only the most relevant call info (relevant is used loosely as it depends what your are trying to accomplish).

这将忽略链式函数并仅获取最相关的调用信息(相关使用松散,因为它取决于您要完成的任务)。

回答by Alien

function findFunction($function, $inputDirectory=""){
    //version 0.1
    $docRoot = getenv("DOCUMENT_ROOT");
    $folderArray = null;
    $dirArray = null;

    // open directory
    $directory = opendir($docRoot.$inputDirectory);

    // get each entry
    while($entryName = readdir($directory)) {
        if(is_dir($entryName) && $entryName != "." && $entryName != ".."){
            $folderArray[] = str_replace($inputDirectory, "", $entryName);
        }
        $ext = explode(".", $entryName);
        if(!empty($ext[1])){
            $dirArray[] = $docRoot.$inputDirectory."/".$entryName;
        }
    }

    // close directory
    closedir($directory);
    $found = false;

    if(is_array($dirArray)){
        foreach($dirArray as $current){
            $myFile = file_get_contents($current);
            $myFile = str_replace("<?php", "", $myFile);
            $myFile = str_replace("?>", "", $myFile);
            if(preg_match("/function ".$function."/", $myFile)){
                $found = true;
                $foundLocation = $current;
                break;
            }
        }
    }
    if($found){
        echo $foundLocation;
        exit;
    } else if(is_array($folderArray)){
        foreach($folderArray as $folder){
            if(!isset($return)){
                $return = findFunction($function, $inputDirectory."/".$folder);
            } else if($return == false){
                $return = findFunction($function, $inputDirectory."/".$folder);
            }
        }
    } else {
        return false;
    }
}

findFunction("testFunction", "rootDirectory");

Hope it helps somebody. If the actual function is outside httpdocs then it can not be found because the server will be setup to not allow it. Only tested it one folder deep too but the recursive methodology should work in theory.

希望它可以帮助某人。如果实际功能在 httpdocs 之外,则无法找到它,因为服务器将设置为不允许它。也只测试了一个文件夹深,但递归方法理论上应该有效。

This is like version 0.1 but I don't intend on continuing development on it so if someone updates it feel free to repost it.

这类似于 0.1 版,但我不打算继续开发它,因此如果有人更新它,请随时重新发布。