我可以将代码包含到PHP类中吗? [英] Can I include code into a PHP class?

查看:170
本文介绍了我可以将代码包含到PHP类中吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想做一个PHP类,让我们说Myclass.php。现在在这个类中,我想只定义类本身和一些实例变量。但是所有的方法必须来自一个Myclass_methods.php文件。我可以只将该文件包括到类体吗?



我有很好的理由为什么我想分离这个。总之,我将有一个后端,我可以改变一个类的业务逻辑,而所有其他的事情必须保持不变。系统为我维护所有的ORM和其他东西。



但是如果这是一个坏主意,最好重新生成整个类文件编辑后业务逻辑(所以,在这种情况下,用户定义的方法)。



性能问题:如果在一个请求Myclass.php只包括一次,实际上Myclass_methods.php应该也只包括一次。可能是错误的。专家?

解决方案

否。

在定义类的文件中,您只能将文件包含在方法主体



从您的说明中我带你想要:

 <?php // MyClass.php 
class MyClass
{
protected $ _prop;
include'myclass-methods.php';
}

<?php // myclass-methods.php
public function myMethod()
{
$ this-> $ _ prop = 1;
}

运行此代码将导致

 解析错误:语法错误,意外的T_INCLUDE,期待T_FUNCTION 


$ b b

这是可能的

 <?php // MyClass.php 
class MyClass
{
protected $ _prop;
public function __construct()//或任何其他方法
{
include'some-functions.php';
foo($ b); // echoes'a';
}
}

<?php // some-functions.php
$ b ='a';
function foo($ str)
{
echo $ str;
}

这样做会将include文件的内容导入方法范围,而不是类范围。您可以在include文件中包括函数和变量,但不包括方法。您可以但不应将整个脚本放入其中,并更改方法的效果,例如

 <?php // MyClass.php 
// ...
public function __construct($ someCondition)
{
// No No here here
include ($ someCondition ==='whatever')? 'whatever.php':'default.php';
}
// ...

<?php // whatever.php
echo'whatever';

<?php // default.php
echo'foo';但是,以这种方式修补类来展示不同的行为不是你应该如何在OOP中做它。这是纯粹的错误,应该让你的眼睛流血。



由于你想动态改变行为,扩展类也不是一个好的选择(见下文为什么)。你真正想要做的是写一个界面,并使你的类使用实现此接口的对象,从而确保适当的方法可用。这称为策略模式,工作方式如下:

 <?php // Meowing.php 
interface Meowing
{
public function meow
}

现在你得到了所有喵行为必须服从的契约,方法。下一步定义一个喵行为:

 <?php // RegularMeow.php 
class RegularMeow implements Meowing
{
public function meow()
{
return'meow';
}
}



现在要使用它:

 <?php // Cat.php 
class Cat
{
protected $ _meowing;

public function setMeowing(Meowing $ meowing)
{
$ this-> _meowing = $ meowing;
}

public function meow()
{
$ this-> _meowing-> meow()
}
}

添加Meowing TypeHint setMeowing,你确保传递的参数实现Meowing接口。让我们定义另一个喵行为:

 <?php // LolkatMeow.php 
类LolkatMeow implements Meowing
{
public function meow()
{
return'lolz xD';
}
}

现在,您可以轻松地交换这样的行为: / p>

 <?php 
require_once'Meowing.php';
require_once'RegularMeow.php';
require_once'LolkatMeow.php';
require_once'Cat.php';

$ cat = new Cat;
$ cat-> setMeowing(new RegularMeow);
echo $ cat-> meow; // outputs'meow';
//现在改变行为
$ cat-> setMeowing(new LolkatMeow);
echo $ cat-> meow; // outputs'lolz xD';

虽然你也可以用继承,方法是定义抽象 BaseCat和喵方法,然后从中导出具体的RegularCat和Lolkat类,你必须考虑你想要实现什么。如果你的猫永远不会改变他们喵的方式,继续使用继承,但如果你的RegularCat和Lolkat应该能够做任意的声音,那么使用战略模式。



