“没有合适的默认构造函数”我到处寻找答案

时间:2016-01-25 05:39:07

标签: c++ constructor default-constructor

我查看了有关此主题的所有帖子,但没有一个有用。请在两小时内完成我的任务。

以下是相关标题

    class RCB {
private:
    str                 rID;
    int                 numResources;
    int                 availableResources;
    int                 resourcesRequested;     //The amount of resources requested including resources requested from PCB's in the waitlist


public:

    std::list<PCB*>     waitList;

    RCB(str name, int r);
    ~RCB();

    void setRID(str name) { rID = name; }
    void allocateResources(int n) { availableResources -= n; }
    void returnResources(int n) { availableResources += n; }

    int getNumResources(){ return numResources; }
    int getAvailableResources(){ return availableResources; }
    str getRID(){ return rID; }
    int getResourcesRequested() { return resourcesRequested; }

};

这是源文件

  RCB::RCB(str name, int r) :
        rID{ name },
        numResources{ r },
        availableResources{ r },
        resourcesRequested{ 0 }
    {}

我收到错误

错误1错误C2512:'RCB':没有合适的默认构造函数c:\ program files(x86)\ microsoft visual studio 12.0 \ vc \ include \ tuple 746 1 ProcessScheduler

这是源的其余部分

#include "Data.h"



PCB::PCB(str name, int p) : 
    pID{ name },
    status{ READY },
    backptr{ nullptr },
    parent{ nullptr },
    priority{ p }
{

    //Insert resource counters into the resource log
    resourceLog.insert(std::pair<str, int>("R1", 0));
    resourceLog.insert(std::pair<str, int>("R2", 0));
    resourceLog.insert(std::pair<str, int>("R3", 0));
    resourceLog.insert(std::pair<str, int>("R4", 0));


    //Insert resource request counters into the request log
    requestBackLog.insert(std::pair<str, int>("R1", 0));
    requestBackLog.insert(std::pair<str, int>("R2", 0));
    requestBackLog.insert(std::pair<str, int>("R3", 0));
    requestBackLog.insert(std::pair<str, int>("R4", 0));
}


PCB::~PCB()
{




}

//Print the proccess ID to stdout
void PCB::printID()
{

    std::cout << pID << " ";

}








RCB::RCB(str name, int r) :
    rID{ name },
    numResources{ r },
    availableResources{ r },
    resourcesRequested{ 0 }
{}


RCB::RCB(const RCB& r)
{
    rID = r.rID;
    numResources = r.numResources;
    availableResources = r.availableResources;
    resourcesRequested = r.resourcesRequested;

}

RCB::RCB() :
    rID{ "R0" },
    numResources{ 5 },
    availableResources{ 5 },
    resourcesRequested{ 0 }
{

}


MainProcess::MainProcess() :
    initProcess("init", 0),
    currentlyRunning{ &initProcess }

{

    //Add init to the list of process names
    nameList.push_back("init");

    RCB R1("R1", 1);
    RCB R2("R2", 2);
    RCB R3("R3", 3);
    RCB R4("R4", 4);


    //Initialize four resources in the resource map
    resourceMap.insert(std::pair<str, RCB>("R1", R1));
    resourceMap.insert(std::pair<str, RCB>("R2", R2));
    resourceMap.insert(std::pair<str, RCB>("R3", R3));
    resourceMap.insert(std::pair<str, RCB>("R4", R4));


    //Add a reference to the initial process to lowest list on the ready list 
    readyList[0].push_back(&initProcess);
    initProcess.setStatus(RUNNING);

    //Print the id of the init process to stdout
    initProcess.printID();







}

void MainProcess::Release(str rID, int num)
{

    //Check for negative numbers
    if (num < 0){
        std::cout << "error ";
        return;
    }


    //Subtract resources from the resource log of the currently running process
    currentlyRunning->resourceLog[rID] = std::max(currentlyRunning->resourceLog[rID] - num, 0);

    //Add resources back to the available resources
    resourceMap[rID].returnResources(num);

    //Iterator pointing to the first PCB in the waitlist
    std::list<PCB*>::iterator it = resourceMap[rID].waitList.begin();

    //CONDITION
    //The waitlist on the RCB is not empty AND 
    //the amount of available resources in the RCB is greater than the amount of
    //requested resources by the PCB at the front of the waitlist
    while (!resourceMap[rID].waitList.empty() && resourceMap[rID].getAvailableResources() > 0 && it != resourceMap[rID].waitList.end())
    {

        if ((*it)->requestBackLog[rID] <= resourceMap[rID].getAvailableResources() ){

            //Allocate backloged resources from the RCB
            resourceMap[rID].allocateResources((*it)->requestBackLog[rID]);

            //Give the allocated resources to the PCB
            (*it)->resourceLog[rID] += (*it)->requestBackLog[rID];

            //Zero out the request back log
            (*it)->requestBackLog[rID] = 0;


            //Change the status of the PCB and add it to the ready list         
            (*it)->setStatus(READY);
            (*it)->setBackPtr(readyList);
            readyList[(*it)->getPriority()].push_back((*it));

            //Move the iterator to the next element in the wait list
            it++;

            //Remove the PCB from the waitlist
            resourceMap[rID].waitList.pop_front();


            //Call the scheduler
            Scheduler();


        }


        //If the PCB at the front of the wait list is asking for too many resources
        //then just skip it and move on to the next PCB on the waitlist
        else
        {
            it++;
        }



    }



}

