Java: When to use fields vs. arguments? - java

My current IVR app uses a wrapper class with several methods to call a web service and then parse its results. Each class has a single "invoke" method which calls the web service, and then calls subsequent submethods to break up the parsing into logical chunks.
Whenever a new input argument is needed in one or more of the submethods, the previous developer would add it as an argument on the invoke, and then add it as an argument on the submethods.
Is this the proper way to do this, or would it be better to set a field on the class, and then reference that whenever necessary?
Instead of:
invoke (oldField1, oldField2, newField1)
submethod1 (results, oldField1, oldField2, newField1)
submethod2 (results, oldField1, oldField2, newField1)
Should it be:
invoke(oldField1, oldField2, newField1){
OldField1=oldField1
OldField2=oldField2
NewField1=newField1
}
submethod1(results)
submethod2(results)
Or even:
new (oldField1, oldField2, newField1){
OldField1=oldField1
OldField2=oldField2
NewField1=newField1
}
invoke()
submethod1(results)
submethod2(results)
Thanks!

The first solution allows making the object stateless, and allows using a unique instance for all the invocations, even in parallel.
The third one allows making the object stateful but immutable. It could be used for several invocations using the same set of fields, even in parallel (if made immutable).
Both of these solutions are acceptable. The less state an object has, the easiest it is to use it, particularly in a multi-thread environment.
The less mutable an object is, the easiest it is to use it.
The second one makes it a stateful mutable object, which can't be used by several threads (without synchronization). It looks less clean than the other two to me.

My general rule is to avoid statefulness in a service-oriented class whenever possible. Although Java doesn't really support functional programming per-se, the simplest and most scalable implementation is your first approach, which uses no member variables.
If your goal is to avoid frequent changes to method signatures, you could try to use a more generic field encapsulation:
public class Invoker {
public static void invoke(ResultContainer result, List<String> parameters) {
submethod1(result, parameters);
submethod2(result, parameters);
}
}
I would also recommend that you take a look at the Decorator design pattern for more ideas.

It depends on if your argument is data or identifying a mode/switch.
I suggest one argument for the data structure type and another argument that contains the enum types of different operations.
And then based on your enum type or mode of operation you can choose a strategy on which class to execute.
To restrict this increasing argument approach, you could provide an interface. And force the implementation to adhere to that.

Related

Find a Decorator of a particular type when using the Decorator Pattern?

