userlist.go 8.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343
  1. package gamelogic
  2. import (
  3. "sort"
  4. "sync"
  5. "bet24.com/log"
  6. "bet24.com/servers/games/masharie_table/common"
  7. userservices "bet24.com/servers/micros/userservices/proto"
  8. )
  9. type gameLog struct {
  10. serialNumber int // 局数编号
  11. betAmount int // 投注金额
  12. winAmount int // 赢金
  13. loseAmount int // 输金
  14. }
  15. const (
  16. GAME_LOG_COUNT = 20 // 游戏日志记录数量
  17. )
  18. type masharieUser struct {
  19. userId int
  20. nickName string
  21. faceId int
  22. faceUrl string
  23. vipLevel int
  24. vipExpire int
  25. decorations []userservices.UserDecoration
  26. totalBetCount int // 累计投注次数
  27. totalBetAmount int // 累计投注金额
  28. totalWinAmount int // 累计赢金
  29. totalWinCount int // 累计赢次数
  30. gameWinAmount int // 本局实际赢金
  31. recentBetAmount int // 最近投注总额
  32. recentWinAmount int // 最近赢金
  33. recentWinCount int // 最近赢次数
  34. isBet bool
  35. gameLog []gameLog //游戏日志 不下注也清除日志
  36. }
  37. type userlist struct {
  38. users []*masharieUser
  39. lock *sync.RWMutex
  40. }
  41. func newUserList() *userlist {
  42. ret := new(userlist)
  43. ret.lock = &sync.RWMutex{}
  44. return ret
  45. }
  46. // 清除最旧的一条统计数据
  47. func (u *masharieUser) clearGameLog() {
  48. if len(u.gameLog) >= 1 && len(u.gameLog) >= GAME_LOG_COUNT {
  49. // 如果gameLog切片的长度超过限制,那么删除最旧的一条游戏日志
  50. oldestLog := u.gameLog[0]
  51. u.recentBetAmount -= oldestLog.betAmount
  52. u.recentWinAmount -= oldestLog.winAmount
  53. if oldestLog.winAmount > 0 {
  54. u.recentWinCount--
  55. }
  56. u.gameLog = u.gameLog[1:]
  57. }
  58. }
  59. func (u *masharieUser) addGameLog(serialNumber, betAmount, winAmount, loseAmount, totalResult int) {
  60. // 写入的数据 是一个用户一条,并且是结算后的统计数据,所以不需要考虑多条的情况
  61. u.clearGameLog()
  62. //新增
  63. log := gameLog{
  64. serialNumber: serialNumber,
  65. betAmount: betAmount,
  66. winAmount: totalResult,
  67. loseAmount: loseAmount,
  68. }
  69. u.gameLog = append(u.gameLog, log)
  70. u.recentBetAmount += betAmount
  71. u.recentWinAmount += totalResult
  72. if totalResult > 0 {
  73. u.recentWinCount++
  74. }
  75. }
  76. func (ul *userlist) addUser(userId int, nickName string,
  77. faceId int, faceUrl string, vipLevel, vipExpire int, decorations []userservices.UserDecoration) {
  78. ul.lock.Lock()
  79. defer ul.lock.Unlock()
  80. for _, v := range ul.users {
  81. if v.userId == userId {
  82. log.Release("userlist.addUser UserId %d already exist", userId)
  83. return
  84. }
  85. }
  86. u := new(masharieUser)
  87. u.userId = userId
  88. u.nickName = nickName
  89. u.faceId = faceId
  90. u.faceUrl = faceUrl
  91. u.vipLevel = vipLevel
  92. u.vipExpire = vipExpire
  93. u.decorations = decorations
  94. u.totalBetCount = 0
  95. u.totalBetCount = 0
  96. u.totalBetAmount = 0
  97. u.totalWinAmount = 0
  98. u.totalWinCount = 0
  99. u.gameWinAmount = 0
  100. u.recentBetAmount = 0
  101. u.recentWinAmount = 0
  102. u.recentWinCount = 0
  103. ul.users = append(ul.users, u)
  104. }
  105. func (ul *userlist) removeUser(userId int) {
  106. ul.lock.Lock()
  107. defer ul.lock.Unlock()
  108. for k, v := range ul.users {
  109. if v.userId == userId {
  110. ul.users = append(ul.users[:k], ul.users[k+1:]...)
  111. return
  112. }
  113. }
  114. log.Release("userlist.removeUser %d not found", userId)
  115. }
  116. // 结束的时候清理状态,并且根据未下注进行连胜扣减
  117. func (ul *userlist) clearBetStatus(serialNumber int) {
  118. ul.lock.Lock()
  119. defer ul.lock.Unlock()
  120. for _, v := range ul.users {
  121. //无论是否下注都要计算参与游戏局数
  122. if !v.isBet {
  123. //如果没有下注清除连胜
  124. // if v.recentStreakWin > 0 {
  125. // v.recentStreakWin = 0
  126. // }
  127. //没有下注也添加日志 解决参与的局数超过20局以后 每局都被清除上一局数据的问题
  128. v.addGameLog(serialNumber, 0, 0, 0, 0)
  129. } else {
  130. v.isBet = false
  131. }
  132. v.gameWinAmount = 0
  133. }
  134. }
  135. func (ul *userlist) addResult(userId, serialNumber, betAmount, winAmount, loseAmount, totalResult int) {
  136. // log.Debug("userlist.addResult %d,betAmount:%d,winAmount:%d,loseAmount:%d,totalResult:%d", userId, betAmount, winAmount, loseAmount, totalResult)
  137. ul.lock.Lock()
  138. defer ul.lock.Unlock()
  139. for _, v := range ul.users {
  140. if v.userId == userId {
  141. // if recentStreakWin < 0 {
  142. // v.recentStreakWin = 0
  143. // }
  144. if totalResult > 0 {
  145. v.totalWinAmount = v.totalWinAmount + totalResult
  146. v.gameWinAmount = totalResult
  147. //v.recentStreakWin = v.recentStreakWin + winAmount
  148. v.totalWinCount++
  149. }
  150. v.addGameLog(serialNumber, betAmount, winAmount, loseAmount, totalResult)
  151. return
  152. }
  153. }
  154. log.Release("userlist.addResult %d not found", userId)
  155. }
  156. func (ul *userlist) addBet(userId, amount, betId int) {
  157. ul.lock.Lock()
  158. defer ul.lock.Unlock()
  159. for _, v := range ul.users {
  160. if v.userId == userId {
  161. v.totalBetAmount += amount
  162. v.totalBetCount++
  163. v.isBet = v.totalBetAmount > 0
  164. return
  165. }
  166. }
  167. log.Release("userlist.addBet %d not found", userId)
  168. }
  169. func (ul *userlist) clearBet(userId, amount int) {
  170. ul.lock.Lock()
  171. defer ul.lock.Unlock()
  172. for _, v := range ul.users {
  173. if v.userId == userId {
  174. v.totalBetAmount -= amount
  175. v.totalBetCount--
  176. v.isBet = v.totalBetAmount > 0
  177. //撤销下注,不需要更新下注区域
  178. return
  179. }
  180. }
  181. log.Release("userlist.addBet %d not found", userId)
  182. }
  183. // 幸运星
  184. func (ul *userlist) getLuckyStarUsers(count, bankerId int) []common.ScoreUser {
  185. ul.lock.Lock()
  186. defer ul.lock.Unlock()
  187. //先考虑最近赢金次数,如果次数相同考虑赢金数,如果赢金数相同考虑投注数
  188. sort.Slice(ul.users, func(i, j int) bool {
  189. if ul.users[i].recentWinCount > ul.users[j].recentWinCount {
  190. return true
  191. } else if ul.users[i].recentWinCount == ul.users[j].recentWinCount {
  192. if ul.users[i].recentWinAmount > ul.users[j].recentWinAmount {
  193. return true
  194. } else if ul.users[i].recentWinAmount == ul.users[j].recentWinAmount {
  195. if ul.users[i].totalBetAmount > ul.users[j].totalBetAmount {
  196. return true
  197. }
  198. }
  199. }
  200. return false
  201. })
  202. ret := []common.ScoreUser{}
  203. for k, v := range ul.users {
  204. if k >= count {
  205. break
  206. }
  207. //不限制赢金次数大于0
  208. // if v.recentWinCount <= 0 {
  209. // break
  210. // }
  211. if v.userId == bankerId {
  212. continue
  213. }
  214. info := make([]int, 0, 2)
  215. info = append(info, v.recentWinCount) //赢局数
  216. info = append(info, v.recentBetAmount) //投注数
  217. u := common.ScoreUser{UserId: v.userId,
  218. NickName: v.nickName,
  219. FaceId: v.faceId,
  220. FaceUrl: v.faceUrl,
  221. VipLevel: v.vipLevel,
  222. VipExpire: v.vipExpire,
  223. Decorations: v.decorations,
  224. Info: info}
  225. ret = append(ret, u)
  226. }
  227. return ret
  228. }
  229. // 每回合赢金排行 最近的
  230. func (ul *userlist) getWinGoldRankingUsers(count, bankerSettle, bankerId, bankerFaceId int, bankerFaceUrl string) []common.ScoreUser {
  231. ul.lock.Lock()
  232. defer ul.lock.Unlock()
  233. ret := []common.ScoreUser{}
  234. if len(ul.users) == 0 {
  235. //没有人下注
  236. return ret
  237. }
  238. //排序
  239. sort.Slice(ul.users, func(i, j int) bool {
  240. return ul.users[i].gameWinAmount > ul.users[j].gameWinAmount
  241. })
  242. info := make([]int, 0, 1)
  243. //如果赢最多的也没有庄家赢得多,则返回庄家信息
  244. if ul.users[0].gameWinAmount <= 0 || ul.users[0].gameWinAmount <= bankerSettle {
  245. info = append(info, bankerSettle)
  246. u := common.ScoreUser{UserId: bankerId,
  247. NickName: "",
  248. FaceId: bankerFaceId,
  249. FaceUrl: bankerFaceUrl,
  250. Info: info}
  251. ret = append(ret, u)
  252. return ret
  253. }
  254. for k, v := range ul.users {
  255. if k >= count {
  256. break
  257. }
  258. if v.gameWinAmount <= 0 {
  259. break
  260. }
  261. if v.userId == bankerId {
  262. continue
  263. }
  264. info = append(info, v.gameWinAmount)
  265. u := common.ScoreUser{UserId: v.userId,
  266. NickName: v.nickName,
  267. FaceId: v.faceId,
  268. FaceUrl: v.faceUrl,
  269. VipLevel: v.vipLevel,
  270. VipExpire: v.vipExpire,
  271. Decorations: v.decorations,
  272. Info: info}
  273. ret = append(ret, u)
  274. }
  275. return ret
  276. }
  277. // 传递0表示不限制数量 最近的
  278. func (ul *userlist) getBetGoldRankingUsers(count int) []common.ScoreUser {
  279. ul.lock.Lock()
  280. defer ul.lock.Unlock()
  281. //排序
  282. sort.Slice(ul.users, func(i, j int) bool {
  283. return ul.users[i].recentBetAmount > ul.users[j].recentBetAmount
  284. })
  285. ret := []common.ScoreUser{}
  286. for k, v := range ul.users {
  287. if k >= count && count != 0 {
  288. break
  289. }
  290. if v.recentBetAmount < 0 {
  291. break
  292. }
  293. info := make([]int, 0, 2)
  294. info = append(info, v.recentWinCount) //赢局数
  295. info = append(info, v.recentBetAmount) //投注数
  296. u := common.ScoreUser{UserId: v.userId,
  297. NickName: v.nickName,
  298. FaceId: v.faceId,
  299. FaceUrl: v.faceUrl,
  300. VipLevel: v.vipLevel,
  301. VipExpire: v.vipExpire,
  302. Decorations: v.decorations,
  303. Info: info}
  304. ret = append(ret, u)
  305. }
  306. return ret
  307. }