结构中的 Golang 切片不附加新值,只保留第一个值

问题描述 投票:0回答:2

我有一个代码需要添加新的值。 目标是吸收用户和报价,为此我创建了一个名为“UserQuote”的结构。

type UserQuote struct {
        User        models.User
        QuoteNumbers []int
    }

每个用户都会有一些语录,但语录需要同化到一个用户。 我创建了一些循环,为我之前选择的用户获取报价和随机同化。这个用户如果是另一种类型的结构,这对我的问题并不重要,但你需要知道它们存储在名为 usersThatBuySweepstakeNumbersBySweepstake 的切片中。

for _, quote := range availableQuotes {
        rand.Seed(time.Now().UnixNano())
        randomIndex := rand.Intn(len(usersThatBuySweepstakeNumbersBySweepstake))
        selectedUser := usersThatBuySweepstakeNumbersBySweepstake[randomIndex]
        selectedUserIsInList := false
        for _, userQuote := range usersQuotes {
            if userQuote.User.ID == selectedUser.ID {
                userQuote.QuoteNumbers = append(userQuote.QuoteNumbers, quote)
                selectedUserIsInList = true
            }
        }

        if !selectedUserIsInList {
            usersQuotes = append(usersQuotes, UserQuote{
                User:        selectedUser,
                QuoteNumbers: []int{quote},
            })
        }
    }

如果用户没有预先关联的引用,则他不会被插入到结构体 UserQuote 数组中。在这种情况下,他被插入到以下代码片段中(是上一个代码片段的一部分):

if !selectedUserIsInList {
            usersQuotes = append(usersQuotes, UserQuote{
                User:        selectedUser,
                QuoteNumbers: []int{quote},
            })
        }

如您所见,“QuoteNumbers”数组已初始化 但是,如果他已经被插入,struct 里面的“QuoteNumbers”数组应该被追加,这里我们有一个问题:不是追加!代码被截断了

for _, userQuote := range usersQuotes {
            if userQuote.User.ID == selectedUser.ID {
                userQuote.QuoteNumbers = append(userQuote.QuoteNumbers, quote)
                selectedUserIsInList = true
            }
        }

代码仅插入此切片“QuoteNumbers”的第一个元素,之后不追加。

我正在使用调试执行应用程序,并且确定调用了“追加”而不是预期的,但是切片只保留在创建结构的“实例”时插入的第一个元素

以下代码被剪断了所有代码,但一起订购:

type UserQuote struct {
        User        models.User
        QuoteNumbers []int
    }
    usersQuotes := make([]UserQuote, 0)

    //TODO
    if len(usersThatBuySweepstakeNumbersBySweepstake) == 0 {

    }

    availableQuotes := GetAvailableSweepStakesNumbersNumbers(sweepStake.ID)
    if availableQuotes == nil || len(availableQuotes) == 0 {
        c.AbortWithStatusJSON(400, gin.H{
            "message": "Não há mais números disponíveis para este sorteio",
        })
    }

    //TODO
    for _, quote := range availableQuotes {
        rand.Seed(time.Now().UnixNano())
        randomIndex := rand.Intn(len(usersThatBuySweepstakeNumbersBySweepstake))
        selectedUser := usersThatBuySweepstakeNumbersBySweepstake[randomIndex]
        selectedUserIsInList := false
        for _, userQuote := range usersQuotes {
            if userQuote.User.ID == selectedUser.ID {
                userQuote.QuoteNumbers = append(userQuote.QuoteNumbers, quote)
                selectedUserIsInList = true
            }
        }

        if !selectedUserIsInList {
            usersQuotes = append(usersQuotes, UserQuote{
                User:        selectedUser,
                QuoteNumbers: []int{quote},
            })
        }
    }

我的“附加”有什么问题?

go slice
2个回答
0
投票

When

append
ing elements to
slice
using a
range
loop, you should update the slice element using the loop index instead of update the local variable (in you case the
userQuote
):

for _, quote := range availableQuotes {
    // ...
    for i, userQuote := range usersQuotes {
        if userQuote.User.ID == selectedUser.ID {
            usersQuotes[i].QuoteNumbers = append(usersQuotes[i].QuoteNumbers, quote) // update the slice indexed object
            selectedUserIsInList = true
        }
    }

    if !selectedUserIsInList {
        usersQuotes = append(usersQuotes, UserQuote{
            User:        selectedUser,
            QuoteNumbers: []int{quote},
        })
    }
}

0
投票

问题似乎与您在创建新的 UserQuote 结构时如何初始化 QuoteNumbers 切片有关。

在创建新 UserQuote 结构的代码片段中,使用 []int{quote} 初始化 QuoteNumbers 切片,这意味着它将只有一个元素。这对于用户还没有任何关联引号的情况是正确的,但是当您尝试附加到现有的 UserQuote 结构时,您应该使用现有值初始化 QuoteNumbers 切片。

要解决此问题,您可以修改代码片段,以便在附加到现有 UserQuote 结构时使用现有值初始化 QuoteNumbers 切片。这是更新的代码。

for _, userQuote := range usersQuotes {
if userQuote.User.ID == selectedUser.ID {
    userQuote.QuoteNumbers = append(userQuote.QuoteNumbers, quote)
    selectedUserIsInList = true
    break
 }
}

if !selectedUserIsInList {
 usersQuotes = append(usersQuotes, UserQuote{
    User: selectedUser,
    QuoteNumbers: []int{quote},
 })
}

当您追加到现有的 UserQuote 结构时,您可以使用追加函数将新报价添加到现有的 QuoteNumbers 切片中,就像您之前所做的那样。但是,您还将 selectedUserIsInList 设置为 true 并跳出循环以确保您不会为同一用户创建新的 UserQuote 结构。

如果你仍然对 append 函数没有向切片添加新元素有问题,你可以尝试打印出切片的值和 append 函数中涉及的变量,看看它们是否是你期望的那样

© www.soinside.com 2019 - 2024. All rights reserved.