0

I have used List arrays in standards form before by simply adding int or strings but I am now looking into collections using the List method.

The code Im currently looking at implements the following class:

public class GeoNamesAsyncTask extends AsyncTask<String, Void, List<GeoName>> {

private Context ctx = null;

public GeoNamesAsyncTask(Context ctx) {
    this.ctx = ctx;
}

@Override
protected List<GeoName> doInBackground(String... arg0) {
    return new GeoNamesService().searchPostalCode(arg0[0]);
}

@Override
protected void onPostExecute(List<GeoName> result) {
    this.populateActivity(result);
}

The class this method is in extends the AsyncTask super class, and features a standard constructor setting the context from the class that calls it. up to this point I understand it.

Now when the overridden methods of the AsyncTask class of the 'doInBackGround' method I'm becoming a little lost.

I understand that the code is returning a List of (in the case of this code) place names that are run from the 'searchPostalCode' method of the GeoNameService class. The passed string is the user inputted post code. Can someone tell me why the three dots are passed with the string? I would of thought it would of simply been 'string arg0' not 'string... arg0'?

Once the doInBackGround method has returned, Am I right in thinking the 'onPostExecute' method is always calling directly after this?

Also I have read it is bad practice to call methods with a 'doInBackGround' method.

At the moment when I run this code, and try to enter a combination of letters and numbers i.e 'E4' I am getting an error within the doInBackGround method but integer numbers such as '24501' are fine, as shown.

02-21 20:05:18.461: E/AndroidRuntime(352): FATAL EXCEPTION: AsyncTask #1
02-21 20:05:18.461: E/AndroidRuntime(352): java.lang.RuntimeException: An error occured while executing doInBackground()
02-21 20:05:18.461: E/AndroidRuntime(352):  at android.os.AsyncTask$3.done(AsyncTask.java:200)
02-21 20:05:18.461: E/AndroidRuntime(352):  at java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:273)
02-21 20:05:18.461: E/AndroidRuntime(352):  at java.util.concurrent.FutureTask.setException(FutureTask.java:124)
02-21 20:05:18.461: E/AndroidRuntime(352):  at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:307)
02-21 20:05:18.461: E/AndroidRuntime(352):  at java.util.concurrent.FutureTask.run(FutureTask.java:137)
02-21 20:05:18.461: E/AndroidRuntime(352):  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1068)
02-21 20:05:18.461: E/AndroidRuntime(352):  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:561)
02-21 20:05:18.461: E/AndroidRuntime(352):  at java.lang.Thread.run(Thread.java:1096)
02-21 20:05:18.461: E/AndroidRuntime(352): Caused by: com.google.gson.JsonSyntaxException: java.lang.NumberFormatException: E4 6AA
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.TypeAdapters$7.read(TypeAdapters.java:232)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.TypeAdapters$7.read(TypeAdapters.java:222)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$1.read(ReflectiveTypeAdapterFactory.java:93)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$Adapter.read(ReflectiveTypeAdapterFactory.java:172)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.TypeAdapterRuntimeTypeWrapper.read(TypeAdapterRuntimeTypeWrapper.java:40)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.CollectionTypeAdapterFactory$Adapter.read(CollectionTypeAdapterFactory.java:81)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.CollectionTypeAdapterFactory$Adapter.read(CollectionTypeAdapterFactory.java:60)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$1.read(ReflectiveTypeAdapterFactory.java:93)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory$Adapter.read(ReflectiveTypeAdapterFactory.java:172)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.Gson.fromJson(Gson.java:795)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.Gson.fromJson(Gson.java:761)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.Gson.fromJson(Gson.java:710)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.Gson.fromJson(Gson.java:682)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.example.restfulweb.GeoNamesService$DataWrapper.fromJson(GeoNamesService.java:85)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.example.restfulweb.GeoNamesService.searchPostalCode(GeoNamesService.java:41)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.example.restfulweb.GeoNamesAsyncTask.doInBackground(GeoNamesAsyncTask.java:21)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.example.restfulweb.GeoNamesAsyncTask.doInBackground(GeoNamesAsyncTask.java:1)
02-21 20:05:18.461: E/AndroidRuntime(352):  at android.os.AsyncTask$2.call(AsyncTask.java:185)
02-21 20:05:18.461: E/AndroidRuntime(352):  at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305)
02-21 20:05:18.461: E/AndroidRuntime(352):  ... 4 more
02-21 20:05:18.461: E/AndroidRuntime(352): Caused by: java.lang.NumberFormatException: E4 6AA
02-21 20:05:18.461: E/AndroidRuntime(352):  at org.apache.harmony.luni.util.FloatingPointParser.initialParse(FloatingPointParser.java:130)
02-21 20:05:18.461: E/AndroidRuntime(352):  at org.apache.harmony.luni.util.FloatingPointParser.parseDouble(FloatingPointParser.java:281)
02-21 20:05:18.461: E/AndroidRuntime(352):  at java.lang.Double.parseDouble(Double.java:287)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.stream.JsonReader.nextInt(JsonReader.java:599)
02-21 20:05:18.461: E/AndroidRuntime(352):  at com.google.gson.internal.bind.TypeAdapters$7.read(TypeAdapters.java:230)
user1352057
  • 3,162
  • 9
  • 51
  • 117
  • Can you post your code for the GeoName object? This line is pointing to a GSON error, possibly with your annotations or how you're trying to map the data: 02-21 20:05:18.461: E/AndroidRuntime(352): Caused by: com.google.gson.JsonSyntaxException: java.lang.NumberFormatException: E4 6AA – Ben Jakuben Feb 21 '13 at 21:11
  • Also, yes, you don't call 'doInBackground()' directly. You want to call the 'execute()' method which handles all the other necessary calls for an AsyncTask. – Ben Jakuben Feb 21 '13 at 21:12