有关PHP中的设计模式的更多信息,请查看以下资源:




I want to make a PHP class, lets say Myclass.php. Now inside that class I want to define just the class itself and some instance variables. But all the methods must come from a Myclass_methods.php file. Can I just include that file into the class body?

I have good reasons why I want to seperate this. In short, I'll have a backend in which I can change the business logic of a class, while all other things must remain untouched. The system maintains all the ORM and other stuff for me.

But if this is a bad idea, it might be better to re-generate the whole class file after editing the business logic (so, the user-defined methods in this case).

Performance question: If during one request Myclass.php is included just once, actually that Myclass_methods.php should also be included just once. Might be wrong. Experts?

解决方案

No. You cannot include files in the class body.
In a file defining a class, you may only include files in a method body or outside the class body.

From your description I take you want this:

<?php // MyClass.php
class MyClass
{
    protected $_prop;
    include 'myclass-methods.php';
}

<?php // myclass-methods.php
public function myMethod()
{
   $this->$_prop = 1;
}

Running this code will result in

Parse error: syntax error, unexpected T_INCLUDE, expecting T_FUNCTION

What is possible though is this

<?php // MyClass.php
class MyClass
{
    protected $_prop;
    public function __construct() // or any other method
    {
        include 'some-functions.php';
        foo($b); // echoes 'a';
    }
}

<?php // some-functions.php
$b = 'a';
function foo($str)
{
   echo $str;
}

Doing it this way, will import the contents of the include file into the method scope, not the class scope. You may include functions and variables in the include file, but not methods. You could but should not put entire scripts into it as well and change what the method does, e.g.

<?php // MyClass.php
    // ...
    public function __construct($someCondition)
    {
        // No No Code here
        include ($someCondition === 'whatever') ? 'whatever.php' : 'default.php';
    }
    // ...

<?php // whatever.php
    echo 'whatever';

<?php // default.php
    echo 'foo';

However, patching the class this way to exhibit different behavior is not how you should do it in OOP. It's just plain wrong and should make your eyes bleed.

Since you want to dynamically change behavior, extending the class is also not a good option (see below why). What you really will want to do is write an interface and make your class use objects implementing this interface, thus making sure the appropriate methods are available. This is called a Strategy Pattern and works like this:

<?php // Meowing.php 
interface Meowing
{
    public function meow();
}

Now you got the contract that all Meowing Behaviors must obey, namely having a meow method. Next define a Meowing Behavior:

<?php // RegularMeow.php
class RegularMeow implements Meowing
{
    public function meow()
    {
        return 'meow';
    }
}

Now to use it, use:

<?php // Cat.php
class Cat
{
    protected $_meowing;

    public function setMeowing(Meowing $meowing)
    {
        $this->_meowing = $meowing;
    }

    public function meow()
    {
        $this->_meowing->meow()
    }
}

By adding the Meowing TypeHint to setMeowing, you make sure that the passed param implements the Meowing interface. Let's define another Meowing Behavior:

<?php // LolkatMeow.php
class LolkatMeow implements Meowing
{
    public function meow()
    {
        return 'lolz xD';
    }
}

Now, you can easily interchange behaviors like this:

<?php
require_once 'Meowing.php';
require_once 'RegularMeow.php';
require_once 'LolkatMeow.php';
require_once 'Cat.php';

$cat = new Cat;
$cat->setMeowing(new RegularMeow);
echo $cat->meow; // outputs 'meow';
// now to change the behavior
$cat->setMeowing(new LolkatMeow);
echo $cat->meow; // outputs 'lolz xD';

While you also could have solved the above with inheritance by defining an abstract BaseCat and meow method and then deriving concrete RegularCat and Lolkat classes from that, you have to consider what you want to achieve. If your cats will never change the way they meow, go ahead and use inheritance, but if your RegularCat and Lolkat is supposed to be able to do arbitrary meows, then use the Strategy pattern.

For more design patterns in PHP, check these resources:

这篇关于我可以将代码包含到PHP类中吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