Я пытаюсь написать функцию процентиля, которая принимает 2 вектора в качестве входных данных и 1 вектор в качестве вывода. Одним из входных векторов (Distr) будет распределение случайных чисел. Другой входной вектор (Тесты) будет вектором значений, который я хочу рассчитать процентиль от Distr. Результатом будет вектор (тот же размер, что и Тесты), который возвращает процентиль для каждого значения в тестах.C++ Fast Percentile Calculation
Ниже приведен пример того, что я хочу:
Input Distr = {3, 5, 8, 12}
Input Tests = {4, 9}
Output Percentile = {0.375, 0.8125}
Ниже моя реализация в C++:
vector<double> Percentile(vector<double> Distr, vector<double> Tests)
{
double prevValue, nextValue;
vector<double> result;
unsigned distrSize = Distr.size();
std::sort(Distr.begin(), Distr.end());
for (vector<double>::iterator test = Tests.begin(); test != Tests.end(); test++)
{
if (*test <= Distr.front())
{
result.push_back((double) 1/distrSize); // min percentile returned (not important)
}
else if (Distr.back() <= *test)
{
result.push_back(1); // max percentile returned (not important)
}
else
{
prevValue = Distr[0];
for (unsigned sortedDistrIdx = 1; sortedDistrIdx < distrSize; sortedDistrIdx++)
{
nextValue = Distr[sortedDistrIdx];
if (nextValue <= *test)
{
prevValue = nextValue;
}
else
{
// linear interpolation
result.push_back(((*test - prevValue)/(nextValue - prevValue) + sortedDistrIdx)/distrSize);
break;
}
}
}
}
return result;
}
Размер как Distr и испытаний может быть от 2000 до 30000.
Существуют ли существующие библиотеки, которые могут вычислять процентили, как показано выше (или аналогичные)? Если нет, как я могу сделать вышеприведенный код быстрее?
Это поможет, если вместо использования 'push_back' вы предварительно выделите задействованные векторы. – nbubis
Одним из способов является получение ваших входных параметров по ссылке. В настоящий момент большие векторы копируются без причины. –
@JonathanPotter, так как вопрос сортируется, взяв его по ссылке, будет изменен вход. Кроме того, когда обе большие, линейная стоимость копирования является тривиальной частью общего времени. – JSF