In OOP, is it better to use class attributes within class functions, or just pass parameters to them.
class User{
private $user = array();
public function Get_Existing_User($user_id){
//SQL selects user info for existing user
$this->user = mysqli_fetch_assoc();
}
public function Set_User($user_data){
$this->user = (array) $user_data;
}
public function Add_User(){
//insert everything from $this->user into database
}
public function Get_User(){
return $this->user;
}
}
VS
class User{
public function Get_Existing_User($user_id){
//SQL selects user info for existing user
$user = mysqli_fetch_assoc();
return $user;
}
public function Add_User($user_data){
//insert everything from $user_data into database
}
}
Whats the better way to go?
Between your solutions, first is better, but you have to change the names of the functions. 'get' should be used only if function returns something.
The reason it is better is that it doesn't use side effects, side effects always bad as they are invisible to user of the class but change class behavior. So you should try to minimize them or make them obvious as they are in the first case, when they not really 'side'.
But in this particular case, Get_Existing_User and Add_User should be static functions, that return new User object, it is sometimes called as static constructor. The reason why it is much better is that it makes it clear what that functions do, they get something as parameter (user_id of existing user or first_name, last_name and other attributes for a new user) and create an object that represents the user. All database manipulation will be hidden away. Object itself should have properties for name and other attributes and even Save() method to push the changes back. But main idea is that you always work with constructed object, object that already have context and linked to something in the real world (that is, user in the database), not an empty shell that will be filled in as you go.
Some clarification on terminology first:
What you call class functions are more properly called methods. A method is a function on an object instance. Additionally, classes may have methods. These are called class methods or static methods. When you use the term class function, you are thus confusing the meaning.
That settled, there is no worse or better of the two approaches. You would use both, depending on the context. Parameters have a smaller scope, and thus cause less coupling. If everything else is the same, I would therefore say that parameters are preferable to setting an object property.
That said, there are usually other factors that can determine which to pick. You can think of an object as a scope for related variables. If a variable belongs to that scope, it would make sense to assign it to a property.
Class attributes are expected to describe the state of an instance of the class known as an object. As such, the attributes can be used by any function of the class to modify it's state. Function parameters on the other hand may have nothing to do with the current state of the object but can be used to modify it's state.
For example: a user object could be expected to have a user name attribute, a password attribute, and an authenticated attribute. this user object also has a function called authenticate that takes a parameter which describes an authentication method. The parameter is used to modify the state of the user object but would not be held as an attribute of it.
That entirely depends on wether you're going to re-use the data and how you're using the Class.
If you create many individual instances of the Class and each Object represents a unique user, it makes sense to persist the data in a member variable. If you're using the Class as a DAO (data access object) with a lot of one-off operations, it probably doesn't make a lot of sense to persist the data. But even in a DAO, depending on its inner workings, it might make sense to store the data at least temporarily in a member variable if there are many functions involved in a single call (like beforeQuery and afterQuery callbacks or the like).
There's no one-better-way-fits-it-all.
It is important that you choose the method that best suits your situation. Ignoring that not-so-helpful suggestion I encourage you to take a good look at some important principles in Object Oriented Design
Coupling
Cohesion
A strong understanding of these topics will help you assess your situation and code to suit the goals of the project. As your project grows, you'll likely find that you'll want to use methods that have optional parameters to interact with your objects to achieve high cohesion and loose coupling. Then you'll use methods and parameters like an expert.
Related
Concise: How I can avoid using static methods in a model?
Loquacious: Suppose I have a user class. Having userID I can get user name by (new user($userID))->getUserName(). Fine, what if I want to lookup a user? (new user())->lookup($uname, $pass). Still fine, but the latter case could be done via a simple static method user::lookup($uname, $pass)!
Some thoughts:
It's OK! Use (new object())->method() whenever you want. So should I create a hollow object to call a function?
Move this function out of your model. If it needs a DB lookup, where is better than Model context?
Define it as a static method. So isn't it lame to have a mixture of public and static methods in a class?
Side note: I've searched this question, no avail!
Move this function out of your model. If it needs a DB lookup, where is better than Model context?
Yes, indeed, this is the best way to solve the problem.
Currently your User class violates single responsibility principle which basically, says "one task - one class".
Right now your User describes user entity/state and handles persistence (in your case - retrieval from database). See, two things.
I suggest you create another class that is going to handle persistence tasks, like add/update/delete user. The simplest solution is to create a primitive repostitory, like this:
<?php
class UserRepository
{
public function addUser(User $user);
public function updateUser(User $user);
public function deleteUser(User $user);
public function getUserById($id);
}
Then retrieval of user can be done in the following manner:
// get an instance of this repository class
$userRepository = new UserRepository;
// ask it to find and return user from the database by ID
$user = $userRepository->getUserById($_GET['id']);
Easy to read, easy to handle, right?
This UserRepository class is actually a primitive implementation of Repository Pattern. UserRepository emulates an in-memory collection of all of your users, hiding implementation inside. It hides actual persistence mechanism from you as user: imagine, your coleague would write this class and you're just using its methods, like UserRepository::getById(1) - you don't even know/care if it grabs data from files/db/API. That's neat. )
This particular implementation is described very clearly in Kristopher Wilson's book "The Clean Architecture in PHP", which I highly recommed for you to read: it will take you two-three evenings, and push you to the next level.
You can extend the list of methods, of course, add lookups, etc.
class UserRepository
{
public function getByCompany(Company $company);
public function getByEmail($email);
public function countTotal();
}
In fact, every time you need to grab/add/update user in the database, you should do it via this repository.
I would like to emphasize that this is a simple implementation of the pattern, particularly, if you compare it to what Martin Fowler describes as Repository. However, in most cases it's totally fine.
It's OK! Use (new object())->method() whenever you want. So should I create a hollow object to call a function?
depends on how much creating an instance will cost
Move this function out of your model
Factory Pattern comes in mind here.
notes here:
What happens when $userID in the first call do not exists?
Isnt your lookup() method not creating 2 instances at one call, first for lookup, second the found one that is returned?
A FactoryPattern for example can have findByID() or findByName() and return an UserObject. And all that should not depend on this syntax at all: (new object())->method(), that is nice, but not always best practise.
A user fills in the form and submits it. Based on the input, an object Organization is hydrated. I want to separate communication with database from the actual object.
I thought of creating an OrganizationMapper that holds the methods for database communication (save, delete...). The organization class would get the OrganizationMapper through the constructor.
With these class definitions, however, I can't instantiate the classes because of their mutual dependence.
How else could I separate the database communication from Organization and put it into OrganizationMapper?
class Organization
{
protected $id;
protected $name;
... other properties ...
public function __construct(OrganizationMapper $mapper)
{
$this->mapper = $mapper;
}
public function getId() {...}
public function setId($id) {...}
... other methods ...
public function saveToDb()
{
$this->mapper->save($this);
}
The OrganizationMapper is
class OrganizationMapper
{
public function __construct(Organization $organization)
{
$this->organization = $organization
}
... other methods
public function save($organization)
{... the code to use the methods of Organization class to save the data to the database...}
}
And that's why circular dependencies are usually considered a bad thing.
Kidding aside, it seems to me that you do not actually need the constructor dependency in the OrganizationMapper class. From the looks of it, you're passing the Organization instance that you want to persist as a parameter into the mapper's save() method anyway and shouldn't need the instance attribute $this->organization in that class at all.
In general, I'd try to keep the OrganizationMapper stateless. Try to avoid storing an Organization instance as an instance attribute (especially if you actually use that same mapper instance for persisting multiple Organizations). Just do as you already did with the save() method and pass the Organization object as a method parameter.
Also, I would not associate the Organization class with the mapper. One could argue that this violates the Single Responsibility Principle as it's not the class' responsibility to persist itself. You could move this logic to the calling code and have the Organization class not know about the mapper at all (which is nice, because you completely eliminate the circular dependency between the two classes):
class Organization
{
protected $id;
protected $name;
// <other properties here>
// <getters and setters here>
}
class OrganizationMapper
{
public function save(Organization $organization)
{
// save $organization to DB, somehow
}
}
$organization = new Organization();
$organization->setName('Foobar International Inc.');
$mapper = new OrganizationMapper();
$mapper->save($organization);
To find a better way of seperating these two concerns, think about the purposes of your two objects:
an Organization is there to give you access to all informations of an organization
your OrganizationMapper is there to save a Organization object to database.
When you think about it like this, then there's a couple of questions, that rise up:
Why does your Organization need a saveToDb() method? It's not it's job to save it?
An instance of OrganizationMapper should be able to save any Organization in the database, so why do you pass it in twice? (once in the constructor, and once in the save($organization) method). In that case - what happens, if you pass a different organization to the constructor than to the save method?
In your current example, how would you load an Organization from Database?
As alternative, I would suggest to remove saveToDb() from Organization entirely, as it's not the job of the org to save itself to database. Additionally, I would remove the current Constructor from OrganizationMapper. In it's current design, there's little reason to pass the Organization to the constructor.
Also, I would rename the OrganizationMapper to OrganizationRepository or OrganizationService. The primary purpose of that class is not to map SQL to Objects but to retrieve/save Organizations from/to DB. (Also, in OOP, classes should only follow the single responsibility pattern, so maybe the part mapping between SQL and Objects should happen in specializied class)
As a side note: generally, it's not a great idea, to give many ways to do exactly the same thing (e.g. saving an organization). This will probably just cause inconsistencies over time (consider that you will be adding some validation logic in the future, but might forget to also add it in the second place).
I hope this helps you :)
Disclaimer: I name your Organization type as OrganizationEntity in this post.
Pretty simply, it's the other way around.
The OrganisationMapper gets an OrganisationEntity object and persists it to wherever you want to, by means you can choose.
For your problem:
move the saveToDb() method from your OrganisationEntity to the OrganisationMapper and pass it an object to be saved.
I don't know why Mapper should do any opperations on DB? Mapper sounds like converting Entity (Organization) into something that can be an input for DB operation ie. Query Object.
You should rename your class into DAO or Repository. It would be better name.
IMHO, the best idea would be to have:
Organization as an object that holds domain logic
OrganizationMapper should convert your domain object into some kind of query object
OrganizationDao should take Organization as an input param and use OrganizationMapper to convert it and do operation on DB.
BTW, why you are not using some kind of an ORM like Doctrine for example? It would make your life easier :)
You can't do that in php. Imagine if it would be posibble. Then instance of Organization would have a property OrganizationMapper, which would have a property Organization. So, property of a property of an instance of the class would be the instance itself! It is only possible in languages with pointers like c++. So, I see only 2 solutions here:
Put the classes together
Have a single link (maybe have 1 class that calls another while second doesn't call first.)
I have some pattern that works great for me, but that I have some difficulty explaining to fellow programmers. I am looking for some justification or literature reference.
I personally work with PHP, but this would also be applicable to Java, Javascript, C++, and similar languages. Examples will be in PHP or Pseudocode, I hope you can live with this.
The idea is to use a lazy evaluation container for intermediate results, to avoid multiple computation of the same intermediate value.
"Dynamic programming":
http://en.wikipedia.org/wiki/Dynamic_programming
The dynamic programming approach seeks to solve each subproblem only once, thus reducing the number of computations: once the solution to a given subproblem has been computed, it is stored or "memo-ized": the next time the same solution is needed, it is simply looked up
Lazy evaluation container:
class LazyEvaluationContainer {
protected $values = array();
function get($key) {
if (isset($this->values[$key])) {
return $this->values[$key];
}
if (method_exists($this, $key)) {
return $this->values[$key] = $this->$key();
}
throw new Exception("Key $key not supported.");
}
protected function foo() {
// Make sure that bar() runs only once.
return $this->get('bar') + $this->get('bar');
}
protected function bar() {
.. // expensive computation.
}
}
Similar containers are used e.g. as dependency injection containers (DIC).
Details
I usually use some variation of this.
It is possible to have the actual data methods in a different object than the data computation methods?
It is possible to have computation methods with parameters, using a cache with a nested array?
In PHP it is possible to use magic methods (__get() or __call()) for the main retrieval method. In combination with "#property" in the class docblock, this allows type hints for each "virtual" property.
I often use method names like "get_someValue()", where "someValue" is the actual key, to distinguish from regular methods.
It is possible to distribute the data computation to more than one object, to get some kind of separation of concerns?
It is possible to pre-initialize some values?
EDIT: Questions
There is already a nice answer talking about a cute mechanic in Spring #Configuration classes.
To make this more useful and interesting, I extend/clarify the question a bit:
Is storing intermediate values from dynamic programming a legitimate use case for this?
What are the best practices to implement this in PHP? Is some of the stuff in "Details" bad and ugly?
If I understand you correctly, this is quite a standard procedure, although, as you rightly admit, associated with DI (or bootstrapping applications).
A concrete, canonical example would be any Spring #Configuration class with lazy bean definitions; I think it displays exactly the same behavior as you describe, although the actual code that accomplishes it is hidden from view (and generated behind the scenes). Actual Java code could be like this:
#Configuration
public class Whatever {
#Bean #Lazy
public OneThing createOneThing() {
return new OneThing();
}
#Bean #Lazy
public SomeOtherThing createSomeOtherThing() {
return new SomeOtherThing();
}
// here the magic begins:
#Bean #Lazy
public SomeThirdThing getSomeThirdThing() {
return new SomeThirdThing(this.createOneThing(), this.createOneThing(), this.createOneThing(), createSomeOtherThing());
}
}
Each method marked with #Bean #Lazy represents one "resource" that will be created once it is needed (and the method is called) and - no matter how many times it seems that the method is called - the object will only be created once (due to some magic that changes the actual code during loading). So even though it seems that in createOneThing() is called two times in createOneThing(), only one call will occur (and that's only after someone tries to call createSomeThirdThing() or calls getBean(SomeThirdThing.class) on ApplicationContext).
I think you cannot have a universal lazy evaluation container for everything.
Let's first discuss what you really have there. I don't think it's lazy evaluation. Lazy evaluation is defined as delaying an evaluation to the point where the value is really needed, and sharing an already evaluated value with further requests for that value.
The typical example that comes to my mind is a database connection. You'd prepare everything to be able to use that connection when it is needed, but only when there really is a database query needed, the connection is created, and then shared with subsequent queries.
The typical implementation would be to pass the connection string to the constructor, store it internally, and when there is a call to the query method, first the method to return the connection handle is called, which will create and save that handle with the connection string if it does not exist. Later calls to that object will reuse the existing connection.
Such a database object would qualify for lazy evaluating the database connection: It is only created when really needed, and it is then shared for every other query.
When I look at your implementation, it would not qualify for "evaluate only if really needed", it will only store the value that was once created. So it really is only some sort of cache.
It also does not really solve the problem of universally only evaluating the expensive computation once globally. If you have two instances, you will run the expensive function twice. But on the other hand, NOT evaluating it twice will introduce global state - which should be considered a bad thing unless explicitly declared. Usually it would make code very hard to test properly. Personally I'd avoid that.
It is possible to have the actual data methods in a different object than the data computation methods?
If you have a look at how the Zend Framework offers the cache pattern (\Zend\Cache\Pattern\{Callback,Class,Object}Cache), you'd see that the real working class is getting a decorator wrapped around it. All the internal stuff of getting the values stored and read them back is handled internally, from the outside you'd call your methods just like before.
The downside is that you do not have an object of the type of the original class. So if you use type hinting, you cannot pass a decorated caching object instead of the original object. The solution is to implement an interface. The original class implements it with the real functions, and then you create another class that extends the cache decorator and implements the interface as well. This object will pass the type hinting checks, but you are forced to manually implement all interface methods, which do nothing more than pass the call to the internal magic function that would otherwise intercept them.
interface Foo
{
public function foo();
}
class FooExpensive implements Foo
{
public function foo()
{
sleep(100);
return "bar";
}
}
class FooCached extends \Zend\Cache\Pattern\ObjectPattern implements Foo
{
public function foo()
{
//internally uses instance of FooExpensive to calculate once
$args = func_get_args();
return $this->call(__FUNCTION__, $args);
}
}
I have found it impossible in PHP to implement a cache without at least these two classes and one interface (but on the other hand, implementing against an interface is a good thing, it shouldn't bother you). You cannot simply use the native cache object directly.
It is possible to have computation methods with parameters, using a cache with a nested array?
Parameters are working in the above implementation, and they are used in the internal generation of a cache key. You should probably have a look at the \Zend\Cache\Pattern\CallbackCache::generateCallbackKey method.
In PHP it is possible to use magic methods (__get() or __call()) for the main retrieval method. In combination with "#property" in the class docblock, this allows type hints for each "virtual" property.
Magic methods are evil. A documentation block should be considered outdated, as it is no real working code. While I found it acceptable to use magic getter and setter in a really easy-to-understand value object code, which would allow to store any value in any property just like stdClass, I do recommend to be very careful with __call.
I often use method names like "get_someValue()", where "someValue" is the actual key, to distinguish from regular methods.
I would consider this a violation of PSR-1: "4.3. Methods: Method names MUST be declared in camelCase()." And is there a reason to mark these methods as something special? Are they special at all? The do return the value, don't they?
It is possible to distribute the data computation to more than one object, to get some kind of separation of concerns?
If you cache a complex construction of objects, this is completely possible.
It is possible to pre-initialize some values?
This should not be the concern of a cache, but of the implementation itself. What is the point in NOT executing an expensive computation, but to return a preset value? If that is a real use case (like instantly return NULL if a parameter is outside of the defined range), it must be part of the implementation itself. You should not rely on an additional layer around the object to return a value in such cases.
Is storing intermediate values from dynamic programming a legitimate use case for this?
Do you have a dynamic programming problem? There is this sentence on the Wikipedia page you linked:
There are two key attributes that a problem must have in order for dynamic programming to be applicable: optimal substructure and overlapping subproblems. If a problem can be solved by combining optimal solutions to non-overlapping subproblems, the strategy is called "divide and conquer" instead.
I think that there are already existing patterns that seem to solve the lazy evaluation part of your example: Singleton, ServiceLocator, Factory. (I'm not promoting singletons here!)
There also is the concept of "promises": Objects are returned that promise to return the real value later if asked, but as long as the value isn't needed right now, would act as the values replacement that could be passed along instead. You might want to read this blog posting: http://blog.ircmaxell.com/2013/01/promise-for-clean-code.html
What are the best practices to implement this in PHP? Is some of the stuff in "Details" bad and ugly?
You used an example that probably comes close to the Fibonacci example. The aspect I don't like about that example is that you use a single instance to collect all values. In a way, you are aggregating global state here - which probably is what this whole concept is about. But global state is evil, and I don't like that extra layer. And you haven't really solved the problem of parameters enough.
I wonder why there are really two calls to bar() inside foo()? The more obvious method would be to duplicate the result directly in foo(), and then "add" it.
All in all, I'm not too impressed until now. I cannot anticipate a real use case for such a general purpose solution on this simple level. I do like IDE auto suggest support, and I do not like duck-typing (passing an object that only simulates being compatible, but without being able to ensure the instance).
Let's say you have a object that is unique, and it's used by all other classes and functions ...something like $application.
How would you access this object in your functions?
using a global variable in each of you functions:
global $application;
$application->doStuff();
creating a function, like application() that instantiates the object into a static variable and returns it; then use this function everywhere you need to access the object:
application()->doStuff();
create a singleton thing, like a static method inside the object class which returns the only instance, and use this method to access the object:
Application::getInstance()->doStuff();
KingCrunch & skwee: Pass the application object as argument to each function/class where is needed
...
public function __construct(Application $app, ...){
....
If there are other options please post them. I'm wondering which of these options is the most efficient / considered "best practice".
I'd pass it to all the needed methods.
i.e.
function doFoo(Application $app) {
$app->doStuff();
}
Both global and singleton considered bad and ties your code too much and this makes unit testing more difficult.
There is one rule when you are allowed to use singleton, if you answer "yes" to the following statement:
Do I need to introduce global state to my application AND I must have a single instance of given object AND having more than one instance will cause error
If you answer yes to all the 3 parts then you can use singleton. In any other case just pass all the instances to all the method who needs them. If you have too much of them, consider using something like Context
class Context {
public $application;
public $logger;
....
}
========
$context = new Context();
$context->application = new Application();
$context->logger = new Logger(...);
doFoo($context);
========
function doFoo(Context $context) {
$context->application->doStuff();
$context->logger->logThings();
}
(you can use getters/setters if you need to protect the data or manipulate it or if you want to use lazy initiation etc).
Good luck!
Singletons, God Classes, monolithic classes, etc. are all anti patterns, so I would suggest a fourth option: dependency injection. You can create an instance of application in your application via a factory (or perhaps even new if it has no dependencies, but this can end up complicating things later).
Then, any class that needs access to application can get it as a member, helpfully via the constructor. I'm sure that not every class needs access to application. Remember the Law of Demeter.
If you need some generic functionality like converting one static string to another, I suggest using php's global functions (as opposed to, for instance, a faux static class). I believe they were designed for that purpose.
Or just give it to the ones, that are interested in it. All the suggestions you made are like global variables, even if you call it not that in 2 of 3 variants.
Before it comes to that: If you want to say "Thats not possible, because everything needs it", than maybe it does too much, can too much, and/or knows too much.
Had a discussion with a colleague about wether this is bad practice or not. Now I can not find immediate examples of this online.
We have a lot of database object mappers and call it's functions like so
(example) - the setId method get's the row from the database and set's it to predefined propertys
class Person {
public static function get($id) {
$object = new Person;
$object->setId($id);
return $object;
}
}
Using it like this we can use simple constructions like this: (where we got the id from for-example a post)
$person = Person::get($id);
instead of
$person = new Person;
$person->setId($id);
Now, my instinct tells me this is bad practice. But I can not explain it. Maybe someone here can explain why this is, or is not bad practice
Here are some other examples how we use it. we mainly use it for getters. (just the names, not the code. Almost all of them just run a query, which can return 1 object and then use the id of the result to use the setId method)
class CatalogArticle {
public static function get($id) { }
public static function getByArticlenumber($articlenumber) {} //$articlenumber is unique in the database
public static function getRandom() {} //Runs a query returning a random row
}
This isn't horrible persay. It's an implementation of a Factory Method design pattern. It's not bad at all in principle.
However, in your specific example, it's not really doing anything significant, so I'm not so sure if it's necessary. You could eliminate the need by taking a (perhaps optional) parameter to the constructor for the id. Then anyone could call $foo = new Person($id); rather than needing an explicit factory.
But if the instantiation is complex, or you want the ability to build several different people types that can only be determined by logic, a factory method may work better. For example, let's say you need to determine the type of person to instantiate by some parameter. Then, a factory method on Person would be appropriate. The method would determine what "type" to load, and then instantiate that class.
Statics in general are hard to test and don't allow for polymorphic changes like an instance would. They also create hard dependencies between classes in the code. They are not horrible, but you should really think about it if you want to use one. An option would be to use a Builder or a Abstract Factory. That way, you create an instance of the builder/factory, and then let that instance determine how to instantiate the resulting class...
One other note. I would rename that method from Person::get() to something a little more semantically appropriate. Perhaps Person::getInstance() or something else appropriate.
This blog post should tell you why people don't like static methods better than i could:
http://kore-nordmann.de/blog/0103_static_considered_harmful.html
The question that strikes me most about your current code snippet: Is a Person allowed to NOT have an Id ?
I feel like that should be an constructor argument if it's representing a real Person. If you use that class to create new persons that ofc might not work.
The difference between the 2 calls is minor. Both "create" a Person class and set the Id so you are not winning / loosing anything there when it comes to 'hard wired dependencies'.
The advantage only shows when you want to be able to pass a Person into another object and that objects needs to change the ID (as an example, the blog post should explain that better than i did here).
I'm only adding to edorian's post, but I've used static get methods in the past, where there is a caching engine in place, and (for example) I might have a given Person object in memcache, and would rather retrieve it from the cache than going off to the database.
For example:
class Person {
public static function get($id) {
if(Cache::contains("Person", $id))
{
return Cache::get("Person", $id);
}
else
{
//fictional get_person_from_database, basically
//getting an instance of Person from a database
$object = get_person_from_database($id);
}
return $object;
}
}
In this way, all cache handling is done by the class in question, rather than the caller getting a person calls having to worry about the cache.
long story short, yes, they are bad practice:
http://r.je/static-methods-bad-practice.html
http://misko.hevery.com/2008/12/15/static-methods-are-death-to-testability/
A good reason apart of everything is that you 'should' be testing your code. Static methods cause issues, so there you have a good reason:
if you want to follow good practices, test your code
Ergo, if static causes testing issues, static prevent writing tests so it prevents to follow good practices :-)
time goes things changes.
just in case you have problems with testing you can use AspectMock library
https://github.com/Codeception/AspectMock
any way static is not so bad at all. to use static you should just know what you are doing and why. if you will place static only as fast solution it is bad idea in 99% of variations. in 1% time it is still bad solution but it gives you time when you need it.