我正在处理有关此项目的最佳做法和效果的几个问题。请原谅我这个大问题。
我目前正在使用PHP和MySql构建一个基于文本的游戏,到目前为止核心文件中大约有2,500行。目前,这是一个完全模块化的功能库。一些用于数据访问,一些用于数据操作,等等。
我的第一个问题是:一个类ItemManager包含几十个专门用于添加,更新和删除数据库中游戏项的方法。这些方法在与数据库交互时唯一的共同点。目前,构造函数请求mysqli对象,然后在其所有函数中使用它。但是,一旦我将MongoDB添加到项目中,其中一些功能可能会与不同的数据库进行交互。
简单地将所有这些功能都设为静态是否可接受或更可取?我认为没有理由在只有一个对象的情况下实例化对象,并且不需要它来维护类成员。 那么,我应该使用静态方法吗?为什么?
第二个问题:有人可以帮我理解在PHP BESIDES模块化中使用类的好处(因为我可以用函数文件实现相同的效果)吗?来自Java背景,我认识到OOP在持久环境中的好处,因为对象在应用程序的整个生命周期中维护数据和状态。但是,使用PHP,脚本的生命周期只有几分之一秒,所有状态信息都存储在数据库中。几乎所有函数都只是操纵数据库,那么目的是什么?当我只能调用函数时,实例化对象是不是没有意义?我可以只执行包含分类数据操作类的完全静态类,而无需实例化类的对象吗? 我应该使用类而不是函数文件的原因是什么?是不是基本相同?完全静态功能是否可以接受?
感谢您的时间,我不知道如何将这个问题减少到更少的文字,所以我道歉。
答案 0 :(得分:0)
那么,我应该使用静态方法吗?为什么呢?
静态方法通常访问静态变量,这些变量是全局状态(它们与这方面的全局变量没有区别),由于很多原因,这些变量很糟糕。
此外,虽然对象实例可以由具有相同接口的其他对象替换,但只需将其他对象传递给使用它的函数,静态方法就不能轻易替换。因此,您无法模拟它们,使用它们的代码也不容易进行单元测试。
如果可以,请不要使用静态方法。
答案 1 :(得分:0)
1)坚持使用对象,因为它可以通过其他数据库驱动程序轻松替换或扩展(例如,您可以覆盖某些功能以透明地重定向到MongoDB以获取特殊的getter。)如果您确定你只会使用一次实例,使用单例,甚至更好的regitry模式。
2) PHP的生命周期并不短。使用MVC模式,它处理引导程序,路由,模型,业务逻辑和输出。因此,虽然单个请求可能只需要几秒钟,但它可能涉及数百个类和数千个方法。
坚持你的RPG示例:有一天你可能会决定让它成为多人游戏。现在你可以实现第二个玩家对象,或者调整大约500个函数。前一个仅适用于类。
一个很重要的原因是人为限制:不太可能记住成千上万个功能的含义,尤其是在团队合作时。通过使用对象,您可以定义slim API。如果player-object具有公共方法add_item(\ item $ item)和remove_item(\ item $ item),则不需要记住所有这些检查,计算和db处理函数。你甚至可以要求一位开发人员“创建一个只有攻击()方法的怪物项目”。就是这样,你完成了,合作最好。
结论如果您来自Java背景并且了解OOP,请不要再三思其辞职。 PHP不是scriptkiddies使用的前OO脚本。这是一个成熟的OO环境 - 但如果您利用这一点,这取决于您。
答案 2 :(得分:0)
简单地制作所有这些是否可以接受或者更可取 功能静态?我认为没有理由在那里实例化对象 永远只会是一个
没有理由实例化对象如果您想要做的就是这个类能够做什么。通过使用静态方法,您可以通过在整个代码库中对类名进行硬编码来将所有客户端代码与类耦合。如果稍后您决定可能需要不同的项目经理服务来满足您的要求,那么您肯定会有糟糕的一天。
请注意,“不同的项目管理器”可以简单地代码为“用于对代码的其余部分进行单元测试的模拟管理器”。因此,即使在永远不会支持替代方案的情况下,使用这样的静态也会使您的代码几乎不可测试。
当然,您已经提到过,很可能会有一个不同的项目管理器:如果当前的项目管理器接受mysqli
对象,那么很明显,您的经理代码与{{}之间没有抽象层。 1}}接口。如果要使用其他对象连接到Mongo,当前项目管理器代码如何支持这两种配置?你不需要写一个新的项目经理课吗?如果类名在任何地方被硬编码,你将如何将它与其余代码集成?
让我们从另一方面看待情况:mysqli
获得了什么?
显然,它使项目管理器成为“单身”对象,这可能听起来像一个好主意,因为“只有一个”。这个想法不能在PHP中被忽略(如支持多线程并且存在隐藏的跨线程依赖性的其他语言),但它仍然没有多少水。如果您希望项目经理成为单身人士,那么就不要创建第二个实例。如果由于某种原因想要强制,请使用静态变量来计算实例化,如果尝试多个,则抛出。最后,创建类static
,以便无法删除此限制。结果:单身不是final
。
这就是static
为此所做的一切,鉴于上述情况,作为一个论点,它是非常弱的。
并且没有必要保持上课 成员。那么,我应该使用静态方法吗?为什么呢?
我不确定这意味着什么 - 你说构造函数已经需要一个数据库驱动程序对象,它有权成为类成员。这是另一个明显的暗示,静态不是这里的方式。
有人可以帮助我理解在PHP中使用类的好处 BESIDES模块化(因为我可以实现与文件相同的效果) 函数)?
我不会在这里提出明显的OOP参数,而是提出一个反点:你可以实现相同的运行时效果,但是你肯定无法达到相同的可维护性水平和应用程序的可调试性。为什么要使用劣质解决方案?
来自Java背景,我认识到OOP的优势 持久环境,因为对象始终保持数据和状态 申请的生命。但是,用PHP,一生的寿命 脚本只是一小部分,所有状态信息都存储起来 在数据库中。几乎所有函数都只是操纵数据库, 那么目的是什么?在实例化对象时不是没有意义的 我只能打电话给函数?
进程的生命周期只是一小部分。 代码库的生命周期以数月,数年和数十年来衡量。这就是人们维持它的时间,这也是我们首先使用OOP的原因。
全局变量可以保持状态和类成员一样,人们在“面向对象”这个术语之前很久就维持状态。 OO的好处是管理代码的源代码级模型的复杂性,我绝对不会同意将其描述为毫无意义。