Skip to content
Snippets Groups Projects
TransitionSet.cpp 3.05 KiB
Newer Older
#include "TransitionSet.hpp"
#include <limits>

TransitionSet::TransitionSet(const std::string & filename)
Franck Dary's avatar
Franck Dary committed
{
  addTransitionsFromFile(filename);
}

TransitionSet::TransitionSet(const std::vector<std::string> & filenames)
{
  for (auto & filename : filenames)
    addTransitionsFromFile(filename);
}

void TransitionSet::addTransitionsFromFile(const std::string & filename)
{
  FILE * file = std::fopen(filename.c_str(), "r");
  if (!file)
    util::myThrow(fmt::format("cannot open file '{}'", filename));

  char readBuffer[1024];

  while (!std::feof(file))
  {
    if (readBuffer != std::fgets(readBuffer, 1024, file))
      break;

    std::string transitionName = readBuffer;
    if (transitionName.back() == '\n')
      transitionName.pop_back();

    transitions.emplace_back(transitionName);
  }

  std::fclose(file);
}

std::vector<std::pair<Transition*, int>> TransitionSet::getAppliableTransitionsCosts(const Config & c)
  using Pair = std::pair<Transition*, int>;
  std::vector<Pair> appliableTransitions;

  for (unsigned int i = 0; i < transitions.size(); i++)
    if (transitions[i].appliable(c))
      appliableTransitions.emplace_back(&transitions[i], transitions[i].getCost(c));

  std::sort(appliableTransitions.begin(), appliableTransitions.end(), 
  [](const Pair & a, const Pair & b)
  {
    return a.second < b.second;
  });

  return appliableTransitions;
}

Franck Dary's avatar
Franck Dary committed
std::vector<Transition *> TransitionSet::getNAppliableTransitions(const Config & c, int n)
{
  std::vector<Transition *> result;

  for (unsigned int i = 0; i < transitions.size(); i++)
Franck Dary's avatar
Franck Dary committed
    if (transitions[i].appliable(c))
      result.emplace_back(&transitions[i]);

  if ((int)result.size() > n)
    util::myThrow(fmt::format("there are {} appliable transitions n = {}\n", result.size(), n));

Franck Dary's avatar
Franck Dary committed
  return result;
}

Franck Dary's avatar
Franck Dary committed
std::vector<int> TransitionSet::getAppliableTransitions(const Config & c)
{
  std::vector<int> result;

  for (unsigned int i = 0; i < transitions.size(); i++)
    if (transitions[i].appliable(c))
      result.emplace_back(1);
    else
      result.emplace_back(0);

  return result;
}

Transition * TransitionSet::getBestAppliableTransition(const Config & c)
{
  Transition * result = nullptr;
  int bestCost = std::numeric_limits<int>::max();

  for (unsigned int i = 0; i < transitions.size(); i++)
  {
    if (!transitions[i].appliable(c))
      continue;

    int cost = transitions[i].getCost(c);

    if (cost == 0)
      return &transitions[i];

    if (cost < bestCost)
    {
      result = &transitions[i];
      bestCost = cost;
    }
  }

  return result;
}

std::size_t TransitionSet::size() const
{
  return transitions.size();
}

std::size_t TransitionSet::getTransitionIndex(const Transition * transition) const
{
  if (!transition)
    util::myThrow("transition is null");

  return transition - &transitions[0];
}

Franck Dary's avatar
Franck Dary committed
Transition * TransitionSet::getTransition(std::size_t index)
{
  return &transitions[index];
}

Transition * TransitionSet::getTransition(const std::string & name)
{
  for (auto & transition : transitions)
    if (transition.getName() == name)
      return &transition;

  return nullptr;
}