【问题标题】:Java requests in thread线程中的 Java 请求
【发布时间】:2021-05-20 01:01:05
【问题描述】:

我陷入了这个问题,我正在使用线程和 http 请求来获取数据,但我的方法总是返回空字符串或最后一个请求的响应。这是我的代码:

static String a = "";
public static String request(String request) {
    new Thread(() -> {
        try {
            HttpURLConnection conn = (HttpURLConnection) new URL(request).openConnection();
            conn.setRequestMethod("GET");
            conn.setDoInput(true);
            BufferedReader br = new BufferedReader(new InputStreamReader(conn.getInputStream()));
            String line, text = "";
            while((line = br.readLine()) != null) {
                text = line;
            }
            br.close();
            a = text;
        } catch (IOException e) {
            e.printStackTrace();
        }
    }).start();
    return a;
}

【问题讨论】:

    标签: java multithreading android-networking


    【解决方案1】:

    您的问题中没有上下文来确定这是问题所在,但您的代码的一个问题是您没有等待线程完成,然后才返回 a 的值。因此,您可能返回了a 的内容线程已经在其中存储了任何内容。

    事实上,这段代码有点搞错了。如果您希望request(String) 返回从服务器检索到的值,则request 调用直到您检索到数据后才能完成。这不可避免地是同步的。使用Thread 进行检索实际上一无所获。

    (按照建议使用join()“修复”症状,但在这里使用线程并非毫无意义。)

    如果您希望这是异步的,您可以更改 request 以返回一个 Future<String>,调用者可以使用它在以后获取检索到的值。

    如果您使用Executor 而不是为每个“请求”创建一次性使用的线程,它会更简单并且(可能)更有效。

    【讨论】:

      【解决方案2】:

      这是一个异步调用,因此您的return 语句不会等到thread 执行,因为它是非阻塞的,您可以使用回调来获取string 何时准备就绪

      interface ResponseCallBack{
         void onResponse(String a);
         void onError(Exception e);
      }
      

      然后在调用你的方法时传递这个接口

      public static void request(String request, ResponseCallBack responseCallBack) {
          new Thread(() -> {
              try {
                  HttpURLConnection conn = (HttpURLConnection) new URL(request).openConnection();
                  conn.setRequestMethod("GET");
                  conn.setDoInput(true);
                  BufferedReader br = new BufferedReader(new InputStreamReader(conn.getInputStream()));
                  String line, text = "";
                  while((line = br.readLine()) != null) {
                      text = line;
                  }
                  br.close();
                  responseCallBack.onResponse(text);
              } catch (IOException e) {
                  e.printStackTrace();
                  responseCallBack.onError(e);
              }
          }).start();
      }
      

      然后你可以使用它来消费它

      request("", new ResponseCallBack() {
              @Override
              public void onResponse(String a) {
                  //here string will be available
              }
      
              @Override
              public void onError(Exception e) {
                  //error in case something failed
              }
      });
      

      【讨论】:

        猜你喜欢
        • 2018-08-17
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-11-30
        • 1970-01-01
        • 2018-09-14
        • 2016-02-16
        • 2013-06-01
        相关资源
        最近更新 更多