php 什么时候应该使用静态方法?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/33705976/
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
When should I use static methods?
提问by stack
I have a class that is containing 10 methods. I always need to use one of those methods. Now I want to know, which approach is better?
我有一个包含 10 个方法的类。我总是需要使用其中一种方法。现在我想知道,哪种方法更好?
class cls{
public function func1(){}
public function func2(){}
.
.
public function func10(){}
}
$obj = new cls;
$data = $obj->func3(); // it is random, it can be anything (func1, or func9 or ...)
OR
或者
class cls{
public static function func1(){}
public static function func2(){}
.
.
public static function func10(){}
}
cls::func3(); // it is random, it can be anything (func1, or func9 or ...)
回答by Gnucki
It is an interesting subject. I'm gonna give you a design oriented answer.
这是一个有趣的话题。我会给你一个面向设计的答案。
In my opinion, you should never use a static class/function in a good OOP architecture.
在我看来,你永远不应该在一个好的 OOP 架构中使用静态类/函数。
When you use static, this is to call a function without an instance of the class. The main reason is often to represent a service class which should not be instantiated many times.
当您使用静态时,这是在没有类的实例的情况下调用函数。主要原因通常是表示不应多次实例化的服务类。
I will give you 3 solutions (from the worst to the best) to achieve that:
我会给你 3 个解决方案(从最坏到最好)来实现这一目标:
Static
静止的
A static class (with only static functions) prevent you from using many OOP features like inheritance, interface implementation. If you really think of what is a static function, it is a function namespaced by the name of its class. You already have namespaces in PHP, so why add another layer?
静态类(只有静态函数)会阻止您使用许多 OOP 功能,例如继承、接口实现。如果你真的想到什么是静态函数,它就是一个以其类名命名的函数。您已经在 PHP 中拥有命名空间,那么为什么还要添加另一层呢?
Another big disadvantage is that you cannot define clear dependencies with your static class and the classes using it which is a bad thing for maintenability and scalability of your application.
另一个很大的缺点是你不能定义你的静态类和使用它的类的明确依赖关系,这对你的应用程序的可维护性和可伸缩性来说是一件坏事。
Singleton
单身人士
A singleton is a way to force a class to have only one instance:
单例是一种强制一个类只有一个实例的方法:
<?php
class Singleton {
// Unique instance.
private static $instance = null;
// Private constructor prevent you from instancing the class with "new".
private function __construct() {
}
// Method to get the unique instance.
public static function getInstance() {
// Create the instance if it does not exist.
if (!isset(self::$instance)) {
self::$instance = new Singleton();
}
// Return the unique instance.
return self::$instance;
}
}
It is a better way because you can use inheritance, interfaces and your method will be called on an instanciated object. This means you can define contracts and use low couplingwith the classes using it. However some people consider the singleton as an anti patternespecially because if you want to have 2 or more instances of your class with different input properties (like the classic example of the connection to 2 different databases) you cannot without a big refactoring of all your code using the singleton.
这是一种更好的方法,因为您可以使用继承、接口,并且您的方法将在实例化对象上调用。这意味着您可以定义契约并与使用它的类使用低耦合。然而,有些人认为单例是一种反模式,特别是因为如果你想拥有 2 个或更多具有不同输入属性的类实例(比如连接到 2 个不同数据库的经典示例),你不能没有对所有使用单例的代码。
Service
服务
A service is an instance of a standard class. It is a way to rationalize your code. This kind of architecture is called SOA (service oriented architecture). I give you an example:
服务是标准类的实例。这是一种合理化代码的方法。这种架构称为 SOA(面向服务的架构)。我给你举个例子:
If you want to add a method to sell a product in a store to a consumer and you have classes Product
, Store
and Consumer
. Where should you instantiate this method? I can guarantee that if you think it is more logical in one of these three class today it could be anything else tomorrow. This leads to lots of duplications and a difficulty to find where is the code you are looking for. Instead, you can use a service class like a SaleHandler
for example which will know how to manipulate your data classes.
如果您想添加一种方法来将商店中的产品销售给消费者并且您有类Product
,Store
并且Consumer
. 你应该在哪里实例化这个方法?我可以保证,如果您认为今天在这三门课中的一门课中更合乎逻辑,那么明天可能是其他任何课程。这会导致大量重复,并且很难找到您要查找的代码。相反,您可以使用像SaleHandler
example 这样的服务类,它将知道如何操作您的数据类。
It is a good idea to use a framework helping you to inject them into each others (dependency injection) in order to use them at their full potential. In the PHP community, you have a nice example of implementation of this in Symfony2for instance.
最好使用一个框架来帮助您将它们相互注入(依赖注入),以便充分发挥它们的潜力。例如,在 PHP 社区中,您有一个在Symfony2中实现此功能的很好示例。
To sum up:
总结:
If you do not have a framework, singletons are certainly an option even if I personally prefer a simple file where I make manual dependency injection.
If you have a framework, use its dependency injection feature to do that kind of thing.
You should not use static method (in OOP). If you need a static method in one of your class, this means you can create a new singleton/service containing this method and inject it to the instance of classes needing it.
如果你没有框架,单例当然是一个选择,即使我个人更喜欢一个我手动进行依赖注入的简单文件。
如果你有一个框架,使用它的依赖注入特性来做那种事情。
您不应该使用静态方法(在 OOP 中)。如果您的类中需要一个静态方法,这意味着您可以创建一个包含此方法的新单例/服务,并将其注入需要它的类的实例。
回答by weirdpanda
So, there is a very basic difference in static
methods.
因此,在static
方法上存在非常基本的差异。
To use static functions, you don't need to initialise the class as an object. For example, Math.pow()
, here .pow()
(in Java; but the explanation still holds) is a static method.
要使用静态函数,您不需要将类初始化为对象。例如,Math.pow()
这里.pow()
(在 Java 中;但解释仍然成立)是一个静态方法。
The general rule is to make the helper methods static
.
一般规则是制作辅助方法static
。
So, for example, if you have a Math class, you wouldn't want to fill the garbage collector with classes which just help other, more important, classes.
因此,例如,如果您有一个 Math 类,您不会想用只帮助其他更重要的类的类来填充垃圾收集器。
You can use it as dynamic initializers, if you please!
如果您愿意,您可以将其用作动态初始值设定项!
Let's say you have a class RSAEncryptionHelper
, now you can generally initialize it without any parameters and this will generate an object with a key size of (say) 512
bits; but you also have an overloaded object constructorwhich gets all of the properties from other classes:
假设您有一个 class RSAEncryptionHelper
,现在您通常可以在没有任何参数的情况下对其进行初始化,这将生成一个密钥大小为(例如)512
位的对象;但是您还有一个重载的对象构造函数,它从其他类中获取所有属性:
$a = new RSAEncryptionHelper::fromPrimeSet(...);
回答by Scott M.
The answer depends on what those methods do. If you're using them to mutate the state of the object at hand, you need to use the instance method calls. If they're independent functionality, then you can use the static versions, but then I'd question why they're part of a class at all.
答案取决于这些方法的作用。如果您使用它们来改变手头对象的状态,则需要使用实例方法调用。如果它们是独立的功能,那么您可以使用静态版本,但是我会质疑为什么它们是一个类的一部分。
回答by Lenin Zapata
Within a PHP class you can use class/methods/attributes: Abstract, Static
, Private, Public, etc ...
The best way is to know how to mix them all within a class depending on the need, I will give you a basic example:
在 PHP 类中,您可以使用类/方法/属性:抽象、Static
私有、公共等......最好的方法是知道如何根据需要在一个类中混合它们,我会给你一个基本的例子:
Within the Person
class, you have privateand publicmethods, but you have a method called "get_nationality" so this is a function that you need somewhere else but you do not have the Person
class installed yet, so this method you put it as STATICin this way you can invoke the "get_nationality" method without installing any Person
class, this makes your business model more optimal and in turn now resources in the CPU.
在Person
该类中,您有私有和公共方法,但是您有一个名为“ get_nationality”的方法,所以这是您在其他地方需要的一个函数,但您Person
尚未安装该类,因此您将此方法作为STATIC放在此您可以在不安装任何类的情况下调用“ get_nationality”方法的方式Person
,这使您的业务模型更加优化,进而现在 CPU 中的资源。
回答by Afraz Ahmad
Static functionsare also very useful but I usually make traitswhen I have to create functions that are independently related to a class.
静态函数也非常有用,但是当我必须创建与类独立相关的函数时,我通常会创建特征。
I don't know if this approach is better or not but most times I found it useful.
我不知道这种方法是否更好,但大多数时候我发现它很有用。
Just sharing my approach here so that I can learn more about its pros and cons.
只是在这里分享我的方法,以便我可以更多地了解它的优缺点。