алгоритм, чтобы найти лучшее совпадение, которое может не вернуть ни одного - PullRequest
3 голосов
/ 13 июля 2011

У меня есть некоторые входы, которые могут быть временно недоступны, и с которыми связана ошибка.

struct sensorVal
{
    bool available;
    double error;
    double val;
    bool betterThan(const sensorVal* that) const;
}

Я ищу алгоритм, который найдет лучший доступный вход.Моя лучшая попытка на данный момент - использовать min_element следующим образом:

bool sensorVal::betterThan(const sensorVal& that) const
{
    if (available)
    {
        if (that.available)
            return (error < that.error);
        return true;
    }
    return false;
}

bool betterThan(const sensorVal& lhs, const sensorVal& rhs)
{
    return lhs.betterThan(rhs);
}

std::vector<sensorVal>::const_iterator 
find_best(const std::vector<sensorVal>& inputs)
{
    std::vector<sensorVal>::const_iterator best;

    best = min_element(inputs.begin(), inputs.end(), betterThan);

    if (best->available)
        return best;

    return inputs.end();
}

Это работает нормально, за исключением случаев, когда все входы помечены как недоступные.В этом случае лучше всего установить значение inputs.begin(), а затем мне нужно проверить, доступно ли оно.

Я бы предпочел установить лучшее значение на inputs.end(), которое уже учтено в моем коде.

Существует ли существующий алгоритм, который может найти наилучшее совпадение, который может вернуть отсутствие подходящих членов?Или способ перефразировать мой тест, чтобы лучше установить inputs.end().

спасибо

Ответы [ 3 ]

2 голосов
/ 14 июля 2011

Может быть, вы просто хотите, чтобы это выглядело немного лучше?

best = min_element(inputs.begin(), inputs.end(), betterThan);
return best->available ? best : inputs.end();
0 голосов
/ 14 июля 2011

Возможно, вы можете использовать std :: partition () для сортировки вектора по доступным и недоступным входам. Затем используйте min_element, чтобы найти лучшее из доступного подмножества.

0 голосов
/ 14 июля 2011

Вместо этого вы можете использовать std::accumulate, но я думаю, что решение, которое у вас уже есть, лучше.

struct best {
  std::vector<sensorVal>::const_iterator end;

  explicit best(std::vector<sensorVal>::const_iterator end) : end(end){}

  std::vector<sensorVal>::const_iterator operator()(std::vector<sensorVal>::const_iterator l, std::vector<sensorVal>::const_iterator r) {
    return (r->available() && (l == end() || r->error < l->error)) ? r : l
  }

};

std::vector<sensorVal>::const_iterator 
find_best(const std::vector<sensorVal>& inputs)
{
  return std::accumulate(inputs.begin(), inputs.end(), inputs.end(), best(inputs.end());
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...