-
-
Notifications
You must be signed in to change notification settings - Fork 5.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Make map() and broadcast() faster for Union{T, Missing/Nothing} element types #25828
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -573,12 +573,11 @@ function collect_to!(dest::AbstractArray{T}, itr, offs, st) where T | |
i = offs | ||
while !done(itr, st) | ||
el, st = next(itr, st) | ||
S = typeof(el) | ||
if S === T || S <: T | ||
if el isa T || typeof(el) === T | ||
@inbounds dest[i] = el::T | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. if you remove the |
||
i += 1 | ||
else | ||
R = promote_typejoin(T, S) | ||
R = promote_typejoin(T, typeof(el)) | ||
new = similar(dest, R) | ||
copyto!(new,1, dest,1, i-1) | ||
@inbounds new[i] = el | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -500,14 +500,13 @@ end | |
@nexprs $nargs i->(@inbounds val_i = _broadcast_getindex(A_i, I_i)) | ||
# call the function | ||
V = @ncall $nargs f val | ||
S = typeof(V) | ||
# store the result | ||
if S <: eltype(B) | ||
if V isa eltype(B) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. +1 This syntax allows the compiler to see / "prove" that |
||
@inbounds B[I] = V | ||
else | ||
# This element type doesn't fit in B. Allocate a new B with wider eltype, | ||
# copy over old values, and continue | ||
newB = Base.similar(B, promote_typejoin(eltype(B), S)) | ||
newB = Base.similar(B, promote_typejoin(eltype(B), typeof(V))) | ||
for II in Iterators.take(iter, count) | ||
newB[II] = B[II] | ||
end | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The need for
typeof(el) === T
is a bit of a mystery, but it was weird to need it in the existing code already. See #25799.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I assume that was some attempt at providing a fast-path for uninferred code. But
S === T
is often much harder to infer thanS <: T
. And sinceisconcretetype(S)
, it won't be faster at runtime either.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yet if I remove that check I get a worse performance than before with
map(identity, y)
(see what I noted at #25799). That's really weird, but...There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Keno recently changed the result of
el isa T
fromConst(true)
toConditional(:el, T, Union{})
– maybe there's was a mistake in the implementation of that?There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Where's the relevant commit? Can I try reverting it?