I'm building an app that needs to use multiple types of similar sensors. Since the sensors could also have different behaviours, or combinations of behaviours, I decided to use the decorator pattern.
In short, I have a hierarchy that looks like this:
So any of the concrete ISensorDecorator classes can decorate (wrap) any of the concrete IMeasureSensor classes, but since a concrete ISensorDecorator also is a concrete IMeasureSensor, they can wrap each other. So for example
IMeasureSensor sensor = new FilteredSensorDecorator(
new CalibratedSensorDecorator(
new AccelerometerSensor()
)
);
is a valid statement that declares a filtered and calibrated accelerometer sensor.
Now let's say I have a method called setCalibration() in CalibratedSensorDecorator. Obviously I can't call
sensor.setCalibration();
because IMeasureSensor doesn't have a setCalibration() method. And trying to use
((CalibratedSensorDecorator)sensor).setCalibration()
won't work either, since sensor is a FilteredSensorDecorator.
How can I get to the CalibratedSensorDecorator in this particular case, and more generally to any specific decorator in any "chain" of decorators? I don't want to store them as separate variables, I want to do it dynamically.
Since its a design question, there won't be any right answer, you need to make choice which could be good or not that good.
You shouldn't add a method for particular class since it will violate the Liskov substitution principle
Objects in a program should be replaceable with instances of their subtypes without altering the correctness of that program.
You can initialize the calibration in constructor CalibratedSensorDecorator and use it while executing your required function.
If that doesn't meet your requirement, then may be CalibratedSensorDecorator doesn't belong in your sensor hierarchy. Consider separating it and use Strategy pattern to decide which one to use.
Edit 1:
what I understand it doesn't say that you shouldn't add methods to subtypes?
Yes, you are right. It doesn't prohibit from adding methods but if the methods are changing the state of an Object, then it should be re-considered. All these patterns are just the guidelines which can be tweaked as per our needs.
To explain my rationale:
Imagine you have create the setCalibration() on CalibratedSensorDecorator. You have following way to expose CalibratedSensorDecorator to either internal developer or to external developer. You have created a Factory which just returns IMeasureSensor as follows:
public IMeasureSensor getCalibratedSensor(){
...
}
Now the user of your API simply gets this and is happy that his/her current code is working. But realizes that he/she missed to setCalibration() which was found after hours of debugging. Moreover he/she has to write the type checking and type casting code to make use of this feature, which might not be great for clean code.
You should try to keep your classes as immutable as possible so that the debugging and maintenance are at ease. There is no harm in recreating the object since the older will be garbage collected.
Again its just my suggestion, its your decision to carefully consider what's best for your use-case. You can still go ahead with your new approach to create the method if its mandatory and ensure proper documentation has been made to make user understand the usage.
While the answer by Sagar discusses some (valid) reasons for considering using another approach than the decorator pattern, I came up with a working solution for the actual problem of finding the correct decorator.
/**
* Walks the decorator hierarchy recursively from the outside in (excluding the final
* IMeasureSensor which is not a ISensorDecorator), and returns the decorator of the given class.
* If none can be found, null is returned.
*/
IMeasureSensor findDecorator(IMeasureSensor sensor, Class decoratorClass){
if( ISensorDecorator.class.isAssignableFrom(sensor.getClass()) ){
return (sensor.getClass() == decoratorClass)
? sensor
: findDecorator(((ISensorDecorator) sensor).getDecoratee(), decoratorClass);
}
else
return null;
}
The method ISensorDecorator.getDecoratee() simply returns the "decoratee", i.e. the IMeasureSensor that the decorator decorates.
public IMeasureSensor getDecoratee(){
return mMeasureSensor;
}
You can then use findDecorator() to find a (the outermost) decorator of a given type like this:
IMeasureSensor sensor;
...
CalibratedSensorDecorator s = (CalibratedSensorDecorator) findDecorator(sensor, CalibratedSensorDecorator.class);

Specialized methods vs. using an Enum as additional parameter

Java design question.
I have an object that needs to maintain sets of say 4 types of widgets: active, inactive, invalid, potential. For each of these types, I have a series of methods that acts on each: say add, get, remove, etc.
My question is, would it be better to have a series of methods like this:
addInactive(Widget)
getInactive()
removeInactive(Widget)
addActive(Widget)
getInactive()
removeInactive(Widget)
addInvalid(Widget)
etc...
OR
Should I have an enum inside this class instead: WidgetStatus and then the consumer would pass in this enum when they need to perform an action. This would result in only 3 public methods instead:
add(Widget, WidgetStatus)
get(WidgetStatus)
remove(Widget, WidgetStatus)
On one hand, I like the first using specialized methods because it not only keeps down the number of parameters needed, but it also forces the consumer's hand to explicitly call the method they need. However, the latter option seems to keep the API simple and makes adding additional status types in the future a bit easier.
Thoughts?
With the enum you get a cleaner API and much easier maintenance if you want to change the states; there really is no good reason for the first approach.
WidgetStatus is attribute of widget, not a container. May be follow will be good for you
Widget.setActive(false);
add(Widget);
I would turn the enum or whatever into some Strategy Pattern that includes the behavior you mention above. Then your add/get/remove methods will simply delegate to the strategy to perform the action.
http://en.wikipedia.org/wiki/Strategy_pattern

No-Parameter Constructor v/s Constructor with params

