1

I read a lot about AsyncTask while trying to make it work with my ListFragment. Now I came across a few articles saying it must be static for technical reasons. Other articles say it doesn't matter as for my case it I couldn't make the right syntax for static so I made my class non-static. If it is recommended to make it static please helping me changing it.

my class :

private class MyAsyncTask extends AsyncTask<List<String>, Void, List<String>>
{
    // List of messages of the rss feed
    private List<Message> messages;
    private WeakReference<NieuwsSectionFragment> fragmentWeakRef;

    private MyAsyncTask(NieuwsSectionFragment fragment)
    {
        this.fragmentWeakRef = new WeakReference<NieuwsSectionFragment>(fragment);
    }
    @Override
    protected void onPreExecute() 
    {
        super.onPreExecute();
       //  progress.setVisibility(View.VISIBLE); //<< set here
    }
    @Override
    protected List<String> doInBackground(List<String>... urls)
    {
        FeedParser parser = FeedParserFactory.getParser();
        messages = parser.parse();
        List<String> titles = new ArrayList<String>(messages.size());
        for (Message msg : messages)
        {
            titles.add(msg.getTitle());
            // Log.w("doInBackground", msg.getTitle());
        }
        return titles;
    }

    @Override
    protected void onPostExecute(List<String> result)
    {
        super.onPostExecute(result);
        if (result != null)
        {
            PostData data = null;
            listData = new PostData[result.size()];
            for (int i = 0; i < result.size(); i++)
            {
                data = new PostData();                  
                data.postTitle = result.get(i);
                listData[i] = data;
                Log.w("onPostExecute", "" + listData[i].postTitle);
            }
            Log.w("onPostExecute", "" + adapter);
            adapter = new PostItemAdapter (getActivity(), android.R.layout.simple_list_item_1, listData);
            setListAdapter(adapter);
            adapter.notifyDataSetChanged();
        }
    }
}

When I make it static it gives errors on the adapter. It says something about setListAdapter and getActivity().

Shishi
  • 601
  • 2
  • 8
  • 27
  • is asynctask an inner class of the activity? – Raghunandan Feb 07 '14 at 09:28
  • no it is a inner class of a ListFragment – Shishi Feb 07 '14 at 09:29
  • http://android-developers.blogspot.in/2009/01/avoiding-memory-leaks.html. scroll down and check the points and do read http://stackoverflow.com/questions/3106912/why-does-android-prefer-static-classes – Raghunandan Feb 07 '14 at 09:30
  • 4
    **"Now I came across a few articles saying it must be static for technical reasons."** - Which articles? I can't think of a good reason for making an `AsyncTask` static and I've written plenty of code which uses `AsyncTasks`. – Squonk Feb 07 '14 at 09:32
  • This is the latest I read but not the only one : http://www.michenux.net/android-asynctask-best-pratices-540.html – Shishi Feb 07 '14 at 09:35
  • You've misinterpreted the article. Using static is a design choice, not a technical limitation. To make an asynctask static in an `Activity` would be a big mistake so the author has moved it to it's own class and made it static. To the asynctask, it does not know or care whether it is static or not. – Simon Feb 07 '14 at 09:41
  • Okay I understand it a bit I should learn some more about performance thanks for the information – Shishi Feb 07 '14 at 09:46
  • Further to what @Simon says above, the article is actually inaccurate. "AsyncTask can not be coded as instance inner class (non-static)......So, it is not possible to relink an instance of an async task to the new instance of the activity (on rotation)." - Yes it can, and it is possible for it to cope with orientation changes but you need to do some extra coding to get it to work. – Squonk Feb 07 '14 at 10:03

1 Answers1

1

Please read:

Is AsyncTask really conceptually flawed or am I just missing something?

An instance of a non-static inner class indeed contains a reference to the enclosing instance of the containing class; if the containing class is an activity, neither the activity nor the referenced views can be freed before the task dies.

OTOH, if you pass an explicit reference to the activity (e.g. as a listener), this will not be any better.

My advice is to remember that from the MVC (Model-View-Controller) viewpoint an Activity is a Controller, while the async operation is most likely belongs to the Model, along with the data that must survive events like changing the screen orientation. (And View is the view hierarchy defined via xml, you can create your own view classes, but typically you just reuse the existing ones.)

That is, do not place the application logic into an Activity, create a special class for that.

Community
  • 1
  • 1
18446744073709551615
  • 16,368
  • 4
  • 94
  • 127