繁体   English   中英

无法在AsyncTask中将Object []强制转换为Void []

[英]Object[] cannot be cast to Void[] in AsyncTask

我在扩展asynctask中遇到此错误,但我确实确定Object []是Void []。

这是我自定义的AsyncTask:

public abstract class RepeatableAsyncTask<A, B, C> extends AsyncTask<A, B, C> {
private static final String TAG = "RepeatableAsyncTask";
public static final int DEFAULT_MAX_RETRY = 5;

private int mMaxRetries = DEFAULT_MAX_RETRY;
private Exception mException = null;

/**
 * Default constructor
 */
public RepeatableAsyncTask() {
    super();
}

/**
 * Constructs an AsyncTask that will repeate itself for max Retries
 * @param retries Max Retries.
 */
public RepeatableAsyncTask(int retries) {
    super();
    mMaxRetries = retries;
}

/**
 * Will be repeated for max retries while the result is null or an exception is thrown.
 * @param inputs Same as AsyncTask's
 * @return Same as AsyncTask's
 */
protected abstract C repeatInBackground(A...inputs);

@Override
protected final C doInBackground(A...inputs) {
    int tries = 0;
    C result = null;

    /* This is the main loop, repeatInBackground will be repeated until result will not be null */
    while(tries++ < mMaxRetries && result == null) {
        try {
            result = repeatInBackground(inputs);
        } catch (Exception exception) {
            /* You might want to log the exception everytime, do it here. */
            mException = exception;
        }
    }
    return result;
}

/**
 * Like onPostExecute but will return an eventual Exception
 * @param c Result same as AsyncTask
 * @param exception Exception thrown in the loop, even if the result is not null.
 */
protected abstract void onPostExecute(C c, Exception exception);

@Override
protected final void onPostExecute(C c) {
    super.onPostExecute(c);
    onPostExecute(c, mException);
}

这是产生问题的子类:

public class ListPalinasAsynkTask extends RepeatableAsyncTask<Void, Void, List<Palina>>{
    private static final String TAG = "ListPalinasAsynkTask";
    private static final boolean D = SystemConstants.ACTIVE_DEBUG;

    private ApiRequest.ListPalinasCallback mCallback;

    public ListPalinasAsynkTask(ApiRequest.ListPalinasCallback callback) {
        if(D) Log.d(TAG, "Called: ListPalinasAsynkTask([callback])");
        mCallback = callback;
    }

    @Override
    protected List<Palina> repeatInBackground(Void... voids) {
        /* Here i send request to get palinas */
        return Api.getPalinasNearMe();
    }

    @Override
    protected void onPostExecute(List<Palina> palinas, Exception exception) {
        if(exception != null)
            Logging.e(TAG, "Received exception in Asynk Task", exception);
        if(palinas != null)
            mCallback.result(palinas);
        else
            mCallback.result(new ArrayList<Palina>());
    }
}

最后,这是错误:

E/ListPalinasAsynkTask﹕ Received exception in Asynk Task
    java.lang.ClassCastException: java.lang.Object[] cannot be cast to java.lang.Void[]
            at ListPalinasAsynkTask.repeatInBackground(ListPalinasAsynkTask.java:19)
            at RepeatableAsyncTask.doInBackground(RepeatableAsyncTask.java:43)
            at android.os.AsyncTask$2.call(AsyncTask.java:288)

我无法解释此异常,因为我将Void作为参数! 那不应该是一个对象。 你有解决方案吗?

编辑 :ListPalinasAsyncTask.java:19是指:

public class ListPalinasAsynkTask extends RepeatableAsyncTask<Void, Void, List<Palina>> {

RepeatableAsyncTask.java:43:

result = repeatInBackground(inputs);

编辑2:

我这样调用执行:

AsyncTask mAsyncTask = new ListPalinasAsynkTask(callback);
....
mAsyncTask.execute();

找到解决方案:

问题是这样的:

AsyncTask mAsyncTask = new ListPalinasAsynkTask(callback);
....
mAsyncTask.execute();

我正在使用通用的AsyncTask调用execute,该类将通过Void作为参数,并且永远不会在ListPalinasAsynkTask上调用.execute(),而是将调用ListPalinasAsynkTask.execute(Void)。 那给出了错误。

解决方案:

  1. 使用ListPalinasAsynkTask而不是通用的AsyncTask
  2. 更好的方法:创建一个新的类VoidRepeatableAsyncTask,并使其他Void AsyncTasks扩展该类。

像这样:

public abstract class VoidRepeatableAsyncTask<T> extends RepeatableAsyncTask<Void, Void, T> {
    public void execute() {
        super.execute();
    }
}

然后,您可以轻松地使用如下代码来调用execute:

VoidRepeatableAsyncTask mAsyncTask = new ListPalinasAsynkTask(callback);
....
mAsyncTask.execute();

这将调用AsyncTask的无参数execute方法。

我解决此问题的另一种方法是即使在不使用参数的情况下,也可以在参数中传递Object

new AsyncTask<Object, Void, MergeAdapter>()

和覆盖:

@Override
protected ReturnClass doInBackground(Object... params) {
    //...
}

如果您想将不同类型的AsyncTasks传递给方法,则上述情况适用(以我为例),当然您并不关心参数。

我认为解决方案要简单得多。 只需以这种方式创建子类对象:

AsyncTask<Void, Void, List<Palina> mAsyncTask = new ListPalinasAsynkTask(callback);
....
mAsyncTask.execute();

尝试使用:

result = repeatInBackground((Void) inputs);

代替

result = repeatInBackground(inputs);

如果发生此问题,则您可能已经创建了派生类对象并添加了其基类变量(AsyncTask)。 因此发生此错误。
AsyncTask mAsyncTask = new ListPalinasAsynkTask(callback);

当您喜欢这样的“执行未检查的调用。参数...”时,棉绒也会发出警告。

解决方案是ListPalinasAsynkTask mAsyncTask = new ListPalinasAsynkTask(callback); 然后调用执行。 会很好的

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM