How to make a ThreadPool? - android

I am making a map app with OnClick marker creation. I am using simple AsyncTask class to get the street address of the LatLng i clicked so i can set a marker and save an Address object into list for future onMarkerClick intent, so i can display address into second activity, and of course database backup in onDestroy. Problem is that AsyncTask is an option when i create a marker and click on it. If i create 2-3-4 or more, they don't build up into a queue and i lose the first or all of them except the last one. I am reading now about ThreadPool and AsyncTask.THREAD_POOL_EXECUTOR but i really find this very difficult. Is it ok to ask for a simpler explanations or/and a code sample?
Stuff i know ATM:
AsyncTask is not an option cause it manages only a single background thread.
Thread is harder to implement but gives control to priority.
I need to create a new thread on every click or make a queue of tasks to get this done.
Geocoder class was an option but doesn't work for me.(bad formatting, random unavailability).

The Android developer documentation has the appropriate trainigs for Thread Pool. Using this, you can also communicate with the UI thread so you can (in your case) be able to manipulate/update markers and set listeners to it.

Related

Are there any thread restrictions on performing operations on the Here SDK Map object?

The way I understand the HERE Android SDK is that there's a MapView that has a backing Map object. Adding objects, setting the center, zooming etc should be performed on the Map object and this eventually reflects on the MapView.
Question:
Are there any restrictions on what thread the operations on the Map object must be performed? For example, must they all be called on the UI thread? Also, should multiple subsequent calls be synchronized?
I ask this because I want to make multiple changes in a Map (resize the map view, change some visible layers, change the scheme, add a MapRoute and zoom out to the bounding box of the route). When I try this, it sometimes works but sometimes doesn't. Sometimes, only some of the operations are applied. For example, everything works except the zoom is not applied.
I know there are some listeners that can help me:
Map.OnTransformListener - this I can use to let me know when a zooming operation has ended
Map.OnSchemeChangedListener - this I can use to know when a scheme change event has ended
What is not clear to me from the documentation is what other operations constitute a "transform"? Which of these operations must be performed in a synchronized fashion?
For example, is the following code expected to behave correctly?
map.setCenter(coordinate, Animation.BOW, 18, 0f, 60f);
map.addMapObject(routeObject);
map.setVisibleLayers(layersToShow, true);
map.setScheme(Map.Scheme.NORMAL_DAY)
Note that in the above example, I'm proceeding to make changes immediately after setCenter even before the animation is complete. Is this the expected way to use the API?
There is no restriction on what thread you call the API from. Internally, all calls are synchronized and thread safe.
What you are looking for is the MapView#executeSynchronized API. [link] This will batch up a few operations into one screen redraw. [At least when I wrote that API a few years ago]
What you are experiencing happens because the underlying rendering thread started drawing some of the commands from the calling thread. This caused subsequent calls to lose effect.

What is the best way to use threading on a sorting algorithm, that when completed, creates a new activity and gives its data to the new activity?

I will start this by saying that on iOS this algorithm takes, on average, <2 seconds to complete and given a simpler, more specific input that is the same between how I test it on iOS vs. Android it takes 0.09 seconds and 2.5 seconds respectively, and the Android version simply quits on me, no idea if that would be significantly longer. (The test data gives the sorting algorithm a relatively simple task)
More specifically, I have a HashMap (Using an NSMutableDictionary on iOS) that maps a unique key(Its a string of only integers called its course. For example: "12345") used to get specific sections under a course title. The hash map knows what course a specific section falls under because each section has a value "Course". Once they are retrieved these section objects are compared, to see if they can fit into a schedule together based on user input and their "timeBegin", "timeEnd", and "days" values.
For Example: If I asked for schedules with only the Course ABC1234(There are 50 different time slots or "sections" under that course title) and DEF5678(50 sections) it will iterate through the Hashmap to find every section that falls under those two courses. Then it will sort them into schedules of two classes each(one ABC1234 and one DEF5678) If no two courses have a conflict then a total of 2500(50*50) schedules are possible.
These "schedules" (Stored in ArrayLists since the number of user inputs varies from 1-8 and possible number of results varies from 1-100,000. The group of all schedules is a double ArrayList that looks like this ArrayList>. On iOS I use NSMutableArray) are then fed into the intent that is the next Activity. This Activity (Fragment techincally?) will be a pager that allows the user to scroll through the different combinations.
I copied the method of search and sort exactly as it is in iOS(This may not be the right thing to do since the languages and data structures may be fundamentally different) and it works correctly with small output but when it gets too large it can't handle it.
So is multithreading the answer? Should I use something other than a HashMap? Something other than ArrayLists? I only assume multithreading because the errors indicate that too much is being done on the main thread. I've also read that there is a limit to the size of data passed using Intents but I have no idea.
If I was unclear on anything feel free to ask for clarification. Also, I've been doing Android for ~2 weeks so I may completely off track but hopefully not, this is a fully functional and complete app in the iTunes Store already so I don't think I'm that far off. Thanks!
1) I think you should go with AsynTask of Android .The way it handle the View into `UI
threadandBackground threadfor operations (Like Sorting` ) is sufficient enough to help
you to get the Data Processed into Background thread And on Processing you can get the
Content on UI Thread.
Follow This ShorHand Example for This:
Example to Use Asyntask
2) Example(How to Proceed):
a) define your view into onPreExecute()
b) Do your Background Operation into doInBackground()
c) Get the Result into onPostExceute() and call the content for New Activty
Hope this could help...
I think it's better for you to use TreeMap instead of HashMap, which sorts data automatically everytime you mutate it. Therefore you won't have to sort your data before start another activity, you just pass it and that's all.
Also for using it you have to implement Comparable interface in your class which represents value of Map.
You can also read about TreeMap class there:
http://docs.oracle.com/javase/7/docs/api/java/util/TreeMap.html

