type Users struct {
ID int64 `json:"id"`
Username string `json:"username"`
Password string `json:"password"`
Tel string `json:"tel"`
}
rows, err := db.Query("select * from users") //
if err != nil {
fmt.Println(err)
}
defer rows.Close()
user := Users{}
What should I do if I want to auto scan values from rows to user
To auto scan values from the rows
to the user
struct, you can use the Scan
method of the rows
object. The Scan
method takes a variadic parameter of pointers to the values you want to scan into.
Here's an example of how you can scan the values from rows
into the user
struct:
for rows.Next() {
err := rows.Scan(&user.ID, &user.Username, &user.Password, &user.Tel)
if err != nil {
fmt.Println(err)
}
// Do something with the scanned user object
fmt.Println(user)
}
if err = rows.Err(); err != nil {
fmt.Println(err)
}
In the above code, the Scan
method is used to scan the values from each row into the corresponding fields of the user
struct. You need to pass the address of each field as an argument to the Scan
method (using the &
operator).
Note that you need to iterate over the rows using a loop since the Scan
method only scans one row at a time. Finally, you can handle any errors using the rows.Err()
method.
use reflect so I do not need to specify columns
To automatically scan values from rows
into the user
struct without specifying columns, you can use reflection in Go. Here's an example of how you can achieve this:
import (
"database/sql"
"fmt"
"reflect"
)
type Users struct {
ID int64 `json:"id"`
Username string `json:"username"`
Password string `json:"password"`
Tel string `json:"tel"`
}
rows, err := db.Query("SELECT * FROM users")
if err != nil {
fmt.Println(err)
}
defer rows.Close()
// Get the type and fields of the Users struct
userType := reflect.TypeOf(Users{})
fields := make([]interface{}, userType.NumField())
for rows.Next() {
// Create a new instance of the Users struct
user := reflect.New(userType).Elem()
// Get the pointers to the fields of the Users struct
for i := 0; i < userType.NumField(); i++ {
fields[i] = user.Field(i).Addr().Interface()
}
// Scan the values from rows into the fields using reflection
err := rows.Scan(fields...)
if err != nil {
fmt.Println(err)
}
// Do something with the scanned user object
fmt.Println(user.Interface().(Users))
}
if err = rows.Err(); err != nil {
fmt.Println(err)
}
In the above code, we use reflection to automatically scan the values from rows
into the user
struct.
First, we get the type of the Users
struct using reflect.TypeOf()
and create a slice fields
to hold the pointers to the fields of the struct.
Then, for each row in rows
, we create a new instance of the Users
struct using reflect.New()
and get the pointers to the fields by using user.Field(i).Addr().Interface()
.
Finally, we pass the pointers to the Scan
method using the fields...
syntax to scan the values from rows
into the struct fields. We can then use user.Interface().(Users)
to convert the reflect.Value
back into the Users
struct and do something with it.
Note that this approach relies on the assumption that the column names and struct fields have the same names and match in order. If the column names don't match the struct fields, you may need to use tags or other techniques to map the columns to the fields.