Android LoaderManager.restartLoader()是否总是导致调用onCreateLoader()?

Android LoaderManager.restartLoader()是否总是导致调用onCreateLoader()?,android,android-loadermanager,android-loader,Android,Android Loadermanager,Android Loader,LoaderManager具有以下方法: 公共抽象加载程序restartLoader(int-id、Bundle-args、LoaderCallbacks回调) 在此管理器中启动新加载程序或重新启动现有加载程序,向其注册回调,然后(如果活动/片段当前已启动)开始加载它。如果以前启动过具有相同id的加载程序,则当新加载程序完成其工作时,该加载程序将自动销毁。回调将在旧加载程序销毁之前传递 基于,我得到的想法是,调用onCreateLoader总是从restartLoader(): 重新启动加载程序

LoaderManager
具有以下方法:

公共抽象加载程序restartLoader(int-id、Bundle-args、LoaderCallbacks回调)

在此管理器中启动新加载程序或重新启动现有加载程序,向其注册回调,然后(如果活动/片段当前已启动)开始加载它。如果以前启动过具有相同id的加载程序,则当新加载程序完成其工作时,该加载程序将自动销毁。回调将在旧加载程序销毁之前传递

基于,我得到的想法是,调用
onCreateLoader
总是从
restartLoader()

重新启动加载程序

要丢弃旧数据,请使用restartLoader()。例如,SearchView.OnQueryTextListener的此实现在用户的查询更改时重新启动加载程序。加载程序需要重新启动,以便可以使用修改后的搜索筛选器执行新查询:

public boolean onquerytexchanged(字符串newText){
//当操作栏搜索文本已更改时调用。更新
//搜索筛选器,然后重新启动加载程序以执行新查询
//用这个过滤器。
mCurFilter=!TextUtils.isEmpty(newText)?newText:null;
getLoaderManager().restartLoader(0,null,this);
返回true;
}
公共加载器onCreateLoader(int-id,Bundle-args){
//注意:加载程序是用用户的查询实例化的
uribaseuri;
if(mCurFilter!=null){
baseUri=Uri.withAppendedPath(Contacts.CONTENT\u FILTER\u Uri,
encode(mCurFilter));
}否则{
baseUri=Contacts.CONTENT\u URI;
}
//现在创建并返回一个游标加载程序,它将处理
//为正在显示的数据创建光标。
String select=“(“+Contacts.DISPLAY_NAME+”NOTNULL)和(”
+Contacts.HAS_PHONE_NUMBER+“=1)和(”
+Contacts.DISPLAY_NAME+“!=”);
返回新的游标装入器(getActivity(),baseUri,
联系人\u摘要\u投影,选择,空,
Contacts.DISPLAY_NAME+“核对本地化ASC”);
}

在本例中,
onCreateLoader
是将有关用户查询的信息传递给加载程序的唯一位置(在实例化时)。但是,这些文档会说“启动一个新的或重新启动一个现有的加载程序”

这让我很反感。您的问题的简单答案是肯定的,对restartLoader()的调用将再次调用onCreateLoader()

您可以并行启动多个加载程序(假设您有两个SimpleCorsorAdapter要填充),例如:

然后,加载程序管理器为每个id调用onCreateLoader(然后,加载程序管理器异步构建返回的加载程序):

…首先调用onLoaderReset:

public void onLoaderReset(Loader<Cursor> loader)
{
    if (loader.getId() == 0)
        //perhaps do swapCursor(null) on an adapter using this loader
    else if (loader.getId() == 1)
        //perhaps do swapCursor(null) on an adapter using this loader
}
public void onLoaderReset(加载程序)
{
if(loader.getId()==0)
//可能使用此加载程序在适配器上执行swapCursor(null)
else if(loader.getId()==1)
//可能使用此加载程序在适配器上执行swapCursor(null)
}

…之后是对onCreateLoader的新调用。因此,在这方面,onCreateLoader既可用于启动全新的加载程序,也可用于重置现有加载程序。

我很想知道为什么您会这样认为?这就是加载程序与ContentProvider/Datasource异步交互的全部要点。长时间运行的任务(可能会阻塞UI)在onCreateLoader中运行—LoaderManager在后台运行该部分。是的,是的,AsyncTaskLoader的部分肯定在后台线程上运行,但我认为onCreateLoader在UI线程上:--与实例化
异步任务
相当,这就是我的推理。从客户机/主线程对加载程序的调用是.initLoader()调用。然后加载程序在后台运行onCreateLoader;似乎onCreateLoader在UI线程上运行。我还在onCreateLoader中添加了一些UI更新,它可以正常工作。@ANemati谢谢;再看一遍,你是对的。onCreateLoader确实在UI线程上运行—它返回的加载程序是由加载程序管理器异步构建的。我已编辑了我的答案,以消除不准确之处。
getLoaderManager().initLoader(0, null, this);  //id = 0
getLoaderManager().initLoader(1, null, this);  //id = 1
public Loader<Cursor> onCreateLoader(int id, Bundle args)
{
    if (id == 0)
        //return a Loader<Cursor> for id 0
    else if (id == 1)
        //return a Loader<Cursor> for id 1
}
public void onLoadFinished(Loader<Cursor> loader, Cursor cursor)
{
    if (loader.getId() == 0)
        //cursor was returned from onCreateLoader for id 0
        //perhaps do swapCursor(cursor) on an adapter using this loader
    else if (loader.getId() == 1)
        //cursor was returned from onCreateLoader for id 1
        //perhaps do swapCursor(cursor) on an adapter using this loader
}
getLoaderManager().restartLoader(0, null, this);  //id = 0
public void onLoaderReset(Loader<Cursor> loader)
{
    if (loader.getId() == 0)
        //perhaps do swapCursor(null) on an adapter using this loader
    else if (loader.getId() == 1)
        //perhaps do swapCursor(null) on an adapter using this loader
}