Java:
Why is a method called void (ie. it doesn't return anything) if it returns this:
System.out.println("Something");
For example:
public static void sayHello() {
System.out.println("Hello");
}
It does return something, this message!
I would say it prints a message to standard output, but it does not return anything to the calling statement.
Consider these two routines.
public void sayHello() { System.out.println("Hello"); }
public int giveANumber() { System.out.println("Hi"); return 42; }
How would you call them?
sayHello();
int i = giveANumber();
Since sayHello is void, there's no equals sign and nothing on the left-hand side when you call it. However, since giveANumber returns an int, you should call it with the equals sign and an integer to receive the value on the left-hand side.
This method does something (prints "Hello"), but it doesn't return anything. If it returned a value, you'd be able to do this:
aVariableToAssignReturnValue = sayHello(); //you can't do it!
Read this for example.
In programming language history there was Algol68, possibly the best procedural language of all. It was the first fully defined language, and everything was typed. It was so to say and expression language.
In it VOID was a type with a single value SKIP. A PROC () VOID, a method, could be coerced to VOID, doing a call.
It doesn't return anything that can be stored in variable.
so it's simply don't return anything.
but it can do things like print to console.
"Return" in this case means that a value is passed back through the stack that could be assigned to a variable in the calling code. That's not the case in your example.
Object o = sayHello(); // WRONG - Compile error
A void method can do things - In your case print to the screen. That's not a "return" in these described here.
Since the question shows at the top of the page as "Java Void Methods Return" with a capital "V" on "Void" it may also be worth noting that Java has a class "Void" in addition to the keyword "void." A method declared to return Void does return something - but if that's your case, you should check the documentation for that class because it's kind of a special case.
It's simple and straightforward because you are asking him to execute something not returning something . your method returns a void which means nothing. Being a c programmer, In C a method that returns nothing is called procedure. for more checkout What is the difference between a "function" and a "procedure"?.
sayHello() has no return statement; therefore, it is a void method. By your assumption, the only truly void method would look like this: public static void wowSuchVoid(){ }. What's even the point?
Related
I was recently reading a java class where the person had created methods via IDE shortcut( extract method shortcut ). All methods had a return type of void and what was supposed to be return type was passed as input parameter for the method. Below is an example of what i'm referring to.
public void multiply(Integer first, Integer second, Integer result){
result = first * second;
}
I was wondering if the above is a good way of doing things. I personally do not like the above way of creating methods. I think the method should have been like below.
public Integer multiply(Integer first, Integer second, Integer result){
return first * second;
}
But in IntelliJ/Eclipse when we do extract method mostly creates method like above.
Can someone please let me know why IDE's usually create void method when we use the extract method shortcut and is the 1st style of method definition a good practice at all?
If the method being called isn't being assigned to a variable, Eclipse has no way to know what the return value is supposed to be.
Presumably, the original code looked something like this:
public static void main(String args[]){
Integer result = 0;
multiply(1,3,result);
}
There's no way for Eclipse to divine that multiply is supposed to return anything, so it defaults to void. If you want to infer return values, have it be assigned to a variable like so:
public static void main(String args[]){
Integer result = 0;
result = multiply(1,3,result);
}
Consider:
class TestParent{
public int i = 100;
public void printName(){
System.err.println(this); //{TestChild#428} according to the Debugger.
System.err.println(this.i); //this.i is 100.
}
}
class TestChild extends TestParent{
public int i = 200;
}
public class ThisTest {
public static void main(String[] args) {
new TestChild().printName();
}
}
I know that similar questions have been asked, but I couldn't get a firm understanding of the 'this' variable in Java.
Let me try to explain how I understand the result of the above image.
Since it's a new TestChild() object that's calling the printName() method, the this variable in line 6 is set to a TestChild object - {TestChild#428} according to the Debugger.
However, since Java doesn't have a virtual field - I'm not completely sure what this means, but I conceptually understand it as being the opposite of Java methods, which support Polymorphism - this.i is set to 100 of TestParent at compile time.
So no matter what this is, this.i in a TestParent method will always be the i variable in the TestParent class.
I'm not sure that my understanding is correct so please correct me if I'm wrong.
And also, my main question is,
How is the this variable set to the current object that's calling the method? How is it actually implemented?
In essence, there is no difference between
this.foo()
and
anyObject.foo()
as both are "implemented" the same way. Keep in mind that "in the end" "object orientation is only an abstraction, and in "reality" what happens is something like:
foo(callingObject)
In other words: whenever you use some object reference to call a method ... in the end there isn't a call on some object. Because deep down in assembler and machine code, something like "a call on something" doesn't exist.
What really happens is a call to a function; and the first (implicit/invisible on the source code level) parameter is that object.
BTW: you can actually write that down in Java like:
class Bar {
void foo(Bar this) { ... }
and later use
new Bar().foo();
And for this.fieldA, in the end: you have a reference to some location in memory; and a table that tells you on which "offset" you will find fieldA.
Edit - just for the record. If you are interested in more details about foo(Bar this) - you can turn to this question; giving the details in the Java spec behind it!
What's happening here is that there are two completely different fields both called i; to use their full names, one is TestParent::i and one is TestChild::i.
Because the method printName is defined in TestParent, when it refers to i, it can only see TestParent::i, which is set to 100.
Whereas when you set i to 200 in TestChild, both fields called i are visible, but because they have the same name, TestChild::i hides TestParent::i, and you end up setting TestChild::i and leaving TestParent::i untouched.
Well when a new object is created that object has an address in memory so you can think of it as if the object had a private member this that is set to the address when the object is created. You can also think of it like this: obj.method(param) is just syntactic sugar for method(obj, param); and this is actually a parameter of method.
To directly address what you see in the output: The call to print 'this.i' is passing as argument to 'print()' the value of the field 'i' in the current scope, which is the scope of the parent class. By contrast, the call to print 'this' is getting translated under the hood to a call to print 'this.getClass().getName()' [roughly speaking], and the 'getClass()' call gets the actual class object, which is for the child class.
Adding some more info on top of #Tom Anderson answer, which explains hiding concept nicely.
I have added one more constructor in Child ( TestChild) which prints values of i in both parent and child.
If you want get value of i from child (TestChild), override the method in TestChild.
class TestParent{
public int i = 100;
public void printName(){
System.err.println("TestParent:printName()");
System.err.println(this); //{TestChild#SOME_NUM} according to the Debugger.
System.err.println(this.i); //this.i is 100.
}
}
class TestChild extends TestParent{
public int i = 200;
public TestChild(){
System.out.println("TestChild.i and TestParent.i:"+this.i+":"+super.i);
}
public void printName(){
//super.printName();
System.err.println("TestChild:printName()");
System.err.println(this); //{TestChild#SOME_NUM} according to the Debugger.
System.err.println(this.i); //this.i is 200.
}
}
public class ThisTest {
public static void main(String[] args) {
TestParent parent = new TestChild();
parent.printName();
}
}
Case 1: If I comment super.printName() call from child, Child version of TestChild.printName() prints the value of i in TestChild
Output:
TestChild.i and TestParent.i:200:100
TestChild:printName()
TestChild#43cda81e
200
Case 2: TestChild.printName() calls super.printName() as the first line in printName() method. In this case, i value from both parent and child are displayed in respective methods.
Output:
TestChild.i and TestParent.i:200:100
TestParent:printName()
TestChild#43cda81e
100
TestChild:printName()
TestChild#43cda81e
200
1) In Java, I can do this:
Void z = null;
Is there any other value except null I can assign to z?
2) Consider the following code snipped:
Callable<Void> v = () -> {
System.out.println("zzz");
Thread.sleep(1000);
return null;
};
This compiles OK, but if I remove the last statement return null; it doesn't. Why? After all, Void is supposed to mean no return value.
From the docs:
The Void class is an uninstantiable placeholder class to hold a reference to the Class object representing the Java keyword void.
So, no.
Void is used by methods having to return an object, but really returning nothing.
A decent example can be observed with some usage of the AsyncTask in Android, in cases where you don't need to return any object after the task is complete.
You would then extend AsyncTask<[your params type], [your progress type], Void>, and return null in your onPostExecute override.
You wouldn't need it in most cases though (for instance, Runnable is typically more suitable than Callable<Void>).
Ansering your question more specifically:
But if I remove the return null it does not compile?! Why?
... because a Void is still an object. However, it can only have value null.
If your method declares it returns Void, you need to (explicitly) return null.
If you check the sources:
package java.lang;
public final class Void {
public static final Class<Void> TYPE = Class.getPrimitiveClass("void");
private Void() {
}
}
Void is:
final class;
has private constructor.
Without using Reflection it's not possible to assign anything but null to a reference of Void type.
In Java, I can do this Void z = null; Is there any other value (but null) which I can assign to z ?
You can if you create you own Void instances. You can use Reflection or Unsafe to create these, not that it's a good idea.
But if I remove the return null it does not compile?! Why? After all, Void is supposed to mean just that - no return type.
Java is case sensitive, this means that Boolean and boolean are NOT the same type nor is Void and void. Void is a notional wrapper for void but otherwise is just a class you shouldn't create any instance of.
Maybe what you are asking for is Runnable or Consumer - some interface that doesn't have a return value. Void only serves to show that you cannot expect anything else than null. It is still just a class, not a keyword or anything special. A class that cannot be instantiated, so you have to return null.
A lot of efforts were spent in designing lambda expression to treat int/Integer etc indistinguishably, so that int->Long will be compatible with Integer->long, etc.
It is possible (and desirable) to treat void/Void in a similar way, see comments from Goetz and Forax.
However, they didn't have the time to implement the idea for java8 :(
You can introduce an adapter type that is both ()->void and ()->Void; it can simplify your use case a little bit, see http://bayou.io/release/0.9/javadoc/bayou/util/function/Callable_Void.html
If you have a method that accepts ()->Void, it is not going to work well with ()->void lambdas. One workaround is to overload the method to accept ()->void. For example, ExecutorService
submit(Callable<T> task)
submit(Runnable task)
...
submit( System::gc ); // ()->void
However, overloading with functional parameter types is tricky... The example above works because both accept a zero-arg function. If the function has non-zero args
foo( Function<String,Void> f ) // String->Void
foo( Consumer<String> f ) // String->void
it's confusing to the compiler (and the programmer)
foo( str->System.out.println(str) ); // which foo?
foo( System.out::println ); // which foo?
Given an implicit lambda str->expr, the compiler needs a target type to make sense of it. The target type here is given by the method parameter type. If the method is overloaded, we need to resolve method overloading first... which typically depends on the type of the argument (the lambda)... So you can see why it is complicated.
(A zero-arg lambda is never implicit. All argument types are known, since there's no argument.)
The lambda spec does have provisions to resolve the following cases
foo( str->{ System.out.println(str); } );
foo( str->{ System.out.println(str); return null; } );
You may argue that in the previous example,
foo( str->System.out.println(str) );
since println(str) returns void, the Void version obviously does not fit, therefore the compiler should be able to resolve it. However, remember that, to know the meaning of println(str), first, the type of str must be resolved, i.e. method overloading of foo must be resolved first...
Although in this case, str is unambiguously String. Unfortunately, the lambda designer decided against to be able to resolve that, arguing it is too complicated. This is a serious flaw, and it is why we cannot overload methods like in Comparator
comparing( T->U )
//comparing( T->int ) // overloading won't work well
comparingInt ( T->int ) // use a diff method name instead
I know I can do this:
void someMethod(){
return;
}
but I get a syntax error on
void someMethod(){
return void;
}
Why is the latter not allowed? It makes more sense to me.
Edit: I know what a void method is, and that I don't have to return from it at all(and probably shouldn't, in most cases) but I don't understand why I can't return void from a void method. In my opinion, there should be no keyword in the method declaration (like constructors) if the you are able to write return;.
I think both are to be shunned. I prefer this:
void someMethod() {
// do stuff; no return at bottom
}
I'd be willing to be that you'd find lots of methods in the JDK source code that look like this.
When you declare a method as void, you're saying that the method does not return a value. Attempting to return a value, therefore, is illegal. Additionally, return void; has a syntax error because void is not (indeed, cannot be) the name of an in-scope variable.
void is a type, not an expression, so trying to write return void is the same as trying to write return int: syntactically invalid.
When you call return void;, you are using a reserved keyword in the incorrect manner. Since it would not expect the keyword void in that manner, it would cause an error.
The Void class is an uninstantiable placeholder class to hold a
reference to the Class object representing the Java keyword void.
If you would prefer to return something, then you can return null; by parameterizing a type Void like in this answer, but that's unconventional. Best bet is to omit return altogether or just say return;.
return x; indicates that control is leaving the method and that its result is the value of x.
return; indicates that control is leaving the method without a result.
The type void is a type with zero values, so for void methods there is no x such that return x makes sense.
All non-void methods must do one of three things:
Fail to exit ever.
Finish abnormally with an exception.
Finish normally with zero or one return values.
Since void is the only type with zero possible values (Classes with private uncalled ctors don't count because of null), there is no possible return in a non-void method such that return makes sense.
I am writing a program for a programming game called robocode. The problem is here:
void wallScan(boolean While){
stop();
getStraight();
turnGunRight(90);
if(startabsolute){
straight=true;
}
while (While){
ahead(10000000);
turnRight(90);
}
resume();
}
You might not understand most of the code as it extends robocode.Robot, but my problem is in the variable While. The loop doesn't end as the method gets the argument once and it is true so the method becomes an eternal loop but is there a way to refresh the method argument as I don't want to make a while loop every time I call this method?
You shouldn't write you parameters in capital letters. So it would be while instead of While. However this isn't allowed because while is a keyword. So first change your argument passed in the method.
Then your problem is, that you call the method with the argument. Since it is a primitive boolean value you pass, the value can't be changed from another method, call, class, etc. during the execution of your wallScan method and therefore the while loop never finishes.
Instead you should for example create a member field in the class containing this method an give it a meaningful way. in the example i just call it whileCondition.
void wallScan(){
stop();
getStraight();
turnGunRight(90);
if(startabsolute){
straight=true;
}
while (whileCondition()){
ahead(10000000);
turnRight(90);
}
resume();
}
public void setWhileCondition(boolean bool) {
whileCondition = bool;
}
public boolean isWhileCondition() {
return whileCondition;
}
So you can set the condition which leads to the termination of the while loop from outside your method.
It seems to me that you don't want a single boolean value - you want something which will return you a boolean every time you ask for one. As a simple example:
public interface ContinueChecker {
boolean shouldContinue();
}
(Horrible names, but hopefully you can come up with something better.) You can then write:
void wallScan(ContinueChecker checker) {
...
while (checker.shouldContinue()) {
...
}
}
An alternative form of this would be a generic interface, such as Provider<T> one from Guice:
public interface Provider<T> {
T get();
}
Your method could take a Provider<Boolean> for the same purpose.
Personally I prefer this approach over that of Sebi - it allows your class to represent the state of the board itself (or whatever) - whether one particular robot should stop doesn't feel like it should be part of the same state. It's effectively local to this method, as far as I can see.