My question is more towards the design pattern to use for my implementation. I have the code written as follows -
X-Service.java
handler.setListeners(new HttpResponseHandler.conListers() {
#Override
public void success() {
}
});
HttpResponseHandler
protected conListers conListener;
public interface conListers {
public void success();
}
public void conListers(conListers listener) {
this.conListers = listener;
}
So now my problem is I can use this technique If I had just one type of success function. To be more clear I have multiple services where success method have different signature like --
public void success(String x);
public void success(HashMap y, Integer z);
I do not want to put all the methods in the interface, as I will have to implement them in all the services. I need a way in which I can just implement the success method I want.
You could define the interface using a generic type declaration:
public interface conListers<E> {
public void success(E value);
}
Alternatively, if you need a variable number of arguments of the same type then you can use:
public interface conListers<E> {
public void success(E... value);
}
If you need a fixed number of arguments then you can just test the length of the value argument in the definition of success() in the implementing class.
However, I can't think of any pattern you can use to allow success() to take a variably fixed number of different typed arguments unless you use Object but that then brings its own issues (like having to type check all the arguments within the implementing class):
public interface conListers {
public void success(Object... value);
}
You can use the command pattern in this scenario, basically the conListener will be your command. You'll have as many conListeners implementations as your services.
Example:
public class conListenersA implements conListener{
protected Service serviceA;
public void success(){
serviceA.success(arg1);//the method has arguments
}
}
public class conListenersB implements conListener{
protected Service serviceB;
public void success(){
serviceB.success(arg1,arg2);//the method has 2 arguments
}
}
The advantage is that whenever you need to execute a conListener you call will be "uniform", as simple as conListener.success()
You can try with most general Java class Object as a parameter and use varargs:
public interface conListers {
public void success(Object... arguments);
}
Inside implementation you'll have to figure out object types and the number of arguments, but you'll have a clean interface for your functions.
Another approach is to define a class that holds all of your arguments that you are planning to send on a success, and then inside implemented success methods get parameters that you really need.
Related
The problem is best explained with the following code:
public class TemplateClass {
public void templateOne() {
checkConditionA();
primitiveOp1();
checkConditionB();
}
public void templateTwo() {
checkConditionA();
primitiveOp2();
checkConditionB();
}
protected abstract void primitiveOp1();
protected abstract void primitiveOp2();
// rest of the methods
}
Now I have code duplication with templateOne() and templateTwo(), but I would like to have just one template method but with interchangeable primitive operations.
What you want is, in essence, a guard block around a method call. DRY programming is good practice, but be advice that you do not wawnt to couple what should not be coupled. I would only couple those two methods if it is guaranteed that they must always be guarded by the same pre- and postcondition(s).
If this is the case, I would recommend to implement a method private void callWithChecks(Runnable primitiveOperation) and then pass the respective primitive operation as parameter to this method:
public abstract class TemplateClass {
public void templateOne() {
callWithChecks(this::primitiveOp1);
}
public void templateTwo() {
callWithChecks(this::primitiveOp2);
}
private void callWithCkecks(Runnable primitiveOperation) {
checkConditionA();
primitiveOperation.run();
checkConditionB();
}
protected abstract void primitiveOp1();
protected abstract void primitiveOp2();
// rest of the methods
}
If you do not want to use the function interface Runnable, you can of course define your own interface. I went with it, since it is a Java base class.
Two remarks on your code:
TempalteClass must be declared abstract, otherwise the code will not compile
If you intend to implement methods checkConditionA() and checkConditionB() within TemplateClass, I would recommend defining them as private or final such that they cannot be overridden.
I have several methods in a class that require a boolean to be set to true in order to execute correctly.
I could write the if statement in each method, but it is not convenient if I or someone else wants to ad another method. I or he could forget about the check.
Is there a way in java to execute a method before each other methods (exactly like JUnit does with #BeforeEach ) in a class ?
Edit: Lots of very interesting techniques/answers/concepts proposed. I'll be in touch when I've understood them. Thanks.
Lets make a method turnBooleanTrue() where effectively the boolean is set to true in order for the method to be execute correctly.
Then, you can write up your very own InvocationHandler that would intercept calls to your objects, and then reflectively (using reflection API) invoke first the turnBooleanTrue() method followed by the method to which the call was made.
Will look something like this
public class MyClassInvocationHandler implements InvocationHandler {
// initiate an instance of the class
MyClass myClass = new MyClassImpl();
#Override
public Object invoke(Object proxy, Method method, Object[] args)
throws Throwable {
// look up turnBooleanTrue() method
Method turnBooleanTrue = myClass.getClass().getMethod("turnBooleanTrue");
// invoke the method
turnBooleanTrue.invoke(...); // toggle the boolean
// invoke the method to which the call was made
// pass in instance of class
Object returnObj = method.invoke(myClass, args);
return returnObj;
}
EDIT
Added some lines to have an object of MyClass initialized. You need something to invoke the method on and maintain the state. Changed util to myClass in the code example above.
Considering my use case, it was a bit overkill to use AOP or other concepts. So I basically did a check in each functions.
With AOP, this is how what you need would look:
// wraps around all methods in your class that have a boolean parameter
#Around(value = "#target(*..YourClass) && args(yourBool)", argNames = "jp,yourBool")
Object scheduleRequest(ProceedingJoinPoint jp, boolean yourBool) {
if (yourBool) {
jp.proceed(yourBool);
} else {
throw new RuntimeException("cannot execute this method!");
}
}
This would handle the case that the method take the boolean you say needs evaluation as its (only) parameter. If it comes from a different source, you may need to wire it into the aspect somehow, that depends on your overall design.
I suggest a simple solution by dividing your workflow in four components.
You have an interface you use to execute commands.
You have an interface that defines which commands you can use.
You have one wrapper that analyzes your boolean value.
You have an implementation of the work performing class, that implements the second interface.
Your wrapper initialize the worker.
Your wrapper exposes an action performing command that accepts the executing interface.
if the boolean is true, pass the worker to the executing interface work method.
the executing interfaces work method calls the work function on the command instance interface, the worker.
See it online: https://ideone.com/H6lQO8
class Ideone
{
public static void main (String[] args) throws java.lang.Exception
{
WorkDistributer wd = new WorkDistributer();
wd.enable();
wd.performAction((w) -> {w.printHello();});
wd.disable();
wd.performAction((w) -> {w.printHello();});
wd.enable();
wd.performAction((w) -> {w.printAnswer();});
wd.disable();
wd.performAction((w) -> {w.printAnswer();});
}
}
class WorkDistributer
{
private boolean enabled = false;
private ActionPerformer worker;
public WorkDistributer() {
this.worker = new Worker();
}
public void enable() {
enabled = true;
}
public void disable() {
enabled = false;
}
public void performAction(ActionCommand command) {
if(this.enabled) {
command.run(this.worker);
}
}
}
class Worker implements ActionPerformer {
public void printHello() {
System.out.println("hello");
}
public void printAnswer() {
System.out.println(21 * 2);
}
}
interface ActionPerformer {
public void printHello();
public void printAnswer();
}
interface ActionCommand {
public void run(ActionPerformer worker);
}
I couldn't think of a good way to name this. Basically I'm have a program where I want to have a default "pattern" almost I guess of how something should function. But I wanted to allow the use to create their own implementation (This is like an API) of the class and use that as a parameter instead, with the functionality inside. Is this the most efficient way to do it? If you don't understand that bad description here is an example.
public class SimpleStyle extends AbstractStyle {
public void personalizedImplementation() {
// manipulate the program this way
}
}
Then in the method
public static void do(Class<? extends AbstractSyle> style) {
// Use reflection in herre to get the implementation and do it
}
Is there a better and more efficient way to do something like this
You should not use reflection for this task if you can avoid it. It is less readable and more error-prone than well designed interfaces.
The basic solution (I’m not sure whether you already considered it) is to simply pass instances of AbstractStyle to your method:
public static void doSomething(AbstractStyle style) {
style.personalizedImplementation();
}
public static void main(String[] args) {
do(new SimpleStyle());
}
If you cannot use this approach – this depends on the specific use case – you could define an additional interface that handles the creation of the AbstractStyle instance:
public interface StyleFactory {
AbstractStyle createStyle();
}
public class SimpleStyleFactory implements StyleFactory {
#Override
public SimpleStyle createStyle() {
return new SimpleStyle(/* ... */);
}
}
public static void doSomething(StyleFactory styleFactory) {
AbstractStyle style = styleFactory.createStyle();
style.personalizedImplementation();
}
public static void main(String[] args) {
do(new SimpleStyleFactory());
}
Note: do is a Java keyword, so it can’t be used as an identifier. I used doSomething instead.
I come from a Python background and in Python you can pass in the type of an object as a parameter. But in Java you cannot do this, any tips on how to get something like this working?
private void function(Type TypeGoesHere)
Stock s = new TypeGoesHere();
s.analyze();
}
Java does not support Python’s way of referencing functions and classes. To achieve this behaviour, you have to use two advanced techniques: generics and reflection. Explaining these concepts is beyond the scope of a SO answer. You should read a Java guide to learn about them.
Yet here is an example how this would look like, assuming that the given class has a no-argument constructor:
public <T extends Stock> void analyzeNewStock(Class<T> clazz) throws Exception {
Stock s = clazz.newInstance();
s.analyze();
}
Then call this function with analyzeNewStock(MyStock.class).
As this is a rather complicated and error-prone approach, you’d rather define an interface that creates Stock instances:
public interface StockProvider {
Stock createStock(String value);
}
public class MyStockProvider implements StockProvider {
private final String valueTwo;
public MyStockProvider(String valueTwo) {
this.valueTwo = valueTwo;
}
#Override
public Stock createStock(String valueOne) {
return new MyStock(valueOne, valueTwo);
}
}
public class MyOtherClass {
public void analyzeNewStock(StockProvider provider) {
provider.createStock("Hi!").analyze();
}
public static void main(String[] args) {
analyzeNewStock(new MyStockProvider("Hey!"));
}
}
In Java you can pass a Class. You can do it like this:
private void function(Class c)
This is not very common procatice though. You can probably get wha you need by looking into Strategy pattern, or proper use of Object Oriented Programming (polymorphism).
If you are looking for a way to build some objects, look into Factory pattern.
If you want to create a generic class- look into this detailed answer: https://stackoverflow.com/a/1090488/1611957
You could use generics. For example:
private <T> void function(Class<T> clazz) {
try{
T t = clazz.newInstance();
//more code here
}catch(InstantiationException | IllegalAccessException ex){
ex.printStackTrace();
}
}
The Class<T> clazz shows what type to instantiate. The try/catch is just to prevent errors from stopping your code. The same idea is expanded in this SO post. More info here.
However, I'm not really sure why you would want to do this. There should easily be a workaround using a simple interface. Since you already know that you want an object with type Stock, you could pass an implementation of the interface. For example:
//interface to implement
public interface Stock {
public void analyze();
}
//rewrite of function
private void function(Stock s){
s.analyze();
}
And using two ways to call function:
//first way
public class XYZ implements Stock{
public void analyze(){
//some code here
}
}
//calling the function
function(new XYZ());
//second way
function(new Stock(){
public void analyze(){
//your code here
}
});
I have FinanceRequests and CommisionTransactions in my domain.
If I have a list of FinanceRequests each FinanceRequest could contain multiple CommisionTransactions that need to be clawed back. Dont worry how exactly that is done.
The class below (very bottom) makes me feel all fuzzy and warm since its succint and reuses existing code nicely. One problem Type erasure.
public void clawBack(Collection<FinanceRequest> financeRequestList)
public void clawBack(Collection<CommissionTrns> commissionTrnsList)
They both have the same signature after erasure, ie:
Collection<FinanceRequest> --> Collection<Object>
Collection<CommissionTrns> --> Collection<Object>
So eclipse complainst that:
Method clawBack(Collection) has the same erasure clawBack(Collection) as another method in type CommissionFacade
Any suggestions to restructure this so that it still an elegant solution that makes good code reuse?
public class CommissionFacade
{
/********FINANCE REQUESTS****************/
public void clawBack(FinanceRequest financeRequest)
{
Collection<CommissionTrns> commTrnsList = financeRequest.getCommissionTrnsList();
this.clawBack(commTrnsList);
}
public void clawBack(Collection<FinanceRequest> financeRequestList)
{
for(FinanceRequest finReq : financeRequestList)
{
this.clawBack(finReq);
}
}
/********COMMISSION TRANSACTIOS****************/
public void clawBack(CommissionTrns commissionTrns)
{
//Do clawback for single CommissionTrns
}
public void clawBack(Collection<CommissionTrns> commissionTrnsList)
{
for(CommissionTrns commTrn : commissionTrnsList)
{
this.clawBack(commTrn);
}
}
}
Either rename the methods, or use polymorphism: use an interface, and then either put the clawback code in the objects themselves, or use double-dispatch (depending on your design paradigm and taste).
With code in objects that would be:
public interface Clawbackable{
void clawBack()
}
public class CommissionFacade
{
public <T extends Clawbackable> void clawBack(Collection<T> objects)
{
for(T object: objects)
{
object.clawBack();
}
}
}
public class CommissionTrns implements Clawbackable {
public void clawback(){
// do clawback for commissions
}
}
public class FinanceRequest implements Clawbackable {
public void clawBack(){
// do clwaback for FinanceRequest
}
}
I prefer this approach, since I'm of the belief your domain should contain your logic; but I'm not fully aware of your exact wishes, so I'll leave it up to you.
With a double dispatch, you would pass the "ClawbackHandler" to the clawback method, and on the handler call the appropriate method depending on the type.
I think your best option is to simply name the method differently.
public void clawBackFinReqs(Collection<FinanceRequest> financeRequestList) {
}
public void clawBackComTrans(Collection<CommissionTrns> commissionTrnsList) {
}
In fact, it's not too bad, since you don't get anything extra out of having the same name on them.
Keep in mind, that the JVM will not decide which method to call at runtime. As opposed to virtual methods / method overriding resolution of overloaded methods are done at compile time. The Java Tutorials on method overloading even points out that "Overloaded methods should be used sparingly...".
Here is a trick with overloading by the second varargs parameter for the CommissionFacade class from the question:
public class CommissionFacade {
public void clawBack(Collection<FinanceRequest> financeRequestList, FinanceRequestType ...ignore) {
// code
}
public void clawBack(Collection<CommissionTrns> commissionTrnsList, CommissionTrnsType ...ignore) {
// code
}
/*******TYPES TO TRICK TYPE ERASURE*******/
private static class FinanceRequestType {}
private static class CommissionTrnsType {}
}
The code snippet to fast-check this trick works:
import java.util.ArrayList;
class HelloType {
public static void main(String[] args) {
method(new ArrayList<Integer>());
method(new ArrayList<Double>());
}
static void method(ArrayList<Integer> ints, IntegerType ...ignore) {
System.out.println("Hello, Integer!");
}
static void method(ArrayList<Double> dbs, DoubleType ...ignore) {
System.out.println("Hello, Double!");
}
static class IntegerType {}
static class DoubleType {}
}