Java generics T vs Object

I was wondering what is the difference between the following two method declarations:

public Object doSomething(Object obj) {....}

public <T> T doSomething(T t) {....}

Is there something you can/would do with one but not the other? I could not find this question elsewhere on this site.


Isolated from context - no difference. On both t and obj you can invoke only the methods of Object.

But with context - if you have a generic class:

MyClass<Foo> my = new MyClass<Foo>();
Foo foo = new Foo();

Then:

Foo newFoo = my.doSomething(foo);

Same code with object

Foo newFoo = (Foo) my.doSomething(foo);

Two advantages:

  • no need of casting (the compiler hides this from you)
  • compile time safety that works. If the Object version is used, you won't be sure that the method always returns Foo. If it returns Bar, you'll have a ClassCastException, at runtime.

The difference here is that in the first, we specify that the caller must pass an Object instance (any class), and it will get back another Object (any class, not necessarily of the same type).

In the second, the type returned will be the same type as that given when the class was defined.

Example ex = new Example<Integer>();

Here we specify what type T will be which allows us to enforce more constraints on a class or method. For example we can instantiate a LinkedList<Integer> or LinkedList<Example> and we know that when we call one of these methods, we'll get back an Integer or Example instance.

The main goal here is that the calling code can specify what type of objects a class will operate upon, instead of relying on type-casting to enforce this.

See Java Generics* from Oracle.

*Updated Link.


The difference is that with generic methods I don't need to cast and I get a compilation error when I do wrong:

public class App {

    public static void main(String[] args) {

        String s = process("vv");
        String b = process(new Object()); // Compilation error
    }

    public static <T> T process(T val) {

        return val;
    }
}

Using object I always need to cast and I don't get any errors when I do wrong:

public class App {

    public static void main(String[] args) {

        String s = (String)process("vv");
        String b = (String)process(new Object());
    }

    public static Object process(Object val) {

        return val;
    }
}