Page 1 of 1

About Question enthuware.ocpjp.v7.2.1445 :

Posted: Mon Sep 23, 2013 1:52 pm
by Student
"The important concept here once the method returns, there is no way to know what is the exact class of objects stored in the returned List. So you cannot declare out in a way that ties it to any particular class, not even Object. Thus, the only way to accomplish this is to use non-typed reference type, such as:  List result;"

Hi
Sorry, I don't get this, and it's come up in another question I think.
When you define a method like this:
"public static <E extends CharSequence> List<? super E> doIt(List<E> nums)"

you're saying, the method will return a List of objects whose type will be "E extends CharSequence" or a superclass of "E extends CharSequence". Correct?
That means, the method is *guaranteed* to return a List that satisfies that criteria? Is that right?
If that's so (maybe it's not but assuming it is), given that Object is a superclass of "E extends Charsequence", i.e. for any class E that extends CharSequence, then why can't List<Object> can't satisfy the assignment? I know you're right, because I checked it; I just don't understand the reason why.
You say " once the method returns, there is no way to know what is the exact class of objects stored in the returned List." But you know what they must be - a class that extends CharSequence, or CharSequence, or any parent of CharSequence.
Btw my knocked-up test code is

Code: Select all

import java.util.*;
public class Q39 {    
    public static void main(String ... args) {
        List<String> stringList = new ArrayList<>();
        //List list = Inner.doIt(stringList); // works
        List<Object> list = Inner.doIt(stringList); // fails
    }   
        
    static class Inner<E> {
        public static <E extends CharSequence> List<? super E> doIt(List<E> nums) {
            return new ArrayList<E>();
        }
    }     
}  

Q39.java:6: error: incompatible types
List<Object> list = Inner.doIt(stringList);
^
required: List<Object>
found: List<CAP#1>
where CAP#1 is a fresh type-variable:
CAP#1 extends Object super: String from capture of ? super String
1 error

All this CAP stuff is gobbledegook to me.
Thanks.

Re: About Question enthuware.ocpjp.v7.2.1445 :

Posted: Mon Sep 23, 2013 2:13 pm
by admin
You might want to go through this: viewtopic.php?f=2&t=473
If you still have a doubt, I would suggest you to go through a book to understand this topic because it is quite involved and is not really possible to explain it in a post.

HTH,
Paul.

Re: About Question enthuware.ocpjp.v7.2.1445 :

Posted: Wed Sep 25, 2013 7:01 pm
by Student
Okay, will do, thanks very much.

Re: About Question enthuware.ocpjp.v7.2.1445 :

Posted: Tue Oct 08, 2013 10:32 am
by Student
"List <?>" also works:

Code: Select all

import java.util.*;
public class C18 {
    public static <E extends CharSequence> List<? super E> doIt(List<E> nums) {
        return new ArrayList<CharSequence>();    
    }
    public static void main(String[] args) throws Exception {    
        List<String> stringList=new ArrayList<>();
        List<?> list1 = doIt(stringList);
        list1.add("xx"); // compiler error
        List list2 = doIt(stringList);
        list2.add("xx"); // ok
    }    
}
but you can't modify the List, hmmph.

Re: About Question enthuware.ocpjp.v7.2.1445 :

Posted: Sat Mar 15, 2014 5:49 pm
by accurate_guy
List<? super String> works too and it is modifiable!
String objects are instances of "? super String" and thus they can be added to a list of type List<? super String>.

The sentence "the only way to accomplish this is to use non-typed reference type" in the explanation of this question should be revised.

Code: Select all

import java.util.*;
public class C18 {
	public static <E extends CharSequence> List<? super E> doIt(List<E> nums) {
		return new ArrayList<E>();
	}

	public static void main(String[] args) throws Exception {
		List<String> stringList = new ArrayList<String>();
		List<? super String> list1 = doIt(stringList);
		list1.add("hi");	// this is ok!
		list1.add(1);	// compiler error
	}
}
This example shows very well why it makes sense to use "? super SomeClass" instead of just "?".

Re: About Question enthuware.ocpjp.v7.2.1445 :

Posted: Sat Mar 15, 2014 9:02 pm
by admin
I don't see how this contradicts with the explanation. Explanation does not say you cannot anny String to List<? super String>. Explanation says, "The important concept here once the method returns, there is no way to know what is the exact class of objects stored in the returned List. So you cannot declare out in a way that ties it to any particular class, not even Object."
So you cannot take anything out from it. For example, in your code, add this line at the end: String s = list1.get(0);

HTH,
Paul.

Re: About Question enthuware.ocpjp.v7.2.1445 :

Posted: Sun Mar 16, 2014 4:31 am
by accurate_guy
To me the explanation has signalled that only the non-typed "List" is possible.

It is possible to get something out of the list. I was not sure about that but you made me try it :) (and it makes sense):

Code: Select all

		List<? super String> list1 = doIt(stringList);
		list1.add("hi");    // you can add Strings
		Object object = list1.get(0);     // you get out Objects

Re: About Question enthuware.ocpjp.v7.2.1445 :

Posted: Sun Mar 16, 2014 5:19 am
by admin
Yes, Object is possible but that is quite obvious since everything in java is an Object, so whatever you get will always be an Object. I was focusing on the point that you raised and not about this.

I see your point about the part of the explanation that signals only List is possible. This has now been fixed.

thank you for your feedback!