In Java, is it possible to prevent a class for being extended anonymously?
For example
public class A () {
public void hello() {}
}
I want to allow a named class extension:
public class B extends A {
}
but not anonymously:
A a = new A() {
public void hello() {
}
}
This is for serialization purpose.
Yes, there is a way to accomplish this, through the use of a runtime exception:
class MyData implements Serializable {
public MyData() {
if (getClass().isAnonymousClass()) {
throw new IllegalStateException("Anonymous subclasses are not serializable.");
}
}
}
Technically, anonymous classes are serializable, but it might be a good idea taking a look at this before trying to live with that.
Related
I have a generic interface
public interface Consumer<E> {
public void consume(E e);
}
I have a class that consumes two types of objects, so I would like to do something like:
public class TwoTypesConsumer implements Consumer<Tomato>, Consumer<Apple>
{
public void consume(Tomato t) { ..... }
public void consume(Apple a) { ...... }
}
Apparently I can't do that.
I can of course implement the dispatch myself, e.g.
public class TwoTypesConsumer implements Consumer<Object> {
public void consume(Object o) {
if (o instanceof Tomato) { ..... }
else if (o instanceof Apple) { ..... }
else { throw new IllegalArgumentException(...) }
}
}
But I am looking for the compile-time type-checking and dispatching solution that generics provide.
The best solution I can think of is to define separate interfaces, e.g.
public interface AppleConsumer {
public void consume(Apple a);
}
Functionally, this solution is OK, I think. It's just verbose and ugly.
Any ideas?
Consider encapsulation:
public class TwoTypesConsumer {
private TomatoConsumer tomatoConsumer = new TomatoConsumer();
private AppleConsumer appleConsumer = new AppleConsumer();
public void consume(Tomato t) {
tomatoConsumer.consume(t);
}
public void consume(Apple a) {
appleConsumer.consume(a);
}
public static class TomatoConsumer implements Consumer<Tomato> {
public void consume(Tomato t) { ..... }
}
public static class AppleConsumer implements Consumer<Apple> {
public void consume(Apple a) { ..... }
}
}
If creating these static inner classes bothers you, you can use anonymous classes:
public class TwoTypesConsumer {
private Consumer<Tomato> tomatoConsumer = new Consumer<Tomato>() {
public void consume(Tomato t) {
}
};
private Consumer<Apple> appleConsumer = new Consumer<Apple>() {
public void consume(Apple a) {
}
};
public void consume(Tomato t) {
tomatoConsumer.consume(t);
}
public void consume(Apple a) {
appleConsumer.consume(a);
}
}
Because of type erasure you can't implement the same interface twice (with different type parameters).
Here's a possible solution based on Steve McLeod's one:
public class TwoTypesConsumer {
public void consumeTomato(Tomato t) {...}
public void consumeApple(Apple a) {...}
public Consumer<Tomato> getTomatoConsumer() {
return new Consumer<Tomato>() {
public void consume(Tomato t) {
consumeTomato(t);
}
}
}
public Consumer<Apple> getAppleConsumer() {
return new Consumer<Apple>() {
public void consume(Apple a) {
consumeApple(t);
}
}
}
}
The implicit requirement of the question was Consumer<Tomato> and Consumer<Apple> objects that share state. The need for Consumer<Tomato>, Consumer<Apple> objects comes from other methods that expect these as parameters. I need one class the implement them both in order to share state.
Steve's idea was to use two inner classes, each implementing a different generic type.
This version adds getters for the objects that implement the Consumer interface, which can then be passed to other methods expecting them.
At least, you can make a small improvement to your implementation of dispatch by doing something like the following:
public class TwoTypesConsumer implements Consumer<Fruit> {
Fruit being an ancestor of Tomato and Apple.
just Stumbled upon this. It just happened, that I had the same Problem, but I solved it in a different way:
I just created a new Interface like this
public interface TwoTypesConsumer<A,B> extends Consumer<A>{
public void consume(B b);
}
unfortunately, this is considered as Consumer<A> and NOT as Consumer<B> against all Logic. So you have to create a small Adapter for the second consumer like this inside your class
public class ConsumeHandler implements TwoTypeConsumer<A,B>{
private final Consumer<B> consumerAdapter = new Consumer<B>(){
public void consume(B b){
ConsumeHandler.this.consume(B b);
}
};
public void consume(A a){ //...
}
public void conusme(B b){ //...
}
}
if a Consumer<A> is needed, you can simply pass this, and if Consumer<B> is needed just pass consumerAdapter
In Functional style it is quite easy do this without implementing the interface and also it does the compile time type checking.
Our functional interface to consume entity
#FunctionalInterface
public interface Consumer<E> {
void consume(E e);
}
our manager to process and consume entity appropriately
public class Manager {
public <E> void process(Consumer<E> consumer, E entity) {
consumer.consume(entity);
}
public void consume(Tomato t) {
// Consume Tomato
}
public void consume(Apple a) {
// Consume Apple
}
public void test() {
process(this::consume, new Tomato());
process(this::consume, new Apple());
}
}
You cannot do this directly in one class as the class definition below cannot be compiled due to erasure of generic types and duplicate interface declaration.
class TwoTypesConsumer implements Consumer<Apple>, Consumer<Tomato> {
// cannot compile
...
}
Any other solution for packing the same consume operations in one class requires to define your class as:
class TwoTypesConsumer { ... }
which is pointless as you need to repeat/duplicate the definition of both operations and they won't be referenced from interface. IMHO doing this is a bad small and code duplication which I'm trying to avoid.
This might be an indicator also that there is too much responsibility in one class to consume 2 different objects (if they aren't coupled).
However what I'm doing and what you can do is to add explicit factory object to create connected consumers in the following way:
interface ConsumerFactory {
Consumer<Apple> createAppleConsumer();
Consumer<Tomato> createTomatoConsumer();
}
If in reality those types are really coupled (related) then I would recommend to create an implementation in such way:
class TwoTypesConsumerFactory {
// shared objects goes here
private class TomatoConsumer implements Consumer<Tomato> {
public void consume(Tomato tomato) {
// you can access shared objects here
}
}
private class AppleConsumer implements Consumer<Apple> {
public void consume(Apple apple) {
// you can access shared objects here
}
}
// It is really important to return generic Consumer<Apple> here
// instead of AppleConsumer. The classes should be rather private.
public Consumer<Apple> createAppleConsumer() {
return new AppleConsumer();
}
// ...and the same here
public Consumer<Tomato> createTomatoConsumer() {
return new TomatoConsumer();
}
}
The advantage is that the factory class knows both implementations, there is a shared state (if needed) and you can return more coupled consumers if needed. There is no repeating consume method declaration which aren't derived from interface.
Please note that each consumer might be independent (still private) class if they aren't completely related.
The downside of that solution is a higher class complexity (even if this can be a one java file) and to access consume method you need one more call so instead of:
twoTypesConsumer.consume(apple)
twoTypesConsumer.consume(tomato)
you have:
twoTypesConsumerFactory.createAppleConsumer().consume(apple);
twoTypesConsumerFactory.createTomatoConsumer().consume(tomato);
To summarize you can define 2 generic consumers in one top-level class using 2 inner classes but in case of calling you need to get first a reference to appropriate implementing consumer as this cannot be simply one consumer object.
Another alternative to avoid the use of more classes. (example using java8+)
// Mappable.java
public interface Mappable<M> {
M mapTo(M mappableEntity);
}
// TwoMappables.java
public interface TwoMappables {
default Mappable<A> mapableA() {
return new MappableA();
}
default Mappable<B> mapableB() {
return new MappableB();
}
class MappableA implements Mappable<A> {}
class MappableB implements Mappable<B> {}
}
// Something.java
public class Something implements TwoMappables {
// ... business logic ...
mapableA().mapTo(A);
mapableB().mapTo(B);
}
Sorry for answer old questions, but I really love it! Try this option:
public class MegaConsumer implements Consumer<Object> {
Map<Class, Consumer> consumersMap = new HashMap<>();
Consumer<Object> baseConsumer = getConsumerFor(Object.class);
public static void main(String[] args) {
MegaConsumer megaConsumer = new MegaConsumer();
//You can load your customed consumers
megaConsumer.loadConsumerInMapFor(Tomato.class);
megaConsumer.consumersMap.put(Apple.class, new Consumer<Apple>() {
#Override
public void consume(Apple e) {
System.out.println("I eat an " + e.getClass().getSimpleName());
}
});
//You can consume whatever
megaConsumer.consume(new Tomato());
megaConsumer.consume(new Apple());
megaConsumer.consume("Other class");
}
#Override
public void consume(Object e) {
Consumer consumer = consumersMap.get(e.getClass());
if(consumer == null) // No custom consumer found
consumer = baseConsumer;// Consuming with the default Consumer<Object>
consumer.consume(e);
}
private static <T> Consumer<T> getConsumerFor(Class<T> someClass){
return t -> System.out.println(t.getClass().getSimpleName() + " consumed!");
}
private <T> Consumer<T> loadConsumerInMapFor(Class<T> someClass){
return consumersMap.put(someClass, getConsumerFor(someClass));
}
}
I think that is what you are looking for.
You get this output:
Tomato consumed!
I eat an Apple
String consumed!
I am not sure how am I suppose to go about my question. It is about Android can Instantiate Interface. I am trying to do in C#. Now I am pretty sure that the rules for both Java and C# is you can't create an Instance of abstract and Interface as being said.
But I would really like to know how Android does this practice.
In Android you can do this.
public interface Checkme{
void Test();
void Test2();
}
public void myFunc(Checkme my){
//do something
}
// Now this is the actual usage.
public void Start(){
myFunc(new Checkme(){
#Override
public void Test()
{
}
#Override
public void Test2()
{
}
});
}
Actually once you press Enter on new Checkme() You will automatically get the Override methods of the Interface. Like auto Implement method of an Interface in C#.
I hope my question make sense.
C# doesn't support anonymously auto-implemented interfaces because it has delegates:
public void Foo(Func<string> func, Action action) {}
// call it somewhere:
instance.Foo(() => "hello world", () => Console.WriteLine("hello world"));
With delegates you can fill the gap and it can be even more powerful than implementing interfaces with anonymous classes.
Learn more about delegates.
This is an Anonymous Class:
public void Start(){
myFunc(new Checkme() {
#Override
public void Test() {
}
#Override
public void Test2() {
}
});
}
An anonymous class is an unnamed class implemented inline.
You could also have done it using a Local Class, but those are rarely seen in the wild.
public void Start(){
class LocalCheckme implements Checkme {
#Override
public void Test() {
}
#Override
public void Test2() {
}
}
myFunc(new LocalCheckme());
}
These both have the advantage that they can use method parameters and variables directly, as long as they are (effectively) final.
As a third option, you could do it with an Inner Class.
private class InnerCheckme implements Checkme {
#Override
public void Test() {
}
#Override
public void Test2() {
}
}
public void Start(){
myFunc(new InnerCheckme());
}
An inner class cannot access method variables (obviously because it's outside the method), but can be used by multiple methods.
Any local values from the method can however be passed into the constructor and stored as fields of the inner class, to get the same behavior. Just requires a bit more code.
If the inner class doesn't need access to fields of the outer class, it can be declared static, making it a Static Nested Class.
So, all 3 ways above a very similar. The first two are just Java shorthands for the third, i.e. syntactic sugar implemented by the compiler.
C# can do the third one, so just do it that way for C#.
Of course, if the interface only has one method, using a Java lambda or C# delegate is much easier than Anonymous / Local / Inner classes.
If I understand correcly, you're defining a class that implements an interface, and when you specify that the class implements an interface, you want it to automatically add the interface's methods and properties.
If you've declared this:
public interface ISomeInterface
{
void DoSomething();
}
And then you add a class:
public class MyClass : ISomeInterface // <-- right-click
{
}
Right-click on the interface and Visual Studio will give you an option to implement the interface, and it will add all the interface's members to the class.
you mean something like this?
pulic interface Foo{
void DoSomething();
}
public class Bar : Foo {
public void DoSomething () {
//logic here
}
}
myFunc(new Checkme(){
#Override
public void Test()
{
}
#Override
public void Test2()
{
}
});
You're passing into myFunc() something that is called an anonymous class. When it says "new Checkme() { .... }", it is defining an anonymous implementation of the Checkme interface. So, it's not an instance of the interface itself, just an instance of a type that implements it.
In C# anonymously implemented classes for Interface are not auto generated just like in java, you need to follow the below procedure to workout.
public class MyClass {
public void someMethod (string id, IMyInterface _iMyInterface) {
string someResponse = "RESPONSE FOR " + id;
_iMyInterface.InterfaceResponse (someResponse);
}
}
public interface IMyInterface {
void InterfaceResponse (object data);
void InterfaceResponse2 (object data, string x);
}
public class MyInterfaceImplementor : IMyInterface {
private readonly Action<object> actionname;
private readonly Action<object, string> actionInterfaceResponse2;
public MyInterfaceImplementor (Action<object> InterfaceResponse) {
this.actionname = InterfaceResponse;
}
public MyInterfaceImplementor(Action<object> interfaceResponseMethod, Action<object, string> interfaceResponseMethod1) {
this.actionname = interfaceResponseMethod ?? throw new ArgumentNullException(nameof(interfaceResponseMethod));
this.actionInterfaceResponse2 = interfaceResponseMethod1 ?? throw new ArgumentNullException(nameof(interfaceResponseMethod1));
}
public void InterfaceResponse (object data) {
this.actionname (data);
}
public void InterfaceResponse2(object data, string x) {
this.actionInterfaceResponse2(data, x);
}
}
Gist Source : https://gist.github.com/pishangujeniya/4398db8b9374b081b0670ce746f34cbc
Reference :
I have a basic question about generics in Java.
I have a class X which is instantiated by another class T. In every class T which will be used has a method called as methodOfT(). However, Java gives me compiler time error since it does not know obj and methodOfT().
public class X<T>
{
T obj;
public void methodOfX()
{
obj.methodOfT();
}
}
In order to avoid this problem, what I did is I defined another class XSuper. And every class now which wants to instantiate X will extend this XSuper class. This removes the compile time error and allows me to achieve what I want.
public abstract class XSuper
{
public abstract void methodOfT();
}
public class UserOfX extends XSuper
{
X<UserOfX> objX = new X<UserOfX>();
public void methodOfT()
{
}
}
However, I want to know the cleaner way of doing this thing. Since I want to derive class UserOfX from another Class. Another Problem is that I want to define methodOfT() method as -
public methodOfT(T objOfT)
{
}
In this case, the above solution fails. Could someone help.
public class X<T>
{
T obj;
public void methodOfX()
{
obj.methodOfT();
}
}
The compiler doesn't know what T is so it is evaluated as Object. Object does not have a methodOfT method, so compilation fails. Here's how to solve that:
public interface SomeInterface{
void methodOfT();
}
public class X<T extends SomeInterface>
{
T obj;
public void methodOfX()
{
obj.methodOfT();
}
}
In this case, the compiler knows that the supplied T will implement the interface SomeInterface and hence have the method methodOfT. (You can also use classes instead of interfaces, but that's less elegant)
Given your additional requirements, we're going t have to change this code some more:
public interface SomeInterface<X>{
void methodOfT(X object);
}
public class X<T1, T2 extends SomeInterface<T1>>
{
T1 obj1;
T2 obj2;
public void methodOfX()
{
obj2.methodOfT(obj1);
}
}
How can an anonymous class implement two (or more) interfaces? Alternatively, how can it both extend a class and implement an interface?
For example, I want to create an object of anonymous class that extends two interfaces:
// Java 10 "var" is used since I don't know how to specify its type
var lazilyInitializedFileNameSupplier = (new Supplier<String> implements AutoCloseable)() {
private String generatedFileName;
#Override
public String get() { // Generate file only once
if (generatedFileName == null) {
generatedFileName = generateFile();
}
return generatedFileName;
}
#Override
public void close() throws Exception { // Clean up
if (generatedFileName != null) {
// Delete the file if it was generated
generatedFileName = null;
}
}
};
Then I can use it in a try-with-resources block as AutoCloseable as lazily-initialized utility class:
try (lazilyInitializedFileNameSupplier) {
// Some complex logic that might or might not
// invoke the code that creates the file
if (checkIfNeedToProcessFile()) {
doSomething(lazilyInitializedFileNameSupplier.get());
}
if (checkIfStillNeedFile()) {
doSomethingElse(lazilyInitializedFileNameSupplier.get());
}
}
// By now we are sure that even if the file was generated, it doesn't exist anymore
I don't want to create an inner class because I'm absolutely sure that this class won't be used anywhere except the method I need to use it in (and I also might want to use local variables declared in that method that might be of var type).
Anonymous classes must extend or implement something, like any other Java class, even if it's just java.lang.Object.
For example:
Runnable r = new Runnable() {
public void run() { ... }
};
Here, r is an object of an anonymous class which implements Runnable.
An anonymous class can extend another class using the same syntax:
SomeClass x = new SomeClass() {
...
};
What you can't do is implement more than one interface. You need a named class to do that. Neither an anonymous inner class, nor a named class, however, can extend more than one class.
An anonymous class usually implements an interface:
new Runnable() { // implements Runnable!
public void run() {}
}
JFrame.addWindowListener( new WindowAdapter() { // extends class
} );
If you mean whether you can implement 2 or more interfaces, than I think that's not possible. You can then make a private interface which combines the two. Though I cannot easily imagine why you would want an anonymous class to have that:
public class MyClass {
private interface MyInterface extends Runnable, WindowListener {
}
Runnable r = new MyInterface() {
// your anonymous class which implements 2 interaces
}
}
I guess nobody understood the question. I guess what this guy wanted was something like this:
return new (class implements MyInterface {
#Override
public void myInterfaceMethod() { /*do something*/ }
});
because this would allow things like multiple interface implementations:
return new (class implements MyInterface, AnotherInterface {
#Override
public void myInterfaceMethod() { /*do something*/ }
#Override
public void anotherInterfaceMethod() { /*do something*/ }
});
this would be really nice indeed; but that's not allowed in Java.
What you can do is use local classes inside method blocks:
public AnotherInterface createAnotherInterface() {
class LocalClass implements MyInterface, AnotherInterface {
#Override
public void myInterfaceMethod() { /*do something*/ }
#Override
public void anotherInterfaceMethod() { /*do something*/ }
}
return new LocalClass();
}
Anonymous classes always extend superclass or implements interfaces. for example:
button.addActionListener(new ActionListener(){ // ActionListener is an interface
public void actionPerformed(ActionEvent e){
}
});
Moreover, although anonymous class cannot implement multiple interfaces, you can create an interface that extends other interface and let your anonymous class to implement it.
// The interface
interface Blah {
void something();
}
...
// Something that expects an object implementing that interface
void chewOnIt(Blah b) {
b.something();
}
...
// Let's provide an object of an anonymous class
chewOnIt(
new Blah() {
#Override
void something() { System.out.println("Anonymous something!"); }
}
);
An anonymous class is extending or implementing while creating its object
For example :
Interface in = new InterFace()
{
..............
}
Here anonymous class is implementing Interface.
Class cl = new Class(){
.................
}
here anonymous Class is extending a abstract Class.
I'm looking to create a set of functions which all implementations of a certain Interface can be extended to use. My question is whether there's a way to do this without using a proxy or manually extending each implementation of the interface?
My initial idea was to see if it was possible to use generics; using a parameterized type as the super type of my implementation...
public class NewFunctionality<T extends OldFunctionality> extends T {
//...
}
...but this is illegal. I don't exactly know why this is illegal, but it does sort of feel right that it is (probably because T could itself be an interface rather than an implementation).
Are there any other ways to achieve what I'm trying to do?
EDIT One example of something I might want to do is to extend java.util.List... Using my dodgy, illegal syntax:
public class FilterByType<T extends List> extends T {
public void retainAll(Class<?> c) {
//..
}
public void removeAll(Class<?> c) {
//..
}
}
You can achieve something like this using a programming pattern known as a 'decorator' (although if the interface is large then unfortunately this is a bit verbose to implement in Java because you need to write single-line implementations of every method in the interface):
public class FilterByType<T> implements List<T> {
private List<T> _list;
public FilterByType(List<T> list) {
this._list = list;
}
public void retainAll(Class<?> c) {
//..
}
public void removeAll(Class<?> c) {
//..
}
// Implement List<T> interface:
public boolean add(T element) {
return _list.add(element);
}
public void add(int index, T element) {
_list.add(index, element);
}
// etc...
}
Alternatively, if the methods don't need to access protected members, then static helper methods are a less clucky alternative:
public class FilterUtils {
public static void retainAll(List<T> list, Class<?> c) {
//..
}
public static void removeAll(List<T> list, Class<?> c) {
//..
}
}
What prevents you from just adding new methods to the interface?
If you can't just add the new functionality to old interface, you could consider making another interface and then an implementation which merely implements those two. Just to be clear, in code this is what I mean:
// Old functionality:
public interface Traveling {
void walk();
}
// Old implementation:
public class Person implements Traveling {
void walk() { System.out.println("I'm walking!"); }
}
// New functionality:
public interface FastTraveling {
void run();
void fly();
}
// New implementation, option #1:
public class SuperHero extends Person implements FastTraveling {
void run() { System.out.println("Zoooom!"); }
void fly() { System.out.println("To the skies!"); }
}
// New implementation, option #2:
public class SuperHero implements Traveling, FastTraveling {
void walk() { System.out.println("I'm walking!"); }
void run() { System.out.println("Zoooom!"); }
void fly() { System.out.println("To the skies!"); }
}
I think it's illegal because you can not guarantee what class T will be. Also there are technical obstacles (parent's class name must be written in bytecode, but Generics information get lost in bytecode).
You can use Decorator pattern like this:
class ListDecorator implements List {
private List decoratingList;
public ListDecorator(List decoratingList){
this.decoratingList = decoratingList;
}
public add(){
decoratingList.add();
}
...
}
class FilterByArrayList extends ListDecorator {
public FilterByAbstractList () {
super(new ArrayList());
}
}
There is a delegation/mixin framework that allows a form of this. You can define a new interface, implement a default implementation of that interface, then request classes which implement that interface but subclass from elsewhere in your hierarchy.
It's called mixins for Java, and there's a webcast right there that demonstrates it.
I'm afraid it's not clear what do you want to get.
Basically, I don't see any benefit in using 'public class NewFunctionality<T extends OldFunctionality> extends T' in comparison with 'public class NewFunctionality extends OldFunctionality' ('public class FilterByType<T extends List> extends T' vs 'public class FilterByType<T> implements List<T>')