1

I Know I can use Generics while defining the ArrayList to do that. But here the case is different.

I have a ArrayList, which when defined accepts any type of Objects. Once the user inserts the first Object, I need to use Class Reference to Find the Class of that Object and then have to ensure that only Objects of that Class are inserted in the ArrayList.

Example:

ArrayList arrayList = new ArrayList();

Now lets say the User enters an object b, of Class B in the arrayList, then from now onwards, I must only allow objects of type B to be added to the arrayList.

I know that I can find the class of the Object inserted using:

arrayList.get(0).getClass();

But what after it? How will I use the Class type I just found?

4
  • 1
    I would consider defining an interface that all objects must implement. I think testing for class type is going to get ugly. If the objects implement an interface then your ArrayList can accept any type of class. Commented Jul 27, 2011 at 5:03
  • @Johnnieb: That's a good point, but interview questions are often contrived like this. Of course, the best answer is "you could do it like this, but a better design would be that". Commented Jul 27, 2011 at 5:09
  • If your "user" can interact with the ArrayList directly they'll be able to insert whatever they like won't they? Is the idea that you are supposed to write your own class that extends ArrayList, or that uses ArrayList for internal storage, where your class will enforce the first-object-stored-restricts-the-rest requirement? (If this is an "interview question" does that mean you're sitting in the interview right now hoping for a response on your smartphone?) Commented Jul 27, 2011 at 5:10
  • @nnnnnn: There is a class, that has a collection of ArrayList type. And I am not sitting in Interview right now and hoping for a quick response. I want to know if that can be done, and if yes, then how. Commented Jul 27, 2011 at 5:18

4 Answers 4

3

Since this is an interview question I won't give you a complete answer, but you might want to take a look at the Class.isAssignableFrom method.

Sign up to request clarification or add additional context in comments.

4 Comments

Thanks Cameron. That was helpful. But still the problem is not completely solved. Class.isAssignableFrom() will return true even if I pass an object of the original class's super or subclass
@Logan: that is usually what you want. A subclass is supposed to be usable everywhere the parent class can be used. If you really don't want that, use equals on the two classes.
@Thilo: I got my Answer. Thanks for helping.
@Logan: It should only return true if the other class is a subclass or the same class, e.g. Number.class.isAssignableFrom(Integer.class) should return true because an Integer is-a Number, but Integer.class.isAssignableFrom(Number.class) should return false because a Number is not necessarily an Integer.
2

You cannot use generics for this, you need to implement runtime checks.

One way would be to subclass ArrayList and implement the various add methods in a way that checks the type of what is being added.

get(0).getClass().cast(newObject);
// will throw a ClassCastException if it does not match

4 Comments

I had that in mind, but after getting the two classes, how do I compare them? Lets say I store the firstObject class in Variable class1 of Type Class, and other objects class in Variable class2, then will I use .equals to compare the two classes?
You do get(0).getClass().cast(theOtherObject). This will try to cast theOtherObject to the given class. If that fails, you will get an exception.
Ok. And if the exception is not thrown, then the classes will be same or will be the subclasses of the specified class.
Your answer is also correct, but I can only select one answer.
0

hmm .. you can do the comparison on the class names - not elegant but should do your work ..

get(0).getClass().getName().equals(classname for the pushed value)

5 Comments

better to just do equals() on the class objects themselves. (If that is what you really want, usually you'd want isAssignableFrom)
@Thilo: but what if equals() has been overridden ?
@Thilo: Not sure I follow this - Say if Person has equals overriden like this - boolean equals(Object b) {return name.equals(((Person)b).name);}
Yes, but Person.class.equals(aPerson.getClass()) will still be true.
@Thilo: I screwed this - simple concept, wasn't focusing on the details enough, thx for correcting.
0

I see some design issues in the code rather how to solve this issue. The flow of the code should determine what the code is doing so that it does not send the collection to a method which can put any arbitrary objects (by checking or not) in it.

I would advise to revisit the design.

For example, if someone is trying to put a soccer ball into the collection and then the collection should be passed into a method where it can deal with a soccer ball. They can use a common code or command pattern for handling any ball or specific behavior for soccer ball and so on.

The same is true if the code wants to put a base ball into a collection, it better knows what its going to do next.

It is a design issue... It is not a code issue.

1 Comment

Thanks for answering, but as mentioned in the question, this question was asked to me in an interview. I wanted to know the answer, hence posted the question here.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.