Я пытаюсь написать программу, которая одновременно добавляет и удаляет элементы из «хранилища».У меня есть класс «Monitor», который обрабатывает операции «storehouse»:
class Monitor
{
private:
mutex m;
condition_variable cv;
vector<Storage> S;
int counter = 0;
bool busy = false;;
public:
void add(Computer c, int index) {
unique_lock <mutex> lock(m);
if (busy)
cout << "Thread " << index << ": waiting for !busy " << endl;
cv.wait(lock, [&] { return !busy; });
busy = true;
cout << "Thread " << index << ": Request: add " << c.CPUFrequency << endl;
for (int i = 0; i < counter; i++) {
if (S[i].f == c.CPUFrequency) {
S[i].n++;
busy = false; cv.notify_one();
return;
}
}
Storage s;
s.f = c.CPUFrequency;
s.n = 1;
// put the new item in a sorted position
S.push_back(s);
counter++;
busy = false; cv.notify_one();
}
}
Потоки создаются следующим образом:
void doThreadStuff(vector<Computer> P, vector <Storage> R, Monitor &S)
{
int Pcount = P.size();
vector<thread> myThreads;
myThreads.reserve(Pcount);
for (atomic<size_t> i = 0; i < Pcount; i++)
{
int index = i;
Computer c = P[index];
myThreads.emplace_back([&] { S.add(c, index); });
}
for (size_t i = 0; i < Pcount; i++)
{
myThreads[i].join();
}
// printing results
}
Запуск программы дал следующие результаты:
Я знаком с условиями гонки, но для меня это не похоже.Моя ставка была бы на что-то, относящееся к ссылке, потому что в результатах мы можем видеть, что для каждого «отсутствующего потока» (темы 1, 3, 10, 25) я получаю «дублирующие темы» (темы 2, 9, 24, 28).
Я пытался создать локальные переменные в функциях и циклах, но это ничего не изменило.
Я слышал о потоках, разделяющих области памяти, но моя предыдущая работа должна была дать аналогичные результаты, поэтому я неНе думаю, что это так, но не стесняйтесь доказать, что я не прав.
Я использую Visual Studio 2017