3

4 つのサービス (A、B、C、D など) を含むサービス マネージャーを作成し、サービスのリストをロードする必要があります。サービスにはメソッドが必要でありstart()stop()次の順序で相互に依存しています。

  • サービス B と C はサービス A に依存します

  • サービス D はサービス B に依存します

そして、次のことが推測できます。

  • サービスDを開始するには、サービスAとBを開始する必要があります

  • サービス A を停止するには、サービス B、D、および C を最初に停止する必要があります

  • サービス B とサービス C は、サービス A の開始直後に並行して開始できます。逆に、並列に停止することもできます。

これは、本来の動作をしていない私のコードです。事は、それがその順序でサービスを開始していることですが、私はそれらをその順序でリストに入れました. 私は混乱しました。コメントしたこの行の使用方法がわからず、停止方法がわからないため、助けが必要です。ご協力いただきありがとうございます!

public class CountDown {

    public static void main(String args[]) {

        List<String> Services = Collections.synchronizedList(new ArrayList<String>());
        Services.add("Services A");
        Services.add("Services B");
        Services.add("Services C");
        Services.add("Services D");


       final CountDownLatch Start = new CountDownLatch(4);
       final CountDownLatch Stop = new CountDownLatch(4);

    new Thread(new Service("Service A", 1000, Start, Stop, Services)).start();
    new Thread(new Service("Service B", 2000, Start, Stop, Services)).start();
    new Thread(new Service("Service C", 3000, Start, Stop, Services)).start();
    new Thread(new Service("Service D", 4000, Start, Stop, Services)).start();

    /* A.start(); // this is how it should work

      if (A.isAlive())
      {
          B.start();
          C.start();
      }

      if(B.isAlive() && A.isAlive())
      {
          D.start();
      }

      D.interrupt();
      if(D.isInterrupted())
      {
          B.interrupt();
          C.interrupt();

      }
      if(B.isInterrupted() && D.isInterrupted())
      {
          A.interrupt();
      }*/



      try { 
          Start.await();
          Stop.countDown();   
    } catch(InterruptedException ie){
        ie.printStackTrace();
    }

    }

}



class Service implements Runnable{

    List<String> list;
    private final String name;
    private final int time;
    private final CountDownLatch Stop;
    private final CountDownLatch Start;


    public Service(String name, int time, CountDownLatch Start, CountDownLatch Stop, List<String> list){
        this.name = name;
        this.time = time;
        this.Start = Start;
        this.Stop = Stop;

        this.list = list;
    }

    @Override
    public void run() {


        try {


            Start.countDown();
           Thread.sleep(time);    
            list.add(name);


            System.out.println( name + " is Up!");


           Stop.await();

        } catch (InterruptedException ex) {
            Logger.getLogger(Service.class.getName()).log(Level.SEVERE, null, ex);
        }


    }

}
4

2 に答える 2

1

これを相互依存サービスの一般化されたシステムにしたい場合は、サービスに関するメタデータで依存関係を取得する必要があります。各サービスで利用可能な次のデータがあると仮定します。

List<String> getPredecessors();

これは、このサービスを開始する前に実行する必要があるすべてのサービスの名前を返します。次に、開始された一連のサービスがあります。

Set<String> startedServices = new HashSet<String>();

for ( String service: Services ) {
    boolean allClear = true;
    for ( String predecessor: Service(service).getPredecessors() ) {
        if ( ! startedServices.contains(predecessor) ) {
            allClear = false;
            break;
        }
    }
    if ( allClear ) {
        // start the service
        new Thread(new Service(service, 1000, Start, Stop, Services)).start();
        startedServices.add(service);
    }
}

これにより、必要なすべてのサービスが実行されている場合にのみ、サービスが開始されます。ここで、すべてのサービスが実行されるまで (またはデッドロックが見つかるまで)、すべてのサービスを反復処理する必要があります。

サービスの停止は逆の問題です。物事を開始するときに、先行者リストから後続者リストを計算できます。後続リストで同じアルゴリズムを使用します。

于 2013-06-11T12:10:17.197 に答える
0

「依存関係解決アルゴリズム」で検索してみてください。この記事には JavaScript の例があります: http://www.electricmonk.nl/log/2008/08/07/dependency-resolving-algorithm/

于 2013-06-11T10:49:10.147 に答える