doInBackground 没有 运行 在 Activity onCreate 里面

doInBackground does not run inside Activity onCreate

我有: 我有一个 SearchActivity,它从片段(单击按钮后)接收 ArrayList (NameDesSearch) 并更新一个简单的 列表视图。当我单击列表视图项时,所单击列表项的相应对象 (orgDesObj) 会出现一个新视图。此功能运行良好。

当前接收列表 (NameDesSearch) 包含名称和描述。都是字符串。

但是,我只想显示列表名称。因此我尝试创建一个函数 (titlefunc())。 这里创建了一个新的 ArrayList ( NameDesTitles ) 以仅添加相关名称。

问题: 但是,当我调用 titlefunc() 时,Do In 后台函数似乎无法正常工作。

尝试次数: 我放了几个Log来捕捉点。 我也在单击项目的列表视图中使用相同的函数 (getLocDesOb())。 令人惊讶的是它有效,甚至 doInBackground 函数也有效。 但是当搜索 activity 创建并调用 titlefunc() 时,doInBackground 中的搜索列表 (finalODescriptionArrayList) 为空()。 从日志中,我收到 finalODescriptionArrayList 的内容为 [],大小为 0。 但是,当我单击列表视图项时 finalODescriptionArrayList 更新。

我什至尝试将 NameDesSearch = getIntent().getStringArrayListExtra("searched"); 移到函数之外。

似乎我的 doInBackground 方法仅在单击列表项而不是 activity 创建时调用。其他所有功能都运行良好。我不确定我的 titlefunc() 何时被调用,为什么 finalODescriptionArrayList 不更新。

如果有任何建议,我将不胜感激。谢谢!

我的代码:为了清楚起见,我删除了日志。

public class SearchActivity extends AppCompatActivity {

    ListView searchedListView;
    String SearchedWord;
    private ArrayAdapter<String> orgAdapter;
    ArrayList<String> NameDesSearch = new ArrayList<String>();
    ArrayList<String> NameDesTitles = new ArrayList<String>();
    private OService OService;
    ArrayList<ODescription> finalODescriptionArrayList = new ArrayList<ODescription>();

    @RequiresApi(api = Build.VERSION_CODES.N)
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_search);
        searchedListView = (ListView) findViewById(R.id.searched_list_view);
        new GetCourse().execute();

        titlefunc();

        ArrayAdapter<String> arrayAdapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, NameDesTitles);
        searchedListView.setAdapter(arrayAdapter);

        searchedListView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
                String selectedItemText = parent.getItemAtPosition(position).toString();
                ODescription orgDesObj = getLocDesOb(selectedItemText);
                if (orgDesObj != null) {

                    Intent intent = new Intent(SearchActivity.this, View.class);
                    intent.putExtra("sOb", orgDesObj);
                    startActivity(intent);
                }
            }
        });
    }

    @SuppressLint("StaticFieldLeak")
    private class GetCourse extends AsyncTask<Void, Void, Void> {

        @TargetApi(Build.VERSION_CODES.N)
        @Override
        protected Void doInBackground(Void... voids) {
            try {
                finalODescriptionArrayList = JsontoObject.jsonToObjectData(getResources().openRawResource(R.raw.newdb));

            } catch (IOException e) {
                e.printStackTrace();
            }
            return null;
        }
    }

    public ODescription getLocDesOb(String selectedItemText) {

        if (finalODescriptionArrayList == null) {
            return null;
        }
        for (ODescription locDescObj : finalODescriptionArrayList) {
            if (locDescObj.getName().equals(selectedItemText) || locDescObj.getDescription().equals(selectedItemText)) {
                return locDescObj;
            }
        }
        return null;
    }

    public void titlefunc() {
        NameDesSearch = getIntent().getStringArrayListExtra("searched");
        for (String searchNameDes : NameDesSearch) {
            ODescription orgDesObj2 = getLocDesOb(searchNameDes);
            if (orgDesObj2 != null) {

                NameDesTitles.add(orgDesObj2.getName());
            }
        }
    }
}

以下回答后的尝试次数 使用 onPostExecute 更新 AsyncTask。然后由于需要一点时间,进度条添加了onPreExecute已删除 oncreate 方法中的 titlefunc()

此方法现在有效。但是,有时存在相同的问题。适配器的数组列表为空,因此列表视图为空。后台任务好像还是要花很多时间。

已更新 AsyncTask

    @SuppressLint("StaticFieldLeak")
    private class GetCourse extends AsyncTask<Void, Void, Void> {
ProgressDialog progressDialog;

@Override
protected void onPreExecute() {
    super.onPreExecute();
    progressDialog = new ProgressDialog(SearchActivity.this);
    progressDialog.setMessage("Searching");
    progressDialog.setCancelable(false);
    progressDialog.show();
}
        @TargetApi(Build.VERSION_CODES.N)
        @Override
        protected Void doInBackground(Void... voids) {
            try {
                finalODescriptionArrayList = JsontoObject.jsonToObjectData(getResources().openRawResource(R.raw.newdb));

            } catch (IOException e) {
                e.printStackTrace();
            }
            return null;
        }
@Override
protected void onPostExecute(Void aVoid) {
    super.onPostExecute(aVoid);
    titlefunc();
    arrayAdapter.notifyDataSetChanged();
    if (progressDialog.isShowing())
        progressDialog.dismiss();
}
   }

修改后的 titlefunc() - 删除重复项

Set<String > set = new HashSet<>( NameDesTitles);
NameDesTitles.clear();
NameDesTitles.addAll(set);

您的 AsyncTask 运行 在后台异步执行。当您调用 titleFunc()(这就是您所看到的)时,它(很可能)不会完成。

您可以通过多种方式解决此问题。一种方法是在 AsyncTask 完成后更新适配器的内容。您可以在 AsyncTaskonPostExecute() 中执行此操作,这将在后台处理完成时调用。在该方法中,您可以 运行 您的 titleFunc() 或类似的东西来过滤您想要显示的结果。然后,您需要通过在 Adapter 上调用 notifyDatasetChanged() 来告诉您的 Adapter 更新视图。