3 Answers3

0

Yeah, what you are doing with the AsyncTask looks correct.

Only the UI thread should modify the UI, and the doInBackground method isn't run in the UI thread. onPostExecute is.

Well, the stacktrace is self-explanatory, JSON is trying to parse you're "E4" as a number an fails to do so. Looks like you should only provide parsable numbers :)

Thibault D.
  • 10,041
  • 3
  • 25
  • 56
0

The passed string is the user inputted post code. Can someone tell me why the three dots are passed with the string? I would of thought it would of simply been 'string arg0' not 'string... arg0'?

They are called variable arity arguments and are provided so that the AsyncTask can be more flexible in terms of arguments. Acessing via arg0[0] is the correct way to access the provided args as long there are 1 or more arguments.

But if you had more than one, you could loop through them:

Eg:

for (String s: arg0)
{
  System.out.println (s);
}

Once the doInBackGround method has returned, Am I right in thinking the 'onPostExecute' method is always calling directly after this?

Yes, see the documentation:

onPostExecute(Result), invoked on the UI thread after the background computation finishes. The result of the background computation is passed to this step as a parameter.


Also I have read it is bad practice to call methods with a 'doInBackGround' method.

If that method modifies the UI Thread yes, it's bad.

At the moment when I run this code, and try to enter a combination of letters and numbers i.e 'E4' I am getting an error within the doInBackGround method but integer numbers such as '24501' are fine, as shown.

02-21 20:05:18.461: E/AndroidRuntime(352): Caused by: java.lang.NumberFormatException: E4 6AA

Based on the stack trace, JsonReader.nextInt() uses the underlying method Double.parseDouble() which doesn't work with letters.

Community
  • 1
  • 1
A--C
  • 36,351
  • 10
  • 106
  • 92
  • 1
    thanks very much that clears that up. I could see the the [0] looked to be some type of first array object and as im only passing one variable that makes perfect sense. The parse exception turned out to be a simple case of setting a field as a int when it should of been a String. – user1352057 Feb 21 '13 at 21:24
0
  1. 3 dots (...) are used for variable arguments also known as varargs. More here Java, 3 dots in parameters

  2. onPostExecute() is called after doInBackground() finishes its execution.

  3. You can call any method in doInBackground(), just be careful not to touch GUI.

  4. Somewhere in searchPostalCode() you are trying to parse E4 as a number that's why you are getting exception.

Community
  • 1
  • 1
M-Wajeeh
  • 17,204
  • 10
  • 66
  • 103