Портирование шаблона потоковой обработки в Swift - PullRequest
0 голосов
/ 19 июня 2019

Я пытаюсь перенести шаблон обработки из приложения Java в приложение Swift, и я не могу найти соответствующие конструкции в Swift, чтобы позволить мне это сделать.Шаблон разработан с одним рабочим потоком, который обрабатывает модель, когда ее об этом просят.Запросы не содержат никаких данных, работа, выполняемая рабочим потоком, определяется во время компиляции, а выполненная работа не возвращается. Подвох состоит в том, что если работника просят выполнить дополнительную работу, пока он уже обрабатывает, эти запросы должныбыть идемпотентом.

Кто-нибудь знает способ воспроизвести это в Swift?Я не вижу способа создать простой поток или создать переменную, безопасную для потока.Кажется, что все решения, которые я вижу с NSOperation или Dispatch, не имеют никакого способа объединить запросы;они хотят запускать один поток на каждый запрос.

(А для бонусных баллов у этого шаблона есть имя? Я не могу его найти, но, возможно, это упростило бы поиск в Google, если бы я его знал.)

Примеры потоков выполнения:

Thread A requests work Worker Thread(WT) starts working Thread B requests work WT finishes work WT Starts working WT Finishes work

Thread A requests work Worker Thread(WT) starts working Thread B requests work Thread A requests work WT finishes work WT Starts working WT Finishes work

А для более ориентированных на код людей, фрагмент концепции, написанный на Java:

import java.util.concurrent.atomic.AtomicBoolean;

class Main {
  
  AtomicBoolean lock = new AtomicBoolean(false);

  //Worker thread
  private final Thread worker = new Thread(){
    int timesRun = 0;
    public void run(){
      while(true){
        //Make sure there has been a request since last time we started
        while(!lock.getAndSet(false)){
          yield();
        }
        System.out.println(timesRun++);
        //Simulate lots of work
        try{Thread.sleep(750);}catch(Exception e){}
      }
    }
  };

  public void run() throws Exception{
    worker.start();

    //Proof of concept
    //These set calls come from many different threads
    lock.set(true);//Causes execution
    Thread.sleep(1000);
    lock.set(true);//Causes execution
    lock.set(true);//Does NOT cause execution
    Thread.sleep(1000);
    lock.set(true);//Causes execution
    Thread.sleep(1000);
  }

  public static void main(String[] args) throws Exception{
    new Main().run();
  }
}
...