dongqing344716 2014-08-15 19:13
浏览 29
已采纳

使用文字来进行赋值

I'm using the code in func Root as a guide to create another method Login shown below. In particular, in Root, I assign the literal Book{} to b and then use the result in the Scan. That code doesn't throw any errors (although I'm not sure if it's nice code), but when I try to do something similar in the Login function, which I'm modifying from this blogpost, I get this error

cannot use User literal (type User) as type *User in assignment

for what it's worth, I also get this error right above when I compile

no new variables on left side of :=

but aren't I doing the same thing in the second method, namely assigning the literal u := User{} to a variable and then using it in the scan?

Can you explain using the code below when you can and can't use a literal for type in an assignment?

func Root(w http.ResponseWriter, r *http.Request) {

    rows, err := db.Query("SELECT title, author, description FROM books")
    books := []Book{}
    for rows.Next() {
        b := Book{}
        err := rows.Scan(&b.Title, &b.Author, &b.Description)
        PanicIf(err)
        books = append(books, b)
    }
    ...//code ommitted



func Login(password, email string) (u *User, err error) {
    u := User{}
    db.QueryRow("select * from users where email=$1 ", email).Scan(&u.Id, &u.Password, &u.Email)
    if err != nil {
        return
    }

    err = bcrypt.CompareHashAndPassword(u.Password, []byte(password))
    if err != nil {
        u = nil
    }
    return
}
  • 写回答

2条回答 默认 最新

  • dongxin1999 2014-08-15 21:15
    关注

    Simplifying your example to focus on the essentials:

    package main
    
    import "net/http"
    
    type Book struct{}
    
    type User struct{}
    
    func Root(w http.ResponseWriter, r *http.Request) {
        books := []Book{}
        _ = books
    }
    
    func Login(password, email string) (u *User, err error) {
        // no new variables on left side of :=
        // cannot use User literal (type User) as type *User in assignment
        // u := User{}
        u = &User{}
        return
    }
    
    func main() {}
    

    The function declaration for Login declares a result parameter u *User, a pointer to type User.

    The u := User{} statement is a short variable declaration of type User.

    The Go Programming Language Specification

    Short variable declarations

    A short variable declaration uses the syntax:

    ShortVarDecl = IdentifierList ":=" ExpressionList .

    It is shorthand for a regular variable declaration with initializer expressions but no types:

    "var" IdentifierList = ExpressionList .

    Unlike regular variable declarations, a short variable declaration may redeclare variables provided they were originally declared earlier in the same block with the same type, and at least one of the non-blank variables is new. As a consequence, redeclaration can only appear in a multi-variable short declaration. Redeclaration does not introduce a new variable; it just assigns a new value to the original.

    Since the variable u has already been declared in the same block (u *User), the compiler complains that u := User{} has "no new variables on left side of :=." Write u = User{} for a simple assignment.

    The statement books := []Book{} is a short variable declaration for a new variable, book, in the block.

    The declaration u *User says that u is a pointer to a variable of type User.

    The Go Programming Language Specification

    Composite literals

    Composite literals construct values for structs, arrays, slices, and maps and create a new value each time they are evaluated. They consist of the type of the value followed by a brace-bound list of composite elements. An element may be a single expression or a key-value pair.

    The LiteralType must be a struct, array, slice, or map type (the grammar enforces this constraint except when the type is given as a TypeName). The types of the expressions must be assignable to the respective field, element, and key types of the LiteralType; there is no additional conversion.

    Taking the address of a composite literal generates a pointer to a unique instance of the literal's value.

    The composite literal User{} is a literal value of type User, not *User. The compiler complains that "cannot use User literal (type User) as type *User in assignment." Take the address of the composite literal for a pointer to a literal value of type User (*User). Write u = &User{}.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(1条)

报告相同问题?

悬赏问题

  • ¥15 关于#matlab#的问题:期望的系统闭环传递函数为G(s)=wn^2/s^2+2¢wn+wn^2阻尼系数¢=0.707,使系统具有较小的超调量
  • ¥15 FLUENT如何实现在堆积颗粒的上表面加载高斯热源
  • ¥30 截图中的mathematics程序转换成matlab
  • ¥15 动力学代码报错,维度不匹配
  • ¥15 Power query添加列问题
  • ¥50 Kubernetes&Fission&Eleasticsearch
  • ¥15 報錯:Person is not mapped,如何解決?
  • ¥15 c++头文件不能识别CDialog
  • ¥15 Excel发现不可读取的内容
  • ¥15 关于#stm32#的问题:CANOpen的PDO同步传输问题