Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it ever okay to have a class as a collection of methods and no properties?

I'm writing a bunch of generic-but-related functions to be used by different objects. I want to group the functions, but am not sure if I should put them in a class or simply a flat library file.

Treating them like a class doesn't seem right, as there is no one kind of object that will use them and such a class containing all these functions may not necessarily have any properties.

Treating them as a flat library file seems too simple, for lack of a better word.

What is the best practice for this?

like image 886
Old McStopher Avatar asked May 12 '11 18:05

Old McStopher


4 Answers

Check out namespaces:

http://www.php.net/manual/en/language.namespaces.rationale.php

Wrapping them in a useless class is a workaround implementation of the concept of a namespace. This concept allows you to avoid collisions with other functions in large projects or plugin/module type deployments.

EDIT

Stuck with PHP 5.2?

There's nothing wrong with using a separate file(s) to organize utility functions. Just be sure to document them with comments so you don't end up with bunchafunctions.php, a 20,000 file of procedural code of dubious purpose.

There's also nothing wrong with prefixes. Using prefixes is another way to organize like-purpose functions, but be sure to avoid these "pseudo-namespaces" already reserved by the language. Specifically, "__" is reserved as a prefix by PHP [reference]. To be extra careful, you can also wrap your function declarations in function_exists checks, if you're concerned about conflicting functions from other libraries:

if (!function_exists('myFunction')) {
    function myFunction() {
            //code
    }
}

You can also re-consider your object structure, maybe these utility functions would be more appropriate as methods in a base class that all the other objects can extend. Take a look at inheritance: http://www.php.net/manual/en/language.oop5.inheritance.php. The base class pattern is a common and very useful one:

abstract class baseObject {
    protected function doSomething () {
        print 'foo bar';
    }
    public function getSomething () {
        return 'bar foo';
    }
}

class foo extends baseObject {
    public function bar () {
        $this->doSomething();
    }
}

$myObject = new foo();
$myObject->bar();
echo $myObject->getSomething();

You can experiment with the above code here: http://codepad.org/neRtgkcQ

like image 117
Chris Baker Avatar answered Oct 06 '22 06:10

Chris Baker


I would usually stick them in a class anyway and mark the methods static. You might call it a static class, even though PHP actually has no such thing (you can't put the static keyword in front of a class). It's still better than having the functions globally because you avoid possible naming conflicts. The class becomes a sort of namespace, but PHP also has its own namespace which may be better suited to your purpose.

You might even find later that there are indeed properties you can add, even if they too are static, such as lazy-loaded helper objects, cached information, etc.

like image 27
Tesserex Avatar answered Oct 06 '22 07:10

Tesserex


I'd use classes with static methods in such case:

class Tools {

    static public function myMethod() {
         return 1*1;
    }

}

echo Tools::myMethod();

EDIT

As already mentioned by Chris and yes123: if the hoster already runs PHP 5.3+, you should consider using namespace. I'd recommend a read of Matthew Weier O'Phinney's article Why PHP Namespaces Matter, if you're not sure if it's worth switching to namespaces.

EDIT

Even though the ones generalizing usage of static methods as "bad practice" or "nonsense" did not explain why they consider it to be as such - which imo would've been more constructive - they still made me rethinking and rereading.

The typical arguments will be, that static methods can create dependencies and because of that can make unit testing and class renaming impossible.

If unit testing isn't used at all (maybe programming for home/personal use, or low-budget projects, where no one is willing to pay the extra costs of unit testing implementations) this argument becomes obsolete, of course.

Even if unit testing is used, creation of static methods dependencies can be avoided by using $var::myMethod(). So you still could use mocks and rename the class...

Nevertheless I came to the conclusion that my answer is way too generalized.

I think I better should've wrote: It depends.

As this most likely would result in an open ended debate of pros and cons of all the different solutions technically possible, and of dozens of possible scenarios and environments, I'm not willing going into this.

I upvoted Chris' answer now. It already covers most technical possibilities and should serve you well.

like image 39
Jürgen Thelen Avatar answered Oct 06 '22 05:10

Jürgen Thelen


Treating them as a class does give you the benefit of a namespace, though you could achieve the same thing by prefixing them like PHP does with the array_* functions. Since you don't have any properties, that basically implies that all your methods are static (as Class::method()). This isn't an uncommon practice in Java.

By using a class, you also have the ability, if necessary, to inherit from a parent class or interface. An example of this might be class constants defined for error codes your functions might return.

EDIT: If PHP 5.3+ is available, the Namespace feature is ideal. However, PHP versions still lag in a lot of hosts and servers, especially those running enterprise-stable Linux distributions.

like image 45
Michael Berkowski Avatar answered Oct 06 '22 07:10

Michael Berkowski