-
Notifications
You must be signed in to change notification settings - Fork 17.8k
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
reflect: add TypeAssert #62121
Comments
#57060 is a compiler optimization that may obviate the need for this API as this falls under the "short-lived heap allocated value" problem. |
Empirical evidence based on module proxy data on 2023-07-01:
This means at least ~40% usages of the |
As a performance workaround, you could do the following today: func AssertTo[T any](rv reflect.Value) (v T, ok bool) {
if v.CanAddr() {
v, ok = *v.Addr().Interface().(*T)
} else {
v, ok = v.Interface().(T)
}
return v, ok
} It's gross, but works. |
Bikeshed: |
I like |
@ianlancetaylor could I gently nudge this proposal for consideration? It would very slightly help with the encoding/json/v2 work :) |
This proposal has been added to the active column of the proposals project |
Plain 'Assert' might be confusing with C-style asserts. Should we call it TypeAssert? With the Type prefix we may not need the To suffix either. t, ok := reflect.TypeAssert[time.Time](v) I think this reads better than TypeAssertTo. |
Have all remaining concerns about this proposal been addressed? The proposal is to add to package reflect:
|
Based on the discussion above, this proposal seems like a likely accept. The proposal is to add to package reflect:
|
How about also adding
So that sometimes, we can use
instead of
Both of the two functions have their own ideal use cases. |
Let's start with just one. |
No change in consensus, so accepted. 🎉 The proposal is to add to package reflect:
|
Change https://go.dev/cl/591495 mentions this issue: |
The CL for this got abandoned. @dsnet did you want to get it in before the freeze? |
Consider the following benchmark:
This currently prints:
Since the underlying
time.Time
is addressable, theInterface
method must make a copy of it.However, one primary reason to use the
Interface
method is to then assert it to a particular concrete type.I propose the addition of:
which avoids the allocation since the value is never boxed in an interface.
Usage would then look like:
and naturally matches type-assertion construct in the Go language itself.
Ideally, this would be a method on
Value
, but we don't have #49085.If we did, the signature would be:
and usage would be more natural as:
The text was updated successfully, but these errors were encountered: