Beispiel #1
0
DECLARE_EXPORT void Resource::inspect(const string msg) const
{
  logger << "Inspecting resource " << getName() << ": ";
  if (!msg.empty()) logger  << msg;
  logger << endl;

  for (loadplanlist::const_iterator oo = getLoadPlans().begin();
    oo != getLoadPlans().end();
    ++oo)
  {
    logger << "  " << oo->getDate()
      << " qty:" << oo->getQuantity()
      << ", oh:" << oo->getOnhand();
    switch (oo->getEventType())
    {
    case 1:
      logger << ", oper:" << static_cast<const LoadPlan*>(&*oo)->getOperationPlan()->getOperation() << endl;
      break;
    case 2:
      logger << ", event set-onhand" << endl;
      break;
    case 3:
      logger << ", event update-minimum" << endl;
      break;
    case 4:
      logger << ", event update-maximum" << endl;
      break;
    }
  }
}
Beispiel #2
0
DECLARE_EXPORT void Resource::inspect(const string msg) const
{
  logger << "Inspecting resource " << getName() << ": ";
  if (!msg.empty()) logger  << msg;
  logger << endl;

  for (loadplanlist::const_iterator oo = getLoadPlans().begin();
    oo != getLoadPlans().end();
    ++oo)
  {
    logger << "  " << oo->getDate()
      << " qty:" << oo->getQuantity()
      << ", oh:" << oo->getOnhand();
    if (oo->getEventType() == 1)
      logger <<  ", oper:" << static_cast<const LoadPlan*>(&*oo)->getOperationPlan()->getOperation();
    logger << endl;
  }
}
Beispiel #3
0
DECLARE_EXPORT void Resource::updateSetups(const LoadPlan* ldplan)
{
  // No updating required this resource
  if (!getSetupMatrix() || (ldplan && ldplan->getOperationPlan()->getOperation() != OperationSetup::setupoperation))
    return;

  // Update later setup opplans
  OperationPlan *opplan = ldplan ? ldplan->getOperationPlan() : NULL;
  loadplanlist::const_iterator i = ldplan ?
      getLoadPlans().begin(ldplan) :
      getLoadPlans().begin();
  string prevsetup = ldplan ? ldplan->getSetup() : getSetup();
  for (; i != getLoadPlans().end(); ++i)
  {
    const LoadPlan* l = dynamic_cast<const LoadPlan*>(&*i);
    if (l && !l->getLoad()->getSetup().empty()
        && l->getOperationPlan()->getOperation() == OperationSetup::setupoperation
        && l->getOperationPlan() != opplan
        && !l->isStart())
    {
      // Next conversion operation
      OperationPlanState x = l->getOperationPlan()->getOperation()->setOperationPlanParameters(
          l->getOperationPlan(),
          l->getOperationPlan()->getQuantity(),
          Date::infinitePast,
          l->getOperationPlan()->getDates().getEnd(),
          true,
          false);
      if (x.start != l->getOperationPlan()->getDates().getStart())
        // We need to change a setup plan
        l->getOperationPlan()->restore(x);
      else if (ldplan && x.start == l->getOperationPlan()->getDates().getStart())
        // We found a setup plan that doesn't need updating. Later setup plans
        // won't require updating either
        return;
    }
  }
}
bool OperationPlan::updateFeasible()
{
  if (!getOperation()->getDetectProblems())
  {
    // No problems to be flagged on this operation
    setFeasible(true);
    return true;
  }

  // The implementation of this method isn't really cleanly object oriented. It uses
  // logic which only the different resource and buffer implementation classes should be
  // aware.
  if (firstsubopplan)
  {
    // Check feasibility of child operationplans
    for (OperationPlan *i = firstsubopplan; i; i = i->nextsubopplan)
    {
      if (!i->updateFeasible())
      {
        setFeasible(false);
        return false;
      }
    }
  }
  else
  {
    // Before current and before fence problems are only detected on child operationplans
    if (getConfirmed())
    {
      if (dates.getEnd() < Plan::instance().getCurrent())
      {
        // Before current violation
        setFeasible(false);
        return false;
      }
    }
    else
    {
      if (dates.getStart() < Plan::instance().getCurrent())
      {
        // Before current violation
        setFeasible(false);
        return false;
      }
      else if (dates.getStart() < Plan::instance().getCurrent() + oper->getFence() && getProposed())
      {
        // Before fence violation
        setFeasible(false);
        return false;
      }
    }
  }
  if (nextsubopplan
    && getEnd() > nextsubopplan->getStart() + Duration(1L)
    && !nextsubopplan->getConfirmed()
    && owner && !owner->getOperation()->hasType<OperationSplit>()
    )
  {
    // Precedence violation
    // Note: 1 second grace period for precedence problems to avoid rounding issues
    setFeasible(false);
    return false;
  }

  // Verify the capacity constraints
  for (auto ldplan = getLoadPlans(); ldplan != endLoadPlans(); ++ldplan)
  {
    if (ldplan->getResource()->hasType<ResourceDefault>() && ldplan->getQuantity() > 0)
    {
      auto curMax = ldplan->getMax();
      for (
        auto cur = ldplan->getResource()->getLoadPlans().begin(&*ldplan);
        cur != ldplan->getResource()->getLoadPlans().end();
        ++cur
        )
      {
        if (cur->getOperationPlan() == this && cur->getQuantity() < 0)
          break;
        if (cur->getEventType() == 4)
          curMax = cur->getMax(false);
        if (
          cur->getEventType() != 5
          && cur->isLastOnDate()
          && cur->getOnhand() > curMax + ROUNDING_ERROR
          )
        {
          // Overload on default resource
          setFeasible(false);
          return false;
        }
      }
    }
    else if (ldplan->getResource()->hasType<ResourceBuckets>())
    {
      for (
        auto cur = ldplan->getResource()->getLoadPlans().begin(&*ldplan);
        cur != ldplan->getResource()->getLoadPlans().end() && cur->getEventType() != 2;
        ++cur
        )
      {
        if (cur->getOnhand() < -ROUNDING_ERROR)
        {
          // Overloaded capacity on bucketized resource
          setFeasible(false);
          return false;
        }
      }
    }
  }

  // Verify the material constraints
  for (auto flplan = beginFlowPlans(); flplan != endFlowPlans(); ++flplan)
  {
    if (
      !flplan->getFlow()->isConsumer()
      || flplan->getBuffer()->hasType<BufferInfinite>()
      )
      continue;
    auto flplaniter = flplan->getBuffer()->getFlowPlans();
    for (auto cur = flplaniter.begin(&*flplan); cur != flplaniter.end(); ++cur)
    {
      if (cur->getOnhand() < -ROUNDING_ERROR && cur->isLastOnDate())
      {
        // Material shortage
        setFeasible(false);
        return false;
      }
    }
  }

  // After all checks, it turns out to be feasible
  setFeasible(true);
  return true;
}