which one of below is better or to be prefered
new Object();
Object.setValue1("1");
Object.setValue2("2");
Object.setValue3("3");
or
new Object("1","2","3");
(I assume you're talking about the design of your own classes, rather than how to use other already-designed classes.)
Neither is always "better," it depends on the nature of the object and (to an extent) on your preferred style.
If an object cannot have a meaningful state without some external information, then requiring that information in the constructor makes sense, because then you can't create instances with an invalid state.
However, having constructors that require as little information as possible is useful in terms of making the class easy to use in a variety of situations. If the class is such that a zero-arguments constructor is feasible and doesn't complicate the class, it's great in terms of supporting various use-cases, including cases where the instance is being built as part of parsing some other structure (JSON, XML, etc.).
There is also a third option that builds on the use of fluent interfaces
MyObject obj = new MyObject().setValue1("1").setValue("2").setValue("3");
I personally like this approach but if the number of parameters is short and known at the time of construction AND the varying possible combinations of parameters is short then I would take the route of parameters on the constructor. I think most would agree that 12 constructor overloads are an eye sore.
Depends on whether you know the values at the time of object construction.
If Yes, then use the constructor version if not then you will have to use the other version.
Ofcourse,Initialization through the Constructor version is faster because it involves just one function call over 3 set function calls and also it is more logical way.
Its always better performance to call in constructor If you know values already.
Then there is my preferred alternative. Thing is the name of some interface. It creates an anonymous class.
Thing createThing ( final int val1 , final int val2 , final int val3 )
{
return new Thing ( )
{
// can use val1, val2, val3
} ;
}
It all depends on the application.
Calling Parameterized constructor will be a good idea if at Compile time you know what values to be given to your variables, rather than calling Setters. Because you are calling 3 setter methods and in parameterized constructor, you are just passing to the cnostructor it self.
But if at compile time you don't know what values to be given then how can you call paramterized constructor.
But for initialization it will be better to call parameterized constructor.
There is a semantic difference. If (1) you are instantiating an object with an initial state. In (2) you are changing the state of an existing instance (3 times). It's a small difference but may become very important in more complex systems (especially if you rely on various JavaBean conventions). But still, neither one is wrong or better.

trying to use only one method name

When I was programming a Form Validator in PHP, when creating new methods, I needed to increase the number of arguments in old methods.
When I was learning Java, when I read that extends is to not touch previously tested, working code, I thought I shouldn't have increased the number of arguments in the old methods, but overridden the old methods with the new methods.
Imagine if you are to verify if a field is empty in one part of the form, in an other and in yet an other.
If the arguments are different, you'll overload isEmpty, but, if the arguments are equal, is it right to use isEmpty, isEmpty2, isEmpty3, three classes and one isEmpty per class or, if both are wrong, what should I have done?
So the question is:
If I need different behaviors for a method isEmpty which receives the same number arguments, what should I do?
Use different names? ( isEmpty, isEmpty2, isEmpty3 )
Have three classes with a single isEmpty method?
Other?
If that's the question then I think you should use:
When they belong to the same logical unit ( they are of the same sort of validation ) but don't use numbers as version, better is to name them after what they do: isEmptyUser, isEmptyAddress, isEmptyWhatever
When the validator object could be computed in one place and passed around during the program lifecycle. Let's say: Validator v = Validator.getInstance( ... ); and then use it as : validator.isEmpty() and let polymorphism to it's job.
Alternatively you could pack the arguments in one class and pass it to the isEmpty method, although you'll end up with pretty much the same problem of the name. Still it's easier to refactor from there and have the new class doing the validation for you.
isEmpty( new Arguments(a,b,c ) ); => arguments.isEmpty();
The Open/Closed Principle [usually attributed to Bertrand Meyer] says that "software entities (classes, modules, functions, etc.) should be open for extension, but closed for modification". This might be the principle that you came across in your Java days. In real life this applies to completed code where the cost of modification, re-testing and re-certification outweighs the benefit of the simplicity gained by making a direct change.
If you are changing a method because it needs an additional argument, you might choose to use the following steps:
Copy the old method.
Remove the implementation from the copy.
Change the signature of the original method to add the new argument.
Update the implementation of the original method to use the new argument.
Implement the copy in terms of the new method with a default value for the argument.
If your implementation language doesn't support method overloading then the principle is the same but you need to find a new name for the new method signature.
The advantage of this approach is that you have added the new argument to the method, and your existing client code will continue to compile and run.
This works well if there is an obvious default for the new argument, and less well if there isn't.
Since java 5 you can use variable list of arguments as in void foo(Object ... params)
You will need to come up with creative names for your methods since you can't overload methods that have same type and number of arguments (or based on return type). I actually personally prefer this to overloading anyway. So you can have isEmpty and isEmptyWhenFoo and isEmptyWhenIHaveTheseArguments (well meybe not the last one :)
Not sure if this actually answers your question, but the best way to think about OO in "real life" is to think of the Nygaard Classification:
ObjectOrientedProgramming. A program execution is regarded as a physical model, simulating the behavior of either a real or imaginary part of the world.
So how would you build a physical device to do what you are trying to do in code? You'd probably have some kind of "Form" object, and the form object would have little tabs or bits connected to it to represent the different Form variables, and then you would build a Validator object that would take the Form object in a slot and then flash one light if the form was valid and another if it was invalid. Or your Validator could take a Form object in one slot and return a Form object out (possibly the same one), but modified in various ways (that only the Validator understood) to make it "valid". Or maybe a Validator is part of a Form, and so the Form has this Validator thingy sticking out of it...
My point is, try to imagine what such a machine would look like and how it would work. Then think of all of the parts of that machine, and make each one an object. That's how "object-oriented" things work in "real life", right?
With that said, what is meant by "extending" a class? Well, a class is a "template" for objects -- each object instance is made by building it from a class. A subclass is simply a class that "inherits" from a parent class. In Java at least, there are two kinds of inheritance: interface inheritance and implementation inheritance. In Java, you are allowed to inherit implementation (actual method code) from at most one class at a time, but you can inherit many interfaces -- which are basically just collections of attributes that someone can see from outside your class.
Additionally, a common way of thinking about OO programming is to think about "messages" instead of "method calls" (in fact, this is the original term invented by Alan Kay for Smalltalk, which was the first language to actually be called "object-oriented"). So when you send an isEmpty message to the object, how do you want it to respond? Do you want to be able to send different arguments with the isEmpty message and have it respond differently? Or do you want to send the isEmpty message to different objects and have them respond differently? Either are appropriate answers, depending on the design of your code.
Instead having one class providing multiple versions of isEmpty with differing names, try breaking down your model into a finer grained pieces the could be put together in more flexible ways.
Create an interface called Empty with
one method isEmpty(String value);
Create implemntations of this
interface like EmptyIgnoreWhiteSpace
and EmptyIgnoreZero
Create FormField
class that have validation methods
which delegate to implementations of
Empty.
Your Form object will have
instances of FormField which will
know how to validate themselves.
Now you have a lot of flexibility, you can combine your Empty implemenation classes to make new classes like EmptyIgnoreWhiteSpaceAndZero. You can use them in other places that have nothing to do with form field validation.
You don't have have have multple similarly named methods polluting your object model.

Is there a rule of thumb for when to code a static method vs an instance method?

I'm learning Java (and OOP) and although it might irrelevant for where I'm at right now, I was wondering if SO could share some common pitfalls or good design practices.
One important thing to remember is that static methods cannot be overridden by a subclass. References to a static method in your code essentially tie it to that implementation. When using instance methods, behavior can be varied based on the type of the instance. You can take advantage of polymorphism. Static methods are more suited to utilitarian types of operations where the behavior is set in stone. Things like base 64 encoding or calculating a checksum for instance.
I don't think any of the answers get to the heart of the OO reason of when to choose one or the other. Sure, use an instance method when you need to deal with instance members, but you could make all of your members public and then code a static method that takes in an instance of the class as an argument. Hello C.
You need to think about the messages the object you are designing responds to. Those will always be your instance methods. If you think about your objects this way, you'll almost never have static methods. Static members are ok in certain circumstances.
Notable exceptions that come to mind are the Factory Method and Singleton (use sparingly) patterns. Exercise caution when you are tempted to write a "helper" class, for from there, it is a slippery slope into procedural programming.
If the implementation of a method can be expressed completely in terms of the public interface (without downcasting) of your class, then it may be a good candidate for a static "utility" method. This allows you to maintain a minimal interface while still providing the convenience methods that clients of the code may use a lot. As Scott Meyers explains, this approach encourages encapsulation by minimizing the amount of code impacted by a change to the internal implementation of a class. Here's another interesting article by Herb Sutter picking apart std::basic_string deciding what methods should be members and what shouldn't.
In a language like Java or C++, I'll admit that the static methods make the code less elegant so there's still a tradeoff. In C#, extension methods can give you the best of both worlds.
If the operation will need to be overridden by a sub-class for some reason, then of course it must be an instance method in which case you'll need to think about all the factors that go into designing a class for inheritance.
My rule of thumb is: if the method performs anything related to a specific instance of a class, regardless of whether it needs to use class instance variables. If you can consider a situation where you might need to use a certain method without necessarily referring to an instance of the class, then the method should definitely be static (class). If this method also happens to need to make use of instance variables in certain cases, then it is probably best to create a separate instance method that calls the static method and passes the instance variables. Performance-wise I believe there is negligible difference (at least in .NET, though I would imagine it would be very similar for Java).
If you keep state ( a value ) of an object and the method is used to access, or modify the state then you should use an instance method.
Even if the method does not alter the state ( an utility function ) I would recommend you to use an instance method. Mostly because this way you can have a subclass that perform a different action.
For the rest you could use an static method.
:)
This thread looks relevant: Method can be made static, but should it? The difference's between C# and Java won't impact its relevance (I think).
Your default choice should be an instance method.
If it uses an instance variable it must be an instance method.
If not, it's up to you, but if you find yourself with a lot of static methods and/or static non-final variables, you probably want to extract all the static stuff into a new class instance. (A bunch of static methods and members is a singleton, but a really annoying one, having a real singleton object would be better--a regular object that there happens to be one of, the best!).
Basically, the rule of thumb is if it uses any data specific to the object, instance. So Math.max is static but BigInteger.bitCount() is instance. It obviously gets more complicated as your domain model does, and there are border-line cases, but the general idea is simple.
I would use an instance method by default. The advantage is that behavior can be overridden in a subclass or if you are coding against interfaces, an alternative implementation of the collaborator can be used. This is really useful for flexibility in testing code.
Static references are baked into your implementation and can't change. I find static useful for short utility methods. If the contents of your static method are very large, you may want to think about breaking responsibility into one or more separate objects and letting those collaborate with the client code as object instances.
IMHO, if you can make it a static method (without having to change it structure) then make it a static method. It is faster, and simpler.
If you know you will want to override the method, I suggest you write a unit test where you actually do this and so it is no longer appropriate to make it static. If that sounds like too much hard work, then don't make it an instance method.
Generally, You shouldn't add functionality as soon as you imagine a use one day (that way madness lies), you should only add functionality you know you actually need.
For a longer explanation...
http://en.wikipedia.org/wiki/You_Ain%27t_Gonna_Need_It
http://c2.com/xp/YouArentGonnaNeedIt.html
the issue with static methods is that you are breaking one of the core Object Oriented principles as you are coupled to an implementation. You want to support the open close principle and have your class implement an interface that describes the dependency (in a behavioral abstract sense) and then have your classes depend on that innterface. Much easier to extend after that point going forward . ..
My static methods are always one of the following:
Private "helper" methods that evaluate a formula useful only to that class.
Factory methods (Foo.getInstance() etc.)
In a "utility" class that is final, has a private constructor and contains nothing other than public static methods (e.g. com.google.common.collect.Maps)
I will not make a method static just because it does not refer to any instance variables.

Categories

Resources