Reputation: 681
Initially i set myself a simple task to make a function to execute with delay. At first i made a runnable and executed it with new Thread(runnable).start();
, but i've read, that non-static inner classes can lead to memory leaks, so i tried to make Runnable
as static.
I followed example in Is this Runnable safe from memory leak? and ended with this code:
public class ApproxManager {
private Context mContext;
private AlarmManager mAlarmManager;
public ApproxManager(Context context){
mContext = context;
mAlarmManager = (AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
}
public void setPeriod(int type, long when, int extendCount){
Intent i = new Intent(mContext, OnAlarmReceiver.class);
long alarmtime = when;
i.putExtra(RReminder.PERIOD_TYPE, type);
i.putExtra(RReminder.EXTEND_COUNT, extendCount);
i.setAction(RReminder.CUSTOM_INTENT_APPROXIMATE_PERIOD_END);
PendingIntent pi = PendingIntent.getBroadcast(mContext, 0, i, PendingIntent.FLAG_CANCEL_CURRENT);
new Thread(new WeakRunnable(mContext, alarmtime,pi)).start();
}
public void setAlarm(long alarmTime, PendingIntent pi){
mAlarmManager.set(AlarmManager.RTC_WAKEUP, alarmTime, pi);
}
private static final class WeakRunnable implements Runnable {
private final WeakReference<Context> mContext;
long mAlarmtime;
PendingIntent mpi;
protected WeakRunnable(Context context, long alarmtime, PendingIntent pi){
mContext = new WeakReference<Context>(context);
mAlarmtime = alarmtime;
mpi = pi;
}
@Override
public void run() {
Context context = mContext.get();
if (context != null) {
try {
Thread.sleep(1500);
} catch (InterruptedException e) {
e.printStackTrace();
}
ApproxManager approxManager = new ApproxManager(context);
approxManager.setAlarm(mAlarmtime,mpi);
}
}
}
}
I am unfamiliar with inner classes and referencing, so despite my code appears to be working, i am not sure, if i have suceeded with my goal to avoid memory leaks. So i would appreciate if someone could look at my code.
Upvotes: 0
Views: 313
Reputation: 7772
Your code looks fine IMHO. I think you have managed to successfully implement you runnable and protect yourself against a memory leak.
Non - static inner classes hold a implicit reference to the instance that created them. This means that, if you go with the non - static approach, you will be keeping a reference to a ApproxManager
instance and this instance will not be garbage collected. The ApproxManager
keeps a reference to the Context
and AlarmManager
instances and they won't be garbage collected neither and this is you memory leak.
Static inner classes don't hold any implicit references, but they can't access non - static members, so you are forced to provide all the needed dependencies so the class can do it's work. Using WeakReference
you won't prevent eventual garbage collection of the variable, if there is need for one.
Upvotes: 2