Several people, including myself, have tried to raise this issue during last months. There were multiple posts on slack, and even a GH issue (Unintuitive argmin and argmax · Issue #39203 · JuliaLang/julia · GitHub). I’ll try to raise it once more, here on discourse, hoping that it gets more traction.
findmax(A) function, which everyone is used to, returns the maximum value in the array
A and its index. However, Julia 1.7 will introduce a
findmax(f, A) version, that doesn’t return any index at all:
julia> A = [5, 1, 3, 8, 0]; julia> maxval, maxix = findmax(A) (8, 4) julia> A[maxix] 8 # but: julia> findmax(identity, A) (8, 8)
There are at least two independent reasons why this feels really weird, confusing, and even surprising (as evidenced by multiple questions on slack).
First: we still have no effecient way to find array index of the maximal value wrt some function! That is, something like (imaginary)
findmax(["a", "bc", "d"], by=length). For arrays and many other collections, obtaining index is a more fundamental operation: easy to go from index to value, hard to go the other way.
findmax(f, A) form, to be introduced in 1.7, is completely inconsistent with both
findmax(A) and with other reductions that take a function and an array:
julia> findfirst([false, false, true]) 3 julia> findfirst(identity, [false, false, true]) 3 # same as above # but: julia> findmax([false, false, true]) (true, 3) julia> findmax(identity, [false, false, true]) (true, true) # definitely not the same
Even the docstrings for these two forms have literally nothing in common:
findmax(A): Return the maximal element of the collection itr and its index or key. findmax(f, A): Returns a pair of a value in the codomain (outputs of f) and the corresponding value in the domain (inputs to f) such that f(x) is maximised.
Currently, any (?) reduction of the form
r(f, A) in base julia is just a more efficient form of
Several different solutions were suggested in the linked GH issue.
I believe the
findmax(f, A) form to-appear-in-1.7 should be removed anyway while it’s not released, and one of those suggested approaches implemented instead, either in 1.7 or later.
NB: discussion above applies to the whole
findmax, findmin, argmax, argmin function family.
As I understand PR Add 2-arg versions of findmax/min, argmax/min by cmcaine · Pull Request #35316 · JuliaLang/julia · GitHub, the motivation for the soon-to-be-released
findmax(f, A) form is based on the mathematical interpretation of
argmax(f, A) == argmax f(x) over x in A. This is, however, not the meaning currently attached to this function family in julia. No optimization package overrides
argmax to perform maximization of
f over some domain, like
argmax(f, 0..Inf). And
findmax(f, A) doesn’t even have this similarity to any mathematical notation.