I'm working on a call center call queue simulation model. I've created a vector of caller objects and assigned them exponential distributed random inter-arrival times, then assigned calculated arrival times in the call center class. I would like to then copy each caller object into a vector priority queue, however I keep receiving this error when i push a caller vector object into the queue:
Error C2280 'Caller::Caller(const Caller &)': attempting to reference a deleted function
I've been trying to fix it for a while now and cannot seem to figure out what is causing the issue or how to fix it. I'm trying to push an already created object, so I'm not sure why I would get a reference to a deleted function. Any help would be appreciated.
My Caller.h file
#pragma once
#include <random>
#include <time.h>
using namespace std;
class Caller
{
private:
bool isPaid;
int priority;
double arrivalTime;
double iarrivalTime;
default_random_engine e1;
random_device rd1;
public:
Caller();
Caller(bool p);
void setPriority();
int getPriority();
void generateInterArrivalTime();
double getInterArrivalTime();
void setArrivalTime(double t);
double getArrivalTime();
};
My Caller.Cpp file
#include "Caller.h"
Caller::Caller() : isPaid(false), priority(0), iarrivalTime(0), arrivalTime(0)
{
}
Caller::Caller(bool p): isPaid(false), priority(0), iarrivalTime(0)
{
isPaid = p;
}
void Caller::setPriority()
{
if (isPaid == true)
{
priority = 1;
}
else(priority = 0);
}
int Caller::getPriority()
{
return priority;
}
void Caller::generateInterArrivalTime()
{
e1.seed(rd1());
exponential_distribution<>callNums(25);
iarrivalTime = callNums(e1);
}
double Caller::getInterArrivalTime()
{
return iarrivalTime;
}
void Caller::setArrivalTime(double t)
{
arrivalTime = t;
}
double Caller::getArrivalTime()
{
return arrivalTime;
}
My CallCenter.h file
class CallCenter
{
private:
vector<Caller> callers;
priority_queue<Caller, vector<Caller>, CompareFunction > callQ;
public:
CallCenter();
void queueCalls();
void assignArrivalTime();
My CallCenter.Cpp file
CallCenter::CallCenter(): callers(10)
{
}
void CallCenter::assignArrivalTime()
{
for (int i = 0; i < callers.size(); i++)
{
callers[i].generateInterArrivalTime();
if (i==0)
{
callers[i].setArrivalTime(callers[i].getInterArrivalTime());
}
else {callers[i].setArrivalTime(callers[i - 1].getArrivalTime() + callers[i].getInterArrivalTime());}
cout << callers[i].getInterArrivalTime() << "\t" << callers[i].getArrivalTime() << endl;
}
}
void CallCenter::queueCalls()
{
for (int i = 0; i < callers.size(); i++)
{
callQ.push(callers[i]);
}
}
My CompareFunction.h file
#pragma once
#include "Caller.h"
class CompareFunction
{
public: bool operator()(Caller& lowp, Caller& highp)
{
return lowp.getArrivalTime() > highp.getArrivalTime();
}
};
random_device rd1;
Your class has a std::random_device
as a class member.
std::random_device
's copy constructor is deleted:
The copy constructor is deleted:
std::random_device
is not copyable nor movable.
This makes this class, which contains this class member, also have a deleted copy constructor.
After all, if a class member cannot be copied, by default, then the class itself can't be copied by default either.
priority_queue<Caller, vector<Caller>, CompareFunction > callQ;
Your priority queue is based on a std::vector
.
callQ.push(callers[i]);
std::vector
s cannot be used with non-copyable/movable classes. You can only use std::vector
with classes that can be copied or moved.
You will have to change your class design, in some form or fashion. The simplest change would be a priority queue of std::unique_ptr
s or std::shared_ptr
s to your Caller
s, which you will need to construct in dynamic scope (you will also have to provide a custom comparator class for std::priority_queue
, so it knows how to prioritize the smart pointers correctly, this is a little bit of extra work but it's not too complicated once you have a complete grasp on all the moving pieces).