Reputation: 1340
the following code
Supplier<String> newString = String::new;
System.out.println(newString.get());
// prints an empty string (nothing) to the console and then a newline character
and for the definition of Supplier get method
T get()
the get method should return T, but constructor has no return type, so why String::new can be assigned to Supplier <String>?
Upvotes: 0
Views: 281
Reputation: 17066
Perhaps you've been reading the Java Tutorial regarding constructors, which states,
Constructor declarations look like method declarations—except that they use the name of the class and have no return type.
It's subtle, but there is a difference between that sentence and the statement in the OP.
...constructor has no return type,
Notice the Tutorial states that a constructor declaration has no return type, which is slightly different from saying that a constructor itself has no return type.
The declaration is the syntax; and we can confirm there is indeed no return type shown in the code. So there is no explicit return type. But there is an implicit return type, which is already stated as the name of the constructor. We simply don't need to repeat the return type in the declaration, because the compiler can infer it from the constructor name.
Upvotes: 1
Reputation:
calling a constructor (new
) creates an object and "return
s" it, as you see.
Object object = new Object();
→ if a constructor would not return anything, this code was false...
But it isn't.
Therefore, the following example is okay
new Thread(new Runnable() {
@Override public void run() {
System.out.print("it runs.");
}
}).start();
Upvotes: 0
Reputation: 201429
I think two examples will explain it, first what you wanted was a supplier for a meaningful string to print. Like,
Supplier<String> newString = () -> "test";
System.out.println(newString.get());
What you provided was an empty string. Like,
System.out.println(new String());
It's perfectly valid to produce an empty string, even if the result deviated from your expectations.
Bonus third example, to elaborate on the first example, in a lambda expression you are actually implementing a single abstract method from a functional interface - specifically Supplier<T>
. Like,
Supplier<String> newString = new Supplier<String>() {
@Override
public String get() {
return "test"; // originally return new String()
}
};
System.out.println(newString.get());
Upvotes: 3