Refresh Java argument - java

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.

Related

Java Void Methods Return

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?

Passing and setting booleans - Java/Android

I have a class like so:
public class Achievements(){
boolean score100_Earned_Offline;
boolean score1000_Earned_Offline;
final String score100 = "xxxxxxxxxx" //where xxxxxxxxxx would be replaced with the achievement's Google Play Games ID
final String score1000 = "xxxxxxxxxx" //where xxxxxxxxxx would be replaced with the achievement's Google Play Games ID
}
In my Game class, I check the state of the achievements every tick and act on them as necessary like so (assume all methods to be valid and defined - this is cut down to provide the code necessary to the question).......
public class Game(){
public void checkAchievements(Achievements achievements){
if (score>=100){
unlockAchievement(achievements.score100, achievements.score100_Earned_Offline);
}
if (score>1000){
unlockAchievement(achievements.score100, achievements.score1000_Earned_Offline);
}
}
public void unlockAchievement(String achievementToUnlock, boolean thisAchievementOfflineFlag){
//If user is signed in, then we are ready to go, so go ahead and unlock the relevant achievement....
if (checkSignedIn()){
Games.Achievements.unlock(getApiClient(), achievementToUnlock);
//Otherwise, I want to do is set the relevant flag to true so it can be checked when the user does eventually log in
else{
thisAchievementOfflineFlag=true;
}
}
}
Pass by value
In the 'unlockAchievement' method, the boolean 'thisAchievementOfflineFlag' does get set to true if the user is not logged in, however, it doesn't effect the actual boolean that was originally sent into the method (which as you can see is defined in my 'Achievements' class). I'm guessing this is because Java is Pass by Value and is therefore, creating a local copy of the variable which is valid inside the method only. I did try using Boolean too (wrapper class) but got the same results.
Other ways to achieve this?
I've currently got it set up so I can define each achievement as an enum so each one will have it's own copy of the boolean flag. However, I'm aware that it's not recommended to use enums in Android so if there is a better way that I am missing, I would rather avoid them.
Please note that I don't want to use if checks or switch statements as this is taking place in a game-loop.
Any suggestions appreciated
This is all because Java's implementation of Boolean (also, for example String) is immutable for safety reasons. You can see it here: http://www.explain-java.com/is-string-mutable-in-java-why-wrapper-classes-immutable-in-java/
You can solve your problem by introducing an object wrapper for that boolean:
public class BooleanWrapper {
private boolean value;
public void set(boolean value) {
this.value = value;
}
public boolean get() {
return value;
}
}
Now, this object reference will be passed by value but will still point to the same BooleanWrapper object on the heap. You can simply use getters and setters to change the inner boolean value.
Then your code would become:
public void unlockAchievement(String achievementToUnlock, BooleanWrapper thisAchievementOfflineFlag){
if (checkSignedIn()){
Games.Achievements.unlock(getApiClient(), achievementToUnlock);
else {
thisAchievementOfflineFlag.set(true);
}
}
Java is pass-by-value:
When you pass boolean then you for sure passed it by value, while it is a primitive type. When you pass Boolean, you would think it's an object and that you can change it's state, but actually you cannot because Boolean is implemented as an immutable object (as already said). You can confirm this just by reading the code of java.lang.Boolean.
But if you create your own wrapper class, and in a sense, you control whether you implement it in immutable or mutable way. BooleanWrapper I wrote lets you change the state of that object. And when you pass an object such as this one to the method, it's passed by value. That means that another reference is created, but it points to the same object on heap (see image below).
You could use an AtomicBoolean, which will have pass-by-reference semantics.

API design - Is it a good practice to dictate method order?

public abstract class A {
private int result=-1;
public void final doExecuteMySpecialAlgorithm() {
result=0;
//do something here and get a new result
//it won't be -1.
}
public int getResult() {
if(result==-1)
throw new RuntimeException("Invoke my special algorithm first!");
return result;
}
}
Isn't getResult method a bad design - It is forcing user to invoke another method before it is invoked? How would you workaround this? Would your rather return -1 or say null (in case of an object type) and let the caller figure out what to do will a null return? or if you are sure that it won't be null, but for the return to be not null, you would have to invoke another method before invoking getResult method, would you just throw a RuntimeException? (or a checked exception?)
There's two ways here. Either make it synchronous (i.e. doExecuteMySpecialAlgorithm actually returns the result) or asynchronous.
The first is obvious, the second can be accomplished by returning a Future object for example. Either way, the caller doesn't need to think which is the proper order to call methods.
In some cases it may be alright to enforce the calling order of methods (such as the doFinal method in crypto classes), but you should still avoid making the code in a way that the user has to think carefully about how he's going to call your methods. Obviously he needs to know what to call, but if he needs to call 5 methods in a specific order, it probably means there should be only 1 method.
I mean after all, if you want to force the caller to call method1(), method2(), method3() in order, you should really make him call method(), which inside calls private methods method1(), method2() and method3(). That way you have the code well structured, but the caller can't fudge things up by calling the methods in the wrong order.
In your example I'd do the following:
public abstract class A {
private int result=-1;
public void final doExecuteMySpecialAlgorithm() {
result=0;
//do something here and get a new result
//it won't be -1.
}
public int getResult() {
if(result==-1)
doExecuteMySpecialAlgorithm();
return result;
}
}
This way a user can do the 'special' algorithm first, or if they 'forget' to, you (as the API writer) catch it for them and do this (instead of throwing an error).
Doing this makes your object do the work for you (object oriented design), of course this is YOUR API design, and I would assume that there would be extensive documentation dictating that if I call getResult that I must first call doExecuteMySpecialAlgorithm ... whatever you choose to implement YOU must document that the user is ordered to call function X before function Y or undefined behavior might result (or throw an error).

return void in a void method?

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.

How to change the value of a boolean var inside a method?

This is maybe so silly.
I have a boolean variable inside the main method. By calling another method of this class or another class I want my boolean value to be modified in the main method. I do this but the change happens only in the called method(locally), not the caller(main). I think this is because of the pass-by-value feature of java.
I even tried Boolean type, but the same problem there!
Actually I'll use this to manage the ordering of concurrent threads. The main processor will check for the boolean value of every thread to see if it is ok to continue and tick the clock. After ticking the clock the main will make the vars false and will wait until the vars are again true. the sub-threads will start their task if the boolean value of them each is false. After the task is done they will make the vars to true so the main processor is able to tick again.
So I want something without a return. I mean as the value is changed inside the method the main could see it.
boolean var = true;
var = methodWhichReturnsTheNewValueOfTheVariable();
and inside the called method:
return newBooleanValue;
or
SomeObjectWithBooleanVariableInside var = new SomeObjectWithBooleanVariableInside(true);
methodWhichModifiesTheObject(var);
and inside the called method:
var.setBooleanValue(newBooleanValue);
A Boolean is such an object: it contains a boolean value. But it's intentionally designed as immutable: its wrapped boolean value can't be changed. So you need to create your own, functional object.
The usual way to do this is the following:
public static void main(String[] args) {
boolean myVar = true;
...
...
myVar = myFunction();
}
public static boolean myFunction() {
// the method should do it's calculation and return the value:
return false;
}
Yes - you cannot modify passed-by-value parameter inside a method in Java (for example in C# you would write method(ref param)).
Why can't you return this value using the method:
public boolean method(params...) {...}
Or you can pass in param the reference to caller:
public void method(params..., CallerClass caller) {
//do something
caller.setValue(Boolean.FALSE);
}
Or you can make this variable accessible in caller and calling method scopes - static variable, etc.
Primitive types are passed by value, so you can't change variables coming as parameter in a method.
This makes also easier to understand how a program works, since this kind of behavior is made more evident in an invocation like this:
boolean prime = false;
prime = isPrime(number);
you can see that found variable is reassigned; while you can assume that number will remain unchanged. This helps in code readability.
There is a dirty trick that sometime can be used. Since arrays are objects, you can use an array to wrap a primitive type:
boolean[] prime = { false };
isPrime(number, result);
public void isPrime(int number, boolean[] result) {
result[0] = true;
}
The object reference is passed by value too, but here we change the content of the array, not the array reference.
This works. But, I don't recommend to design your code like this.
Sometimes, knowing this trick can be useful in unit tests though.
when you think that you changed the value of the primitive boolean it only changed the value in the scope of that method. same with Boolean as it is immutable. changing its value actually assigned a new value to it inside the scope of that method.
you should return the new value from that method and then assign it or you could also use a global boolean that is known to all and to change that one.
(and by the way, if you're dealing with concurrency check out AtomicBoolean)

Categories