Here I found the following code -
// ptr wraps the given value with pointer: V => *V, *V => **V, etc.
func ptr(v reflect.Value) reflect.Value {
pt := reflect.PtrTo(v.Type()) // create a *T type.
pv := reflect.New(pt.Elem()) // create a reflect.Value of type *T.
pv.Elem().Set(v) // sets pv to point to underlying value of v.
return pv
}
As stated, calling this function on variable V of type reflect.Value, which describes an element of type T that holds data d, returns variable VP of type reflect.Value, which describes an element of type *T that points to data d.
When modifying VP by setting it's data to something other then d, V doesn't change (ie by calling VP.Set(..)).
I need a function that returns VP as described above, but so that modifying the data in VP modifies it in V.
The reason I need this function is that I want to extend this stack overflow answer to initialize strings and ints with default values. I wanted to use this stack overflow answer to do it, but for that I need to have a value of a pointer of a struct, not a value of a struct, when running SetString and SetInt.
Thanks,
Related
My problem is that I need a pointer to an element of a list asserted as type T:
e *list.Element
t *T
But if I want to use type assertion, I can only get a copy of e.Value:
if instance, ok := e.Value.(T); ok {
t = &instance
}
How do I get the reference to e.Value as a pointer to type T?
If e stores a value of type T, you can't.
Store *T values in the elements, so you can type assert *T from e.
See related questions:
Get pointer on var obtained via interface
Cannot take the address of map element
How can I store reference to the result of an operation in Go?
How to get the pointer of return value from function call?
I want to iterate over struct definition recursively and for slices get a type of a singular element. Then, create an empty instance of that type. For example:
type Path struct {
Name string
Points []Coordinate
}
type Coordinate struct {
Latitude float64
Longitude float64
}
Assuming that types are unknown at runtime, how can I create an empty instance of the nested type (in the above example Coordinate). I mean:
x := Coordinate{}
When at input I get Path (which can be any other struct, with slices of different types)?
If you have the reflect.Type descriptor of some value, you may use reflect.New() function to obtain a pointer to a new, zeroed value.
This will return you a reflect.Value value. This will be a pointer, to get the reflect.Value of the pointed object, use Value.Elem(). To "unwrap" the value held inside reflect.Value(), you may use Value.Interface().
So if you have a reflect.Type descriptor of a slice, you may use Type.Elem() to get the reflect.Type descriptor of the element type of the slice.
See this example:
p := Path{
Name: "foo",
Points: []Coordinate{
{1.1, 2.2},
{3.3, 4.4},
},
}
v := reflect.ValueOf(p)
f := v.FieldByName("Points")
cv := reflect.New(f.Type().Elem()).Elem()
c := cv.Interface()
fmt.Printf("%#v\n", c)
This outputs (try it on the Go Playground):
main.Coordinate{Latitude:0, Longitude:0}
The official Go site writes as follows:
As the Go specification says, the method set of a type T consists of
all methods with receiver type T, while that of the corresponding
pointer type *T consists of all methods with receiver *T or T. That
means the method set of *T includes that of T, but not the reverse.
This distinction arises because if an interface value contains a
pointer *T, a method call can obtain a value by dereferencing the
pointer, but if an interface value contains a value T, there is no
safe way for a method call to obtain a pointer. (Doing so would allow
a method to modify the contents of the value inside the interface,
which is not permitted by the language specification.)
Even in cases where the compiler could take the address of a value to
pass to the method, if the method modifies the value the changes will
be lost in the caller.
My question is, when can't the compiler take a value to a pointer receiver value?
Addressable is defined in the https://golang.org/ref/spec#Address_operators:
For an operand x of type T, the address operation &x generates a pointer of type *T to x. The operand must be addressable, that is, either a variable, pointer indirection, or slice indexing operation; or a field selector of an addressable struct operand; or an array indexing operation of an addressable array. As an exception to the addressability requirement, x may also be a (possibly parenthesized) composite literal.
A counter examples include map values and functions:
func f() {}
func main() {
var m map[string]string
p1 := &m["foo"] // cannot take the address of m["foo"]
p2 := &f // cannot take the address of f
}
I am trying to understand the representation of a reflection value:
type S struct {
F string `species:"gopher" color:"blue"`
}
var x float64 = 3.4
v := reflect.ValueOf(x)
fmt.Println("v = ", v) // v = 3.4
s := S{}
ss := reflect.ValueOf(s)
fmt.Println("ss = ", ss) // ss = {}
I understand that the representation of a reflection interface value is a two-word pair that gives a pointer to type information and a pointer to the associated value.
What is the reflection representation of a variable. Is it just the value and if so, how is the type determined by code below:
fmt.Println("type:", reflect.TypeOf(x))
If the representation is just value, as it appears to be, where does the code above find the type information?
The type of reflect.TypeOf is:
func TypeOf(i interface{}) Type
When you call reflect.ValueOf(x) in your code, the value of x is implicitly converted to interface{}. At compile time, the type of x is known (float64), and the interface value is represented as you already know; as a two word pair with the pointer to the information for float64 and a pointer to the float64 value (3.4).
The same reasoning applies to s later in your program.
There's very little implicit conversion done between types in Go, but the conversion between values and interfaces when calling a function (or assigning to a variable) is an exception.
From the docs
func (v Value) Elem() Value
Elem returns the value that the interface v contains or that the pointer v points to. It panics if v's Kind is not Interface or Ptr. It returns the zero Value if v is nil.
func Indirect(v Value) Value
Indirect returns the value that v points to. If v is a nil pointer, Indirect returns a zero Value. If v is not a pointer, Indirect returns v.
So can I safely assume the following?
reflect.Indirect(reflect.ValueOf(someX)) === reflect.ValueOf(someX).Elem().
Is Indirect method just a convenience method for the right hand side of the above?
If a reflect.Value is a pointer, then v.Elem() is equivalent to reflect.Indirect(v). If it is not a pointer, then they are not equivalent:
If the value is an interface then reflect.Indirect(v) will return the same value, while v.Elem() will return the contained dynamic value.
If the value is something else, then v.Elem() will panic.
The reflect.Indirect helper is intended for cases where you want to accept either a particular type, or a pointer to that type. One example is the database/sql conversion routines: by using reflect.Indirect, it can use the same code paths to handle the various types and pointers to those types.