【问题标题】:Call functions of 2nd class from 1st class's outside object in php从 php 中第一类的外部对象调用第二类的函数
【发布时间】:2017-11-30 11:29:34
【问题描述】:

我需要您的指导,这可能是一个非常基本的问题,但即使经过大量谷歌搜索,我也无法弄清楚这一点。我可以通过 Eureka 类访问其他类的变量,但不能访问它们的函数。

这是我的情况:

index.php 中的类自动加载函数

<?php
function __autoload($class_name)
{
    //$class_name = strtolower($class_name);
    $path = "{$class_name}.php";
    if (file_exists($path)) {
        include ($path);
    } else {
        die("{$path} file could not be found!<br />");
    }
}
?>

基类,我想在html页面上使用这个类的对象访问所有其他类:

<?php
    class Eureka
    {
        public $some_var1;

        public function get_all_settings()
        {
            echo 'get_all_settings was called from Eureka class.';
        }
    }
?>

timezone.php 中的时区类

<?php
class TimeZone
    {
        public $some_var2;

        public function get_time_zone()
        {
            echo 'get_time_zone was called from TimeZone class.';
        }
    }
 ?>

location.php 中的位置类

<?php
    class Location
    {
        public $some_var3;

        public function set_location($location_name)
        {
            echo 'set_location was called from Location class.';
        }
    }
?>

html页面索引.php

<?php
 $eureka = new Eureka;

    //**How can I achieve this ????**
    $eureka->TimeZone->get_time_zone();
    //**OR**
    $eureka->Location->set_location('some_location_name');       
?>

例如当 $eureka 对象调用 'TimeZone' 类时,它应该被加载并调用 'get_time_zone()' 方法没有任何错误。

【问题讨论】:

  • 修改 Eureka 类的构造函数,创建新的 TimeZone 和 Location 实例,并将它们存储为属性......public function __construct() { $this-&gt;TimeZone = new TimeZone(); $this-&gt;Location = new Location(); }
  • 这不是它的工作方式,也不是依赖注入。你可以实现__get 来做到这一点,但这完全是错误的。
  • 或者你可以使用魔术__get()方法
  • 但是像你描述你的“Eureka”类的“God Class”是非常糟糕的编码实践
  • @MarkBaker 我不一定会这么说,CI 是一个“神”类。这取决于它在功能上是否适合应用程序或惰性。让我告诉你我是一个懒惰的程序员。但是我建造东西是为了为我建造东西,这就是我的懒惰。

标签: php oop dependency-injection


【解决方案1】:

你必须做这样的事情,基本上你将其他类存储在第一个类中,然后访问它们。毕竟不能凭空拉出来。

<?php
    class Eureka
    {
        protected $someVar1; //shouldn't really use public, instead use getters and setters

        protected $TimeZone;

        //should use dependacy injection
        public function __construct(TimeZone $TimeZone = null){
               if($TimeZone) $this->setTimeZone($timezone);
        }

        public function getTimeZone(){
            return $this->TimeZone;
        }

        public function setTimeZone(TimeZone $TimeZone){
            $this->TimeZone =  $TimeZone;
        }

        public function getAllSettings()
        {
            echo 'get_all_settings was called from Eureka class.';
        }
    }

    class TimeZone
    {
        protected $someVar2;

        public function getTimeZone()
        {
            echo 'get_time_zone was called from TimeZone class.';
        }

        public function hello(){
            echo "Hello";
        }
    }


    $Eureka = new Eureka( new TimeZone() );

    $Eureka->getTimeZone()->hello();

就您的代码风格get_time_zone 而言,您可以在技术上按照您的意愿命名它们。我个人尝试遵循PSR-2 标准。

你不应该使用公共属性,因为一个类应该是一个黑盒子,它不应该将它的实现暴露给外界。这将使以后重构类和维护它更容易。

如果您将其打开以查看其余代码,您将在整个应用程序中搜索您使用这些属性的位置。您可以尝试与methods 争论相同,但我会说考虑一下。

class Foo
{
    protected $bar;

    public function getBar()
    {
        return $this->bar;
    }
}

$Foo = new Foo;
echo $Foo->getBar();

如果你重构它

class Foo
{
    protected $baz; //renamed

    public function getBar()
    {
        return $this->baz;
    }
}

//no code change requred
$Foo = new Foo;
echo $Foo->getBar();

如果你这样做

class Foo
{
    public $bar;
}

$Foo = new Foo;
echo $Foo->bar;

然后改变它

class Foo
{
    public $baz; //changed
}

$Foo = new Foo;
echo $Foo->baz; //also required changing

这是一个非常简单的小例子,但这些事情很快就会失控。使用public 确实限制了自己,大多数新手编码人员认为protected 更受限制。当它反过来时。

http://www.php-fig.org/psr/psr-2/

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-09-17
    • 1970-01-01
    • 2015-08-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多