void MainProcess::FreeResources(PCB* p)
{

    //Free all the resources currently held by PCB p
    for (auto& item : p->resourceLog){
        Release(item.first, item.second);
    }


}

void MainProcess::Destroy(str PID)
{

    //Search the ready list for the PCB with the specified PID
    for (int i = 1; i < 3; i++){
        for (PCB* p : readyList[i]){
            if (p->getPID() == PID){
                KillTree(p);
                Scheduler();
                return;
            }
        }
    }

    //If no PCB was found with PID then output error
    std::cout << "error ";



}

void MainProcess::KillTree(PCB* p)
{
    //Recursively call kill tree on each child
    if (!p->children.empty()){
        for (PCB* child : p->children)
        {
            KillTree(child);

        }

    }

    //If the PCB has no children then free all of its resources and delete it.
    FreeResources(p);
    delete p;
    return;


}

void MainProcess::Create(str name, int p)
{

    std::vector<str>::iterator it = std::find(nameList.begin(), nameList.end(), name);

    if (it != nameList.end()){
        std::cout << "error ";
        return;
    }

    else{

        //Add the new process name to the list of process names
        nameList.push_back(name);

        //Create a reference to a new process
        PCB* newProcess = new PCB(name, p);

        //Set the back pointer to the ready list
        newProcess->setBackPtr(readyList);

        //Set the parent pointer to the parent process
        newProcess->setParent(currentlyRunning);

        //Add it to the process tree
        currentlyRunning->children.push_back(newProcess);

        //Add the new process to the ready list
        newProcess->setStatus(READY);
        readyList[newProcess->getPriority()].push_back(newProcess);

        //Call the scheduler
        Scheduler();

    }



}



void MainProcess::Request(str rID, int num)
{
    RCB* rcb;

    //Check for negative numbers
    if (num < 0){
        std::cout << "error ";
        return;
    }

    //rcb is a reference to a resource in the resource map
    rcb = &resourceMap[rID];

    //If resources are available
    if (rcb->getAvailableResources() >= num){
        rcb->allocateResources(num);

        //Give the requested resources to the running process
        currentlyRunning->resourceLog[rID] += num;




        //Insert RCB into resource list of currently running process if not in there already
        std::list<RCB*>::iterator it = std::find(currentlyRunning->other_Resources.begin(), currentlyRunning->other_Resources.end(), rcb);

        if (it == currentlyRunning->other_Resources.end()){

            currentlyRunning->other_Resources.push_back(rcb);

        }
    }



    else
    {

        //Stop the process from running and put it on the blocked list
        currentlyRunning->setStatus(BLOCKED);
        currentlyRunning->setBackPtr(&rcb->waitList);

        readyList[currentlyRunning->getPriority()].pop_front();
        rcb->waitList.push_back(currentlyRunning);

        //Log the requested amount in the request back log
        currentlyRunning->requestBackLog[rID] += num;

        //Call Scheduler
        Scheduler();


    }

}


void MainProcess::Scheduler()
{

    PCB* p = getHighestPriority();

    if (currentlyRunning != p){

        //Set the currently running process to the 
        currentlyRunning = p;

        //Set the status of the currently running process to "RUNNING"
        currentlyRunning->setStatus(RUNNING);
    }

    //Print the id of the currently running process
    currentlyRunning->printID();

}

void MainProcess::TimeOut()
{


    //Remove currently running process from the front of the list and put it in the back
    readyList[currentlyRunning->getPriority()].pop_front();
    currentlyRunning->setStatus(READY);
    readyList[currentlyRunning->getPriority()].push_back(currentlyRunning);

    Scheduler();

}

PCB* MainProcess::getHighestPriority()
{
    //Iterate through the ready list to find the highest priority process
    for (int i = 2; i >= 0; i--){
        if (!readyList[i].empty()){
            return readyList[i].front();
        }
    }

    //Return null if no process is found
    return nullptr;
}

void MainProcess::Reset()
{

    for (PCB* p : initProcess.children){

        KillTree(p);

    }

    Scheduler();


}

我很确定这就是问题所在

//Add init to the list of process names
    nameList.push_back("init");

    RCB R1("R1", 1);
    RCB R2("R2", 2);
    RCB R3("R3", 3);
    RCB R4("R4", 4);


    //Initialize four resources in the resource map
    resourceMap.insert(std::pair<str, RCB>("R1", R1));
    resourceMap.insert(std::pair<str, RCB>("R2", R2));
    resourceMap.insert(std::pair<str, RCB>("R3", R3));
    resourceMap.insert(std::pair<str, RCB>("R4", R4));

2 个答案:

答案 0 :(得分:1)

当您定义参数化构造函数[RCB(str name,int r)]时,编译器将不会生成默认的无参数构造函数。因此,在您的情况下,如果您尝试创建RCB [RCB obj;]的对象,则必然会抛出此错误。要解决此问题,您需要定义默认的无参数构造函数。不确定这是否有帮助。

答案 1 :(得分:0)

根据错误,类RCB没有默认构造函数。这可以。并非所有类都必须具有默认构造函数。但是,您的代码中使用RCB的东西(不是您在问题中包含的内容的一部分)试图显式或隐式地调用RCB的默认构造函数。

例如,如果您在代码中的某处声明

RCB rcb;

然后您使用默认构造函数。