Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/234.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Android 使用单例模式同步HTTP请求_Android_Multithreading_Http_Singleton_Intentservice - Fatal编程技术网

Android 使用单例模式同步HTTP请求

Android 使用单例模式同步HTTP请求,android,multithreading,http,singleton,intentservice,Android,Multithreading,Http,Singleton,Intentservice,我正在尝试(在android应用程序中)使用单例模式将我的主线程与向服务器发出http请求的intent服务同步。我在理解正确的实现方面遇到了困难,我想知道我是否可以在正确的方向上得到一些指针 下面是来自主线程的http请求的一个示例用法: Intent intent = new Intent(getActivity(), ClientService.class); intent.putExtra(ClientService.REQUEST, ClientService.CLIENT_LIST_

我正在尝试(在android应用程序中)使用单例模式将我的主线程与向服务器发出http请求的intent服务同步。我在理解正确的实现方面遇到了困难,我想知道我是否可以在正确的方向上得到一些指针

下面是来自主线程的http请求的一个示例用法:

Intent intent = new Intent(getActivity(), ClientService.class);
intent.putExtra(ClientService.REQUEST, ClientService.CLIENT_LIST_REQ);
SyncManager syncManager = SyncManager.getInstance(getActivity());
syncManager.submitHttpRequest(intent);
Log.d(TAG, syncManager.getResponse());
这里是SyncManager singleton,我承认它来自于我在这里发现的一个早期主题的解决方案:(Vladimir Lichonos的解决方案)

总之:

因此,您可能会从示例调用中注意到,我希望能够做的是进行HTTP调用,然后在该调用返回后访问数据(现在我在Log.d函数中得到一个空指针异常,因为在http请求返回填充'respose'变量之前调用了该语句)。因此,一旦服务启动,我想阻止启动它的线程,然后在服务停止运行后取消阻止它。在以前的线程中作为答案提供给我的示例单例结构似乎很有希望,但我不知道如何实现包含的侦听器部分。相反,我尝试只设置同步单个变量,因此SyncManager代码中与侦听器无关但不起作用的部分。希望了解更多有关如何实现singleton模式的信息,以实现在intent服务进行http调用时阻止主线程的目标


我意识到我的一些措辞可能过于重复,但我正在努力明确过去的否决权。

实现目标不需要任何单件。使用
AsyncTask
参见doc。基本上你需要覆盖
doInBackground()
方法,在后台线程上执行;这里您将实现
HTTPRequest
传递。后台线程将等待服务器的响应(或超时),并通过调用
onPostExecute()将结果提供给主线程
您可以在其中实现如何处理结果。

因为蜂巢,s是在一个线程上执行的。所以我认为您可能不需要自己编写。请参见编写什么?singleton manager?是否有其他方法让主线程等待intent service?为什么希望主线程等待?主线程不需要eds访问http请求应该返回的数据,因此主线程需要等待请求返回(也称为服务完成运行)在它能够访问数据之前。onPostExecute将再次在UI线程上运行。我考虑过这个解决方案,但它对我来说似乎太复杂了,因为我需要在应用程序中发出许多不同类型的http请求。要做到这一点,我不需要为每一个请求创建一个单独的异步任务吗?我要说的是,您的原始解决方案绝对是可行的更复杂。那么你更确切地说“不同类型的http请求”是什么意思?您不需要实现不同的异步任务。您可以为httprequests提供一个公共接口,尽管这种方式看起来更复杂,但我想使用它,因为它应该提供一个公共接口。我如何为异步任务提供一个公共接口?在提交任务之前,首先定义您的httprequestsi’我能完成任务吗?很抱歉,如果这听起来像n00b15H,我对异步任务不是很熟悉。
public class SyncManager {

    private static SyncManager instance;
    private Object Lock;
    private boolean hasReturned;
    private String response;
    public Context mContext;
    LinkedList<OnCompletionListener> mListeners;

    private SyncManager(Context c){
        mContext = c;
        mListeners = new LinkedList<OnCompletionListener>();
        hasReturned = false;
    }

    public static SyncManager getInstance(Context c) {
        if(instance == null){
            synchronized (SyncManager.class){
                if(instance == null){
                    instance = new SyncManager(c.getApplicationContext());
                }
            }
        }
        return instance;
    }

    //to be called by the activity/fragment
    public void submitHttpRequest(Intent intent){
        mContext.startService(intent);
    }

    public boolean checkHasReturned(){
        synchronized(Lock){
            return hasReturned;
        }
    }

    public void setReturnFlag(){
        synchronized(Lock){
            hasReturned = true;
        }
    }

    public void resetReturnFlag(){
        synchronized(Lock){
            hasReturned = false;
        }
    }

    public void setResponse(String response){
        synchronized(Lock){
            this.response = response;
        }
    }

    public String getResponse(){
        synchronized(Lock){
            return response;
        }
    }

    public void addListener(OnCompletionListener listener){
        synchronized(mListeners){
            mListeners.add(listener);
        }
    }

    public void removeListener(OnCompletionListener listener){
        synchronized(mListeners){
            mListeners.remove(listener);
        }
    }


    //to be called by the service
    public void HttpRequestComplete(){
        synchronized(mListeners){
            for (OnCompletionListener listener : mListeners){
                listener.onCompleted(this);
            }
        }
    }


    public static interface OnCompletionListener{

        public void onCompleted(SyncManager instance);

    }
}
protected void onHandleIntent(Intent intent) {
    SyncManager syncManager = SyncManager.getInstance(getApplicationContext());
    Log.d(TAG, "entered onHandleIntent");
    int rqst = intent.getIntExtra(REQUEST, DEFAULT_REQ);
    Log.d(TAG, ""+rqst);
    String response = "";
    switch(rqst){
        case ABOUT_REQ: 
            response = getAbout();
            break;
        case VER_DATA_REQ:
            response = getVerificationData("douglas_adams_uri");
            break;
        case CLIENT_LIST_REQ:
            response = getClientList();
            break;
    }
    syncManager.setResponse(response);
    syncManager.setReturnFlag();
    return;
}