0

I understand the concept of PECS (Producer extends, Consumer super) but still have confusion regarding these notations:

public class PECSTest {
    public static void main(String[] args) {
        //List<? extends Object> ProducerList = new ArrayList<String>();
        //ProducerList.add("1"); // Line 1 :compileTimeError

        PECSTest myTest = new PECSTest();
        List<String> myList = new ArrayList<String>();
        myList.add("abc");
        myTest.printMyList(myList);
    }

    private void printMyList(List<? extends Object> myList) {
        // TODO Auto-generated method stub
        int i=0;
        while(i<myList.size()) {
            System.out.println(myList.get(i).getClass()); //Line 2
            System.out.println(myList.get(i).charAt(0)); // Line 3
            System.out.println(myList.get(i).equals(new String("abc")));
            i++;
        }
    }
}
  • Even I have created a list that can accept any object that extends Object class but when i tried to add string it gave compile time error at Line 1. Why So ?
  • In the second case when i am passing my List to printMyList method it print each elements class type in String at Line 2 but then at Line 3 why i am not able to call any String class specific methods like charAt. Also why there is no casting required to String.

Also in case of consumer

 List<? super Number> myList = new ArrayList<Object>();
 myList.add(new Object());// compile time error

Why can't i add Object in myList. Because if we are using super that mean this list can contains objects that are equal and higher than number in heirarchy of Java classes. So new Object() should get added in the list as per that statement.

Thanks.

user2342558
  • 5,567
  • 5
  • 33
  • 54
Manish
  • 1,274
  • 3
  • 22
  • 59
  • You cant instantiate a "generic" `Object` like `new Object()` – user2342558 Nov 25 '19 at 11:24
  • why are you using a lower bounded wildcard on `Number` (`List super Number>`)? It may be `List extends Number>` that allows every subclass of `Number` instead every Object that is not a Number... – user2342558 Nov 25 '19 at 11:27

1 Answers1

0

List is already a Generic so you shouldn't set its type as generic; if you want that it accepts all types so set its type to Object; also, you shouldn't specify the type in the instantiation because Java can infers it from the type declaration:

List<Object> ProducerList = new ArrayList<>();

Thanks to Java Polymorphism, ProducerList now allows all types, because all Classes are a specialization of the Object Class.

Since the printMyList's parameter myList accepts more that one type, you must check its type passed before cast it in order to invoke its methods, e.g. charAt() for String:

if (myList.get(i) instanceof String) { 
    System.out.println(((String)myList.get(i)).charAt(0)); // Line 3
}

Complete working code:

import java.util.*;

class PECSTest
{
    public static void main(String[] args) {
        List<Object> ProducerList = new ArrayList<>();
        ProducerList.add("1"); // Line 1

        PECSTest myTest = new PECSTest();
        List<String> myList = new ArrayList<String>();
        myList.add("abc");
        myTest.printMyList(myList);
    }

    private void printMyList(List<? extends Object> myList) {
        int i=0;
        while(i<myList.size()) {
            System.out.println(myList.get(i).getClass()); //Line 2
            if (myList.get(i) instanceof String) { 
                System.out.println(((String)myList.get(i)).charAt(0)); // Line 3
            }
            System.out.println(myList.get(i).equals(new String("abc")));
            i++;
        }
    }
}

outputs:

class java.lang.String
a
true

A side note: why are you using a lower bounded wildcard on Number (List<? super Number>)? It may be List<? extends Number> that allows every subclass of Number instead every Object that is not a Number...

user2342558
  • 5,567
  • 5
  • 33
  • 54
  • "In the first case, you may not specify the type in the instantiation because Java can infers it from the type declaration:" but java is allowing that. I am not getting any error while using List extends Object> ProducerList = new ArrayList(); So why i am getting error while adding string object. – Manish Nov 25 '19 at 17:53