Best practice to use AsyncTask in autocomplete?

I am using Async task to populate auto-complete suggestions from server.
Problem:
when user types and removes the text in edittext so many times.
lets say he typed: cofee > cof > coffee >coffee late .... etc for so many times.
for each text changed after 3 keyword(threshold) i am initializing an asynctask and ask for result.
so in current scenario i have so many threads running in background. so some of my latest async threads are waiting for there chance.
Whole this make my app very slow.
What can I do to tackle this problem?
If it is possible to load entire data from server at beginning...then you can avoid calling asynctask repeatedly and fetching the data from server. This will improve performance of you app. If data displayed in Listview is String, following link show how to filter it:
http://www.androidhive.info/2012/09/android-adding-search-functionality-to-listview/
And if custom object is used in ListView adapter, try:
Filtering ListView with custom (object) adapter
Hopefully this helps.
You should cancel the current task before issuing a new one. Use AsyncTask#cancel(true) for that and make sure that the execution of the task can be quickly stopped. This means correct handling of interruption and frequent checking whether the task was cancelled in the body of AsyncTask#doInBackground.
And you cannot execute again the AsyncTask you have cancelled. You have to create a new one. (Trying to execute it again leads to IllegalStateExceptions)
It worked for me by cancelling the task each time you change the text (if it is still running).
You need to define your request once outside the listener(private for the class), and then start your listener function by (if your request is not finished, then cancel it).
define your request out side the function
private YourSearchTaskClass YourTaskReq = new YourSearchTaskClass();
then start your addTextChangeListener/afterTextChanged by this
if (YourTaskReq.getStatus()!= AsyncTask.Status.FINISHED)
YourTaskAvReq.cancel(false);
YourTaskReq= new YourSearchTaskClass(keyword);

Best way to get lat and long from gps and sending to a server to get data back using expandable list view android

what is the best way to design an expandable list view, the details for the list view will come from server after the device sends the latitude and longitude to the server.
I am early learner on AsyncTask, as User Interface might freeze when getting lat,long and sending the same to the server and getting back branch details. Some example, pointers would be helpful.
Looking forward to reply.
thanks.
See this link for usage of AsyncTask:
http://geekjamboree.wordpress.com/2011/11/22/asynctask-call-web-services-in-android/
Basically, once you get the AsyncTask going all you need to do is to populate the ExpandableListAdapter with your data and call notifyDataChanged on the adapter. That should populate the list with your items. There's plenty of tutorials available on how to write a custom ExpandableListAdapter should you need one. Just use Google to find the item.
Since you've mentioned AsynTask, once you get the coordinates (in OnLocationChanged() execute the instance of AsyncTask, this means the listview will be repopulated every time there is update in your location) send the coordinates in doInBackground() method and when you are done with the getting/sending in the onPostExecute() method try to populate the expandable listview with the data from the server.

What's the best way to save and restore a MapView in Android?

I have a MapActivity that contains a MapView with some custom controls, state information, and an ItemizedOverlay composed by some locations that I draw using the default approach (using populate(), super.draw() and createItem()) and by some lines that I draw in the overrided draw() method.
So, when the activity is paused, I have to save:
Some state information
The ItemizedOverlay
[Maybe more Overlays in the future.]
I'm saving the state information as usual, putting them in the bundle. I'm thinking in doing the same with the Overlays, implementing Parcelablein each one of the OverlayItems and so, but I don't know if there is a better way to store the complete state of the MapViews.
The information depends on remote requests that I don't want to repeat each time the activity is paused.
Any recommendation?
If all information regarding OverlayItems is obtained from remote request, the most simple solution would be to store last request output in a file.
On activity restart, you check if the cashed request output is available (and perhaps is still valid for your needs) and than use the existing methods to extract data from it.
For example, if you get POI's from remote KML or JSON, you can use the existing parser to extract data from local file as well.
As general solution onRetainNonConfigurationInstance() and getLastNonConfigurationInstance() with the complete Activity or with an array with the Objects of interest can be used. Then in onCreate() the View can be regenerated.

Categories

Resources