【问题标题】:Using methods() with threads in Java在Java中将methods()与线程一起使用
【发布时间】:2011-06-21 22:12:58
【问题描述】:

这是我的问题:

我有一大堆相同的对象。这些对象与服务器交互。从服务器获取数据需要 4 或 5 秒,因为服务器很慢。

现在我需要所有对象来获取数据。所以我为每个对象调用 MyObject.getData() 。我可以做一个系列,但 20 个对象,每个需要 5 秒太慢了。我认为我应该使用线程并将每个对象放在自己的线程上。

这是我的问题:

如果我让对象扩展线程。将调用 o MyObject.getData();在该对象的线程中运行,还是在调用该方法的线程中运行?我知道我可以使用 Thread.Run() 来让对象运行,但这不是我想要的。我想让方法随心所欲地运行。

那我该怎么做呢?

非常感谢。

【问题讨论】:

  • Thread.run() 不会“让对象运行”——这是一个常见的误解。您要调用的是Thread.start()
  • 最佳实践是不要扩展线程。相反,您应该实施 RunnableCallable (就像大多数答案所暗示的那样)。使用这些接口,您仍然可以根据需要手动启动 Thread 对象,但可以轻松切换到使用 ExecutorService

标签: java multithreading methods


【解决方案1】:

教科书的做法可能是这样的:

class GetDataObj implements Callable<Data> {
    public Data call(){
        //get data
        return data; 
    }
}

然后

ExecutorService exec = Executors.newCachedThreadPool();
Set<Callable<Data>> objects = //get objects;
List<Future<Data>> futures = exec.invokeAll(objects);
for(Future<Data>> future : futures){
    Data data = future.get();
    //do stuff with data
}
exec.shutdown();

请注意,当您遍历 futures 时,get() 方法将被阻塞,直到结果可用于该 DataObj。如果您想等到所有数据都可用,这很好。

【讨论】:

    【解决方案2】:

    如果您调用 object.myMethod(),该方法将在调用者线程中运行。

    您必须 start() 线程才能使其运行,而不是调用 run() 方法。

    您可以做的一个想法是重写您的对象,以便 myMethod() 方法启动一个新线程。因此,您可以使用与实际完全相同的对象。但是如果 myMethod 返回了一些东西,那就改变了,因为你必须等待线程终止之前

    【讨论】:

      【解决方案3】:

      我认为最好使用线程池从对象中获取数据。因此,您需要每个对象来实现 Runnable。见thread pools

      如果您在对象获得数据后将队列的引用传递给对象,则它们可以将其放入队列中。然后,主线程可以在准备好时将数据从队列中取出。 请参阅producer-consumer pattern

      一个例子是:

      BlockingQueue<Data> queue = new BlockingQueue<Data>();
      ExecutorService pool = Executors.newFixedThreadPool(5);
      
      //implements Runnable, getting data from this
      //places Data object in queue instead of returning it
      DataObject obj = new DataObject(queue); 
      pool.execute(obj); //invokes the run method of the DataObject
      Data data = queue.take();
      

      您需要为多个对象创建一个 for 循环。

      希望这会有所帮助。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-01-06
        • 2022-06-17
        • 2018-07-29
        • 2011-12-13
        • 2021-09-14
        相关资源
        最近更新 更多