Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

I have a switch statement

    switch ( $id ) {
        case 'abc':    return 'Animal';
        case 'xyz':    return 'Human';
                    //many more
                    }

I am returning class names,and use them to call some of their static functions using call_user_func(). Instead I can also create a object of that class, return that and then call the static function from that object as $object::method($param)

    switch ( $id ) {
        case 'abc':    return new Animal;
        case 'xyz':    return new Human;
                    //many more
                    }

Which way is efficient? To make this question broader : I have classes that have mostly all static methods right now, putting them into classes is kind of a grouping idea here (for example the DB table structure of Animal is given by class Animal and so for Human class). I need to access many functions from these classes so the switch needs to give me access to the class

share|improve this question
    
I'm not proficient in PHP but could you return a delegate/function pointer/callback? –  MattDavey Jun 14 '12 at 17:11
    
@MattDavey I need the class not a single function –  nischayn22 Jun 14 '12 at 17:15
1  
Are you sure you need the class? It seems from the question you just want to execute one or more functions... –  MattDavey Jun 14 '12 at 17:17
    
I need more than one static functions from that class, so I return the class –  nischayn22 Jun 14 '12 at 17:49
    
Please move your clarifying comments (the above one and the one on Dibbeke's answer) into the question itself, they are easy to miss as comments. –  Yannis Rizos Jun 14 '12 at 19:25
show 1 more comment

3 Answers

up vote 4 down vote accepted

Obviously, needlessly calling a constructor for the sole reason of calling a static method is less efficient. Apparently there is some kind of meta-class encapsulating the static behavior of Animal/Human or perhaps the static method has the wrong location. The situation reeks of a modelling/design error, but there isn't enough context to determine which.

share|improve this answer
    
IANAPHPprogrammer, but it could also be a limitation of the language in use. At an abstract level, it does seem to be the wrong way about it. –  GlenH7 Jun 14 '12 at 17:30
    
PHP certainly has some odd limitations and edge cases that can be cumbersome... –  tdammers Jun 14 '12 at 17:30
    
I am starting to implement these classes and right now they have only a bunch of static methods, so there isn't any constructor atm –  nischayn22 Jun 14 '12 at 17:56
    
If you only have static methods, you are most likely abstracting at the wrong level. A static method is essentially a 'normal' method of the meta-class (the class of the class). But since you probably don't have a language in which you can express behavior of meta-classes, you should model the meta-class as a normal class instead and have it produce instances, just like you'd do with a factory pattern (you'd return factories with behavior that allows you to instantiate objects implementing an interface). Hope this makes sense to you. –  Dibbeke Jun 14 '12 at 18:58
    
By the way, if it doesn't, please say so. I can't become a good teacher without feedback :) –  Dibbeke Jun 14 '12 at 19:01
show 2 more comments

can you do factory methods in PHP?

Interfrace IMethodsINeedToCall()
    Method1INeed();
    Method2INeed();

and your Animal / Human classes implement the interface:

Class Animal:IMethodsINeedToCall
    ...implement methods

Class Human:IMethodsINeedToCall
    ...implement methods    

IMethodsINeedToCall animalResults = CallSwitchStatementAndRetrunObject('animal');

animalResults.Method1INeed();
animalResults.Method2INeed();

IMethodsINeedToCall humanResults = CallSwitchStatementAndRetrunObject('human');

humanResults.Method1INeed();
humanResults.Method2INeed();

not sure if PHP supports that methodology... I"m sure it does to some extent, but seems like a clean approach.

share|improve this answer
    
+1 This is basically what I'm trying to get at in my comments in the question –  MattDavey Jun 14 '12 at 18:08
add comment

Definitely go with the static-calling route. Constructing an object for the sole purpose of calling a static method on it is wasteful, but since you've decided to use PHP, you shouldn't be worrying about optimization on this level anyway. What you should worry about is side effects - there is no rule in PHP that says a constructor can't have any side effects, and if it does, it can bite you badly. For example, you might construct an object, and the constructor happens to output stuff to the client, and then you try to redirect, but header() fails because you've already sent output.

As an even better solution, see if you can come up with a proper design. I can see two sane routes you could take here:

a) Wrap each of the static methods you want to call in a free function, and pass that (as of PHP 5.3, you can use anonymous functions for this, which, BTW, also provide a neat way of controlling variable scope beyond the normal two-level rules).

b) Wrap each of the static methods in a non-static method of a class that implements a common interface defining this method; return instances by interface, and call the interface method. This is essentially your basic factory pattern with behavior classes.

share|improve this answer
    
addendum to b) make the static methods non-static in the first place, then you don't need wrappers and the code will actually be object oriented. –  Michael Borgwardt Jun 16 '12 at 8:54
    
@MichaelBorgwardt: Good point. I assumed that the static methods were basically set in stone; if they aren't, then yes, making them non-static is the way to go. –  tdammers Jun 16 '12 at 9:59
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.