vendredi 7 juin 2019

How to implement a static extensible registry in java

I was trying to implement a static registry that can be extended by 3rd party developers adding their items to this registry, again, statically.

I am running into the problem described at Java: use static initializer blocks to register classes to global static registry - however, the suggestion described there to have a Registrar that registers each class does not fit my requirements since the 3rd party developers in my case only get my library in a jar and they can only extend it adding additional classes to it but not modify anything in my jar.

Any suggestions to achieve this, if possible at all? (should be, I am guessing)

here's what I have:

import java.util.HashMap;

public class Calculator {

    public double eval(String symbol, double operand1, double operand2) {
        return OperatorRegistry.get(symbol).calculate(operand1, operand2);
    }

    public static void main(String[] args) {
        Calculator c = new Calculator();
        System.out.println(c.eval("+", 3, 9));
        System.out.println(c.eval("-", 13, 9));
    }

}

class OperatorRegistry {
    static HashMap<String, Operator> registry = new HashMap<String, Operator>();
    public static void register(Operator o) {
        System.out.println("Registering: " + o.getSymbol());
        registry.put(o.getSymbol(), o);
    }

    public static Operator get(String c) {
        return registry.get(c);
    }

}

interface Operator {

    public  String getSymbol() ;
    public  double calculate(double a, double b) ;
}


class AddOperator implements Operator{
    static {
        OperatorRegistry.register(new AddOperator());
    }

    public  String getSymbol() {
        return "+";
    }
    public  double calculate(double a, double b) {
        return a + b;
    }
}



class SubtractOperator implements Operator {
    static {
        OperatorRegistry.register(new SubtractOperator());
    }

    public  String getSymbol() {
        return "-";
    }
    public  double calculate(double a, double b) {
        return a - b;
    }
}

Aucun commentaire:

Enregistrer un commentaire