当前位置: 首页 > 知识库问答 >
问题:

Java代码设计使用ExecutorService调用多个服务

相云
2023-03-14

我正在尝试并行运行15个服务,每个服务将向不同的客户发送邮件。提取标准因服务而异

服务1、服务2、服务3。。。。服务15。每个类都扩展了NotificationService类。

NotificationService类具有方法extractRecipients()、sendMail()、sendSMS()、logNotification()。

所有的Service类[1到15]都有进程()方法,它将调用NotificationService方法并完成它们的工作。

这是设计java代码的正确方法吗?

而且下面代码看起来很难看,有没有什么聪明的处理方法。拜托谁来帮帮我。

public void startService() {

try {
    ExecutorService service = Executors.newFixedThreadPool(3);

    for (;;) {
        service.submit(new Service1(conn) {
                    public Object call(){
                        try {
                            process(conn, param2); // Passing connection & obj
                        } catch (Exception e) {
                            throw e;
                        }
                        return null;
                    }
                });

        service.submit(new Service2(conn) {
                    public Object call(){
                        try {
                            process(conn, param2);
                        } catch (Exception e) {
                            throw e;
                        }
                        return null;
                    }
                });

        // like above i have 15 services. so its ugly.
    }

} catch (InterruptedException e) {
    e.printStackTrace();
}
}

public boolean process(Connection conn) throws Exception {
try {
// getRecipientsList(serviceID);

// sendMail(recipientsList);

// logNotificationDetails(notificationList);
} catch (Exception e) {
}
}

共有3个答案

方长卿
2023-03-14
public void startService() {

try {
    List<Bean> list = getServicesNotificationList();

    ExecutorService service = Executors.newFixedThreadPool(list.size); here list size should be 15

    for (int i=0; i < list.size(); i++) {

        service.submit(new NotificationService(conn, list[i]));
    }

    service.shutdown();

} catch (InterruptedException e) {
    e.printStackTrace();
}
}
单于浩邈
2023-03-14

使用executor服务的invokeAll。

孙光临
2023-03-14

一些需要改进的地方(不完整):

我假设服务1,服务2。。。类是从NotificationService派生的,覆盖了过程方法。

Callable的匿名接口实现

service.submit(new Service1(conn) {
                public Object call(){
                    try {
                        process(conn, param2); // Passing connection & obj
                    } catch (Exception e) {
                        throw e;
                    }
                    return null;
                }
            });

应移动到NotificationService类。然后,该代码简化为:

service.submit(new Service1(conn)); // Will call Service1's "process" implementation
service.submit(new Service2(conn)); // Will call Service2's "process" implementation
...

编辑:

我想到的是这种设置:

abstract class NotificationService implements Callable<Object>{
  // ...

  // I don't know what types conn and param2 are, so ...
  protected abstract void process( ConnType conn, Param2Type param2 );

  @Override
  public Object call(){
      try {
              process(conn, param2); // Passing connection & obj
      } catch (Exception e) {
              throw e;
      }
      return null;
  }
}

然后,您可以覆盖Service1、Service2中的进程。。。以他们特定的方式处理这个过程。

class Service1 extends NotificationService{
    @Override
    protected void process( ConnType conn, Param2Type param2 ){
        // do process according to Service1's needs.
    }
}

无止境循环:

for(;;){
   service.submit(...
}

将阻止该循环中的startService调用方,同时将新任务永远添加到执行器中。

如果每次执行都会给客户发送一封电子邮件,那么他已经被淹没了。

每分钟调用start Service

将产生一个新的Executor服务,每分钟都会有无数的任务!

这不仅会向客户发送垃圾邮件,还会很快降低性能

首先,你可以这样改变:

public void startService() {

try {
    ExecutorService service = Executors.newFixedThreadPool(3);


        service.submit(new Service1(conn)); // assuming callable impl is moved

        service.submit(new Service2(conn));

        // like above i have 15 services. so its ugly.
    service.shutdown();

} catch (InterruptedException e) {
    e.printStackTrace();
}
}

另一种方法是使用一个ScheduledExecutorService,在该服务上,您计划每分钟执行一次服务。

 类似资料:
  • 我有一个Java的Play 2.1控制器,需要调用一个外部的webservice来获取一些数据。然后有了这个数据结果,我必须用n次调用调用另一个web服务,对应于第一个web service调用的n个结果。 对于性能问题,我想使用 promise 在单独的线程中进行 n 次调用。 所以我会有一个这样的循环: 如何使用异步API同步n个promise,然后在一个响应(所有结果的列表)中减少结果,然后

  • 本文向大家介绍Spring Cloud多个微服务之间调用代码实例,包括了Spring Cloud多个微服务之间调用代码实例的使用技巧和注意事项,需要的朋友参考一下 这篇文章主要介绍了Spring Cloud多个微服务之间调用代码实例,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下 现在又一个学生微服务 user 和 学校微服务 school,如果u

  • 我有一个fixedThreadPool,我正在使用它运行一组工作线程,以实现具有许多组件的任务的并行执行。 当所有线程完成后,我使用方法(getResult)检索它们的结果(相当大),并将其写入文件。 最后,为了节省内存并能够看到中间结果,我希望每个线程在完成执行后将其结果写入文件,然后释放内存。 通常,我会在run()方法的末尾添加这样的代码。但是,此类中的某些其他对象也调用这些线程,但不希望它

  • 我在Scala上使用Play 2.5,我创建了一个类,可以多次调用外部web服务。 外部Web服务在某些条件下被调用并得到ok或nok的简单响应。如果可以,那么我应该更新内部对象状态,如果可以,我现在什么也不做。 这是我的类,它将String的列表作为参数,并返回要在控制器中处理的对象的Future列表。 是列表类型的列表,但我希望它只是一个简单的响应列表。 1)如何简化和纠正我的代码以获得响应列

  • 问题内容: 有没有人能将C#代码集成到Java应用程序中呢? 代码很小,所以我可以用Java重写,但是如果可能的话,我宁愿重用代码。不要重复自己,等等。 另外,我知道我可以将C#公开为Web服务或其他任何东西,但是其中包含一些安全性/加密功能,因此,我宁愿将其紧密集成。 编辑:它将在基于服务器的应用程序上,因此“下载”另一个运行时是无关紧要的。 问题答案: 有一个IL到Java字节码编译器Gras

  • gcc-g-i/usr/lib/jvm/java-1.6.0-openJDK-1.6.0.0.x86_64/include/-i/usr/lib/jvm/java-1.6.0-openJDK-1.6.0.0.x86_64/include/-i/usr/lib/jvm/java-1.6.0-openJDK-1.6.0.0.x86_64/include/-i/usr/lib/jvm/java-1.6.