简体   繁体   中英

Is there an idiomatic way to find min/max of transform of array without storing the transform or needlessly recalculating?

I have an array of some data type T on which I have to perform some long_calculation(const T&) and find its minimum value. Because the array is pretty large and the function takes a significant amount of my run-time, I want to do it in a multi-threaded way and in the most efficient way possible. The closest thing to what I'm looking for seems to be std::min_element but it is not a perfect fit because it doesn't seem to work internally with the values it calculates and it doesn't even return the value I want. This forces me to do something like the following.

const auto iter = std::min_element(std::execution::par_unseq,
    my_container.begin(), my_container.end(), [](const T& t1, const T& t2) {
        return long_calculation(t1) < long_calculation(t2);
    }
const auto value = long_calculation(*T1);

The standard guarantees at most N-1 comparisons but without storing the result of long_calculation I expect 2N-2 calculations rather than the optimal N. Or rather 2N-1 because of the final line.

On the other hand, pre-calculating the values and doing the search does N long_calculation s but uses O(N) extra storage which will also have to be dynamically allocated in my case.

Is there any way to do this in a generic fashion in the standard or some 3rd party library? If not, what is the most appropriate way to do this? The ideal solution would be a multi-threaded function that can be called somewhat like this.

const auto min_value = min_of_transform(
    my_container.begin(), my_container.end(), long_calculation);

Use the std::transform_reduce algorithm:

std::transform_reduce(std::execution::par_unseq, my_container.begin(), my_container.end(),
                      std::numeric_limits<T>::max(),
                      [](const auto& x, const auto& y) { return std::min(x, y); },
                      long_calculation);

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM