Reputation: 1098
I have got
interface Module {
List<String> parse();
}
There are several implementations of the interface and in application I would like to have a HashSet<Module>
which ensures there is only one instance of each module. For this I need a proper hashCode
for each class. The proper implementation of hashCode
would be the one that returns the same constant for various instances of one module class but different one for different modules.
To create a nice design solution I would like to compute the hashCode from name of the module like:
public int hashCode() {
return ConcreteModule.class.getName().hashCode();
}
but this code would be the same for every implementation of interface... My idea was to create an abstract module which implements the hashcode but is it possible to reach the name of the class which extends this abstract class? Like:
public abstract class AbstractModule implements Module {
public int hashCode() {
// get the class name of class extending the abstract module
// and return hashcode of its string name
}
}
and then
public class ConcreteModule extends AbstractModule implements Module {
// implementation of parse() no need to create hashcode for each module
}
Would you suggest to create hashCodes for each module or is it possible to create something I am trying? Any suggestions or advices are welcome. Thanks in advance
Upvotes: 0
Views: 936
Reputation: 17707
After some thought, what you want to do is key the map off the class, not the instance....
HashMap<Class<? extends Module>, <Module>> mymap = .....
Then you have just one value for each class type. You can put with:
mymap.put(module.class(), module);
Upvotes: 2
Reputation: 691963
You could simply implement it like the following:
@Override
public final int hashCode() {
return this.getClass().getName().hashCode();
}
@Override
public final boolean equals(Object other) {
if (other == this) {
return true;
}
if (other == null) {
return false;
}
return other.getClass().equals(this.getClass());
}
But I'm not sure it's the best idea. Moreover, you can't guarantee that all implementations of the interface extend your abstract class.
You could simply maintain a Map<Class<? extends Module>, Module>
. Each module implementation would add itself to your registry, and if the class of the module is already in the map, you would simply reject or ignore the new module instance.
Upvotes: 1
Reputation: 53694
how about:
return getClass().getName().hashCode();
Although, you could just as easily use:
return getClass().hashCode();
Upvotes: 1