Использование future <> и обещания <> для передачи сообщений? - PullRequest
0 голосов
/ 28 мая 2020

Я пытаюсь написать простую программу для передачи сообщения с будущим <> и обещанием <>, поэтому я понимаю, как они работают. Цель состоит в том, чтобы передать потребителю 10 предметов от продукта. К сожалению, у меня проблемы с компиляцией. Кто-нибудь знает, где я ошибся? Спасибо!

Обновление решения.

#include <iostream>
#include <thread>
#include <unistd.h>
#include <stdlib.h>
#include <future>
#include <functional>
#include <vector>
using namespace std;
using namespace std::chrono;

struct MSG {
  int val;
};

void consumer(vector<future<MSG>> *futv) {
  for (auto& p : *futv) {
    this_thread::sleep_for(milliseconds{rand() % 25});
    MSG m = p.get();
    cout << m.val << endl;
  }
}

void producer(vector<promise<MSG>> *promv) {
  MSG m = {0};

  for (auto& p : *promv) {
    this_thread::sleep_for(milliseconds{rand() % 25});
    p.set_value(m);
    m.val++;
  }
}


int main(int argc, char *argv[])
{
  vector<promise<MSG>> promv;
  vector<future<MSG>> futv;

  for (int i=0; i<10; i++) {
    promv.push_back(promise<MSG>());
    futv.push_back(promv[i].get_future());
  }

  thread tp {producer, &promv};
  thread tc {consumer, &futv};

  tp.join();
  tc.join();

  return 0;
}

Компиляция ...,

g++ -lpthread -pedantic -Wall test84.cc && ./a.out
0
1
2
3
4
5
6
7
8
9

Ответы [ 2 ]

2 голосов
/ 28 мая 2020

Ошибка связана с тем, что future является только перемещаемым , но не копируемым

for (auto p : futv) - это попытка скопировать элементы из вектора. Вместо этого используйте следующие циклы, чтобы ссылаться на элемент вектора:

for (auto& p : futv) или for (decltype(auto) p : futv)


Обычно идея может работать как упражнение, но обещания / фьючерсы на самом деле не подходят предназначен для этого. Проблема в том, что вы не можете повторно использовать элементы вашего массива для другого запуска. Таким образом, для реального использования очереди производитель-потребитель реализуются с использованием примитивов более низкого уровня: мьютексов, переменных состояния, атомики и т. Д. c.

0 голосов
/ 28 мая 2020

Вы можете использовать condition_variable, в этом случае он лучше, чем реализация future / обещания.

Например, если взять два потока, продукт и потребитель, когда продукт 'i' (элемент продукта) завершено, оно будет передано потребителю 'i', который ждет, пока продукт не будет готов, а затем будет использован.

future / обещание используется, например, для нескольких потоков возвращаемых значений.

Если вы хотите, чтобы ваш поток возвращал несколько значений в разный момент времени, просто передайте несколько объектов std :: prom в потоке и выберите несколько возвращаемых значений из связанных с ними нескольких объектов std :: future.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...