【问题标题】:Giving PHP include()'d files parent variable scope给 PHP 包含()的文件父变量范围
【发布时间】:2011-01-13 18:56:21
【问题描述】:

无论如何,一个包含文件是否可以在其被调用的父范围中使用?下面的例子经过了简化,但作用相同。

本质上,一个文件将被一个函数包含,但希望被包含文件的范围是调用包含它的函数的范围。

main.php:

<?php
  if(!function_exists('myPlugin'))
  {
    function myPlugin($file)
      {
        if(file_exists($file)
        {
          require $file;
          return true;
        }
        return false;
      }
  }

  $myVar = 'something bar foo';

  $success = myPlugin('included.php');

  if($success)
  {
    echo $myResult;
  }

包含的.php:

<?php
  $myResult = strlen($myVar);

提前致谢,
亚历山大。

编辑:解决方案

嗯,有点,感谢 Chacha102 的贡献。
现在也可以从类中调用!

main.php

<?php
  class front_controller extends controller
  {
    public function index_page()
    {
      $myVar = 'hello!';

      // This is the bit that makes it work.
      // I know, wrapping it in an extract() is ugly,
      // and the amount of parameters that you can't change...
      extract(load_file('included.php', get_defined_vars(), $this));

      var_dump($myResult);
    }
    public function get_something()
    {
      return 'foo bar';
    }
  }

  function load_file($_file, $vars = array(), &$c = null)
  {
    if(!file_exists($_file))
    {
      return false;
    }
    if(is_array($vars))
    {
      unset($vars['c'], $vars['_file']);
      extract($vars);
    }
    require $_file;
    return get_defined_vars();
  }

包含的.php:

<?php
  $myResult = array(
    $myVar,
    $c->get_something()
  );

如果你想引用一个方法,它必须是公开的,但结果符合预期:

array(2) {
  [0]=>
  string(6) "hello!"
  [1]=>
  string(7) "foo bar"
}

现在,这并没有任何实际用途,我想知道如何做到这一点的唯一原因是因为我很固执。这个想法进入了我的脑海,并且不会让它打败我:D

&lt;rant&gt;
感谢所有做出贡献的人。除了那个嘘我的人。这是一个足够简单的问题,现在已经发现(复杂的)解决方案存在。
搞砸它是否“符合PHP的做事方式”。曾经告诉客户“哦不,我们不应该那样做,这不是正确的做事方式!”?没想到。
&lt;/rant&gt;

再次感谢 Chacha102 :)

【问题讨论】:

    标签: php function include scope


    【解决方案1】:
    function include_use_scope($file, $defined_variables)
    {
        extract($defined_variables);
        include($file);
    }
    
    include_use_scope("file.php", get_defined_vars());
    

    get_defined_vars() 获取在调用它的范围内定义的所有变量。extract() 接受一个数组并将它们定义为局部变量。

    extract(array("test"=>"hello"));
    echo $test; // hello
    
    $vars = get_defined_vars();
    echo $vars['test']; //hello
    

    因此,达到了预期的结果。但是,您可能希望从变量中去除超全局变量和其他内容,因为覆盖它们可能很糟糕。

    查看此comment 以消除不良影响。

    为了得到相反的结果,你可以这样做:

    function include_use_scope($file, $defined_variables)
    {
        extract($defined_variables);
        return include($file);
    }
    
    extract(include_use_scope("file.php", get_defined_vars()));
    

    include.php

    // do stuff
    return get_defined_vars();
    

    但总而言之,我认为您不会获得想要的效果,因为 PHP 不是这样构建的。

    【讨论】:

    • main.php 如何访问included.php 的本地变量,就像在OP 的代码中一样?
    • 嘎……忽略了那部分。我会回答说这只是一种方式,因为我相信双向操作是行不通的。
    • 我想出了一个解决方案,文件可以返回定义的变量,然后主文件可以提取它们..但它看起来真的很hacky和烦人。
    • 这确实给了我一个很好的想法。它冗长,复杂,而且不是真正必要的。但是感谢您的帮助!
    【解决方案2】:

    我知道的唯一方法是使用超全局数组。

    main.php:

      $GLOBALS['myVar'] = 'something bar foo';
    
      $success = myPlugin('included.php');
    
      if($success)
      {
        echo $GLOBALS['myResult'];
      }
    

    包含的.php:

    <?php
      $GLOBALS['myResult'] = strlen($GLOBALS['myVar']);
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-10-19
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-10-06
      相关资源
      最近更新 更多