问题
I use the code below for getting some work done everytime after some time interval, and using post delay in 'finally' clause and oustide of runnable. Here is the code.
Runnable runnable = new Runnable() {
@Override
public void run() {
try {
// do somthing
} catch (Exception e) {
// TODO: handle exception
} finally {
handler.postDelayed(this, 60000);
}
}
};
handler.postDelayed(runnable, 60000);
handler.postDelayed(runnable, 60000);
will run two times or a single time.
回答1:
it depends!
- first matter
how the each try / catch / finally block completes normally or abruptly?
the finally block "always ^" executes when the try block exits
This ensures that the finally block is executed even if an unexpected exception occurs.
^ exception from above - finally may not be executed if jvm exits or thread gets killed
for details see java specs:
https://docs.oracle.com/javase/specs/jls/se7/html/jls-14.html#jls-14.20.2
- second matter
how Handler post/postDelayed method executes will pass? or fails? for some reason - for second this may happen if message was not placed in to the message queue - on failure, usually because the looper processing the message queue is exiting.
but most likely your statement will make a INFINITE loop
** ps. you need to throw an exception in try block or remove catch block (as try{} finally{} ) can exist "without" catch but code in catch block without rising any exception will make a compiler complain (code will not compile)
if you want loop n-times+1 you need to add some condition before postDelayed in Runnable run() method
in your case code flow execution:
- postDelayed method from last line outside definition of runnable
- execution of runnable by:
- start of try block
- with or without passing catch
- through finally block with postDelayed in runnable run() method - wich will place runnable in message que for delayed execution on main thread
- then infinite loop on 2
so should i remove last postDelay out side of run() method to achieve postDelay run only ones in one loop. – AndroidMob
you can write this in such way:
final Handler handler = new Handler();
handler.post(new Runnable() {
// this int will also be passed to method post delayed
// as "this" keyword applies to Anonymous Class
// which body contains everything between brackets of new Runnable() { ... }
int withThis = 1;
@Override
public void run() {
handler.postDelayed(this,1000);
}
});
so where should i call method to get done somthing ? in run() method..? – AndroidMob
this also depends what you want to achieve:
example
handler.post(new Runnable() {
int counter = 0;
@Override
public void run() {
boolean wasPlacedInQue = false;
doPreMethod();
if(counter =< 10) {
doMethod();
wasPlacedInQue = handler.postDelayed(this,1000);
}
if(wasPlacedInQue) {
counter++;
doPostyMethod();
} else doFailureMethod();
}
the code in run() method is executed synchronously on so called UI Thread - i'ts main thread which executes your application see:
https://developer.android.com/training/multiple-threads/communicate-ui.html
if you are interested to study it more I have made a full working example for you:
https://gist.github.com/c3ph3us/7d237d540e60597369856cb1fa652a23
回答2:
it surely will run two times. Because they are two different messages and handler will handle them separately.
来源:https://stackoverflow.com/questions/37957863/what-will-happen-if-i-use-try-catch-and-finally-for-handler-using-runnable