1

我正在为过去一年一直在开发的网站实施用户奖励/成就系统。基本前提类似于您在 GameTrailers 或 GiantBomb.com 上找到的内容:用户通过以下操作获得奖励徽章(成就的视觉表示):发表 [x] 条评论,或添加 [x] 条物品到他们的愿望清单等

我正在尝试确定实现此功能的最有效方法,但我有点卡住了。我目前的解决方案是:

  1. 在数据库中创建每个成就(无论如何都会发生)。成就有一个类别、一个接受编号和动态执行的 SQL,以确定是否满足接受。
  2. 每当用户执行可能产生成就的操作(例如对文章发表评论)时,我都会运行 SQL 语句来确定他们有资格获得哪些成就(我根据类别进行过滤,并删除他们的成就)已经完成)。
  3. 从该查询中返回的成就中,我遍历每个并执行动态 SQL 以确定是否满足接受数。如果是这样,则用户完成了成就。

第 2 步和第 3 步是我担心的地方,因为每次用户发表评论时我都会执行这些查询。

下面是上述场景的一个示例(此代码并不完全完美,只是一个模拟......顺便说一句,用户 ID 是我检索的东西,而不是用户输入的东西):

achievements = From ach In searchCtx.Achievements
               Where ach.CategoryID = achievementCategoryID And ach.IsActive = 1
               Select ach 

For Each achmt As Achievement In achievements
    Dim achieved As Boolean
    Dim sqlToExecute As String = qst.SQLToRun
    sqlToExecute = sqlToExecute.Replace("@USERID", "'" + userid.ToString + "'")
    sqlToExecute = sqlToExecute.Replace("@TARGETVAL", achmt.AcceptanceNumber)
    achieved = searchCtx.ExecuteQuery(Of Boolean)(sqlToExecute).First

    If achieved Then
        ' Add Conquest to User Achievemnets
        Dim usrAhmt As New UserAchievement
        usrAhmt .UserID = userid
        usrAhmt .DateCompleted = DateTime.Now
        usrAhmt .AchievementID = achmt .ID
        searchCtx.UserAchievements.InsertOnSubmit(usrAhmt)
    End If

下一个

SqlToExecute 正在调用一个返回布尔值的函数,例如:

select count(id) from comment where userid = @userID

说了这么多,我认为这会奏效,但我担心性能。我对网络编程不太熟悉,但是也许在会话中保留一个 UserStats 对象会更好,然后对其进行操作以确定用户是否发表了足够的评论来完成一项成就?这将不太动态,但对 SQL 服务器的压力可能较小。

我们欢迎所有的建议!!

4

1 回答 1

1

这取决于您有多少用户操作。如果你很少(比如每天不到 10k)你有一个很好的方法,那就别管它了。

如果它更大,您可以将策略更改为仅每隔一段时间执行一次操作,因此不要在每次执行操作时为所有用户调用此函数,而是为过去 30 分钟内活动的所有用户调用此函数立刻。请务必检查该问题在任何给定时间仅运行一次,如果一次检查时间超过 30 分钟,则下一次检查可能无法开始!

或者将信息存储在元表中(使用 cols 用户 ID、评论数等)并相对于用户操作(如增加评论数)操作该表并在每个操作后调用检查。

如需更具体的答案,请提供您拥有多少用户等数据,其中:有多少是活跃用户?每天有多少操作等。关于最佳执行方式的问题在很大程度上取决于用例的统计数据。

于 2011-09-14T22:38:03.850 回答