lua——牛牛牌型处理相关算法,中——牌型判定

牛牛的牌型按从小到大的顺序分为:无牛<有牛<牛牛<银牛<金牛<炸弹<五小牛。

算牛的方式为:先选出三张牌,若能组成十的整数倍 即为有牛,然后再看剩余两张牌除以十的余数。余几就是牛几,若正好也能整除十,即为牛牛。若无法选出三张组成十的整数倍的牌即为无牛。

银牛:1张10 加4张大于10的牌

金牛:5张大于10的牌

炸弹:存在四张相同的牌

五小牛:五张牌总数值相加小于等于10

首先定义牌型,因为客户端不同数的牛显示不一样,所以把有牛的九种情况都分开定义

[plain]view plaincopy

  1. --五小牛>炸弹>金牛>银牛>牛牛>有牛>没牛
  2. CardType =
  3. {
  4. NOT_NIU=0, --没牛
  5. NIU_1 =1, --牛一
  6. NIU_2 =2, --牛二
  7. NIU_3 =3, --牛三
  8. NIU_4 =4, --牛四
  9. NIU_5 =5, --牛五
  10. NIU_6 =6, --牛六
  11. NIU_7 =7, --牛七
  12. NIU_8 =8, --牛八
  13. NIU_9 =9, --牛九
  14. NIU_NIU =10, --牛牛
  15. SILVER_NIU =11, --银牛
  16. GOLD_NIU=12, --金牛
  17. BOMB = 13, --炸弹
  18. SMALL_NIU = 14, --五小牛
  19. }

为了方便计算,在判定牌型前要对牌进行排序。

[plain]view plaincopy

  1. function compByCardsValue(a, b)
  2. if a.card_value < b.card_value then
  3. return true
  4. end
  5. if a.card_value > b.card_value then
  6. return false
  7. end
  8. return a.card_color < b.card_color
  9. end
  10. function cardTool.sortByCardsValue(cards)
  11. table.sort(cards, compByCardsValue);
  12. end

下面进行牌值的判定,先计算特殊的牌型

[plain]view plaincopy

  1. function cardTool.is_small_niu(cards)
  2. local sum = 0
  3. for i = 1,#cards do
  4. sum = sum + cards[i].card_count
  5. end
  6. if sum <= 10 then
  7. return true
  8. else
  9. return false
  10. end
  11. end
  12. function cardTool.is_bomb(cards)
  13. if cards[1].card_value == cards[4].card_value then
  14. return true
  15. elseif cards[2].card_value == cards[5].card_value then
  16. return true
  17. else
  18. return false
  19. end
  20. end
  21. function cardTool.is_gold_niu(cards)
  22. if cards[1].card_value > 10 then
  23. return true
  24. else
  25. return false
  26. end
  27. end
  28. function cardTool.is_silver_niu(cards)
  29. if cards[2].card_value > 10 and cards[1].card_value == 10 then
  30. return true
  31. else
  32. return false
  33. end
  34. end

判定牛数的算法其实很简单,我们先算出五张牌总值除以十的余数,然后再枚举两张牌,若存在两张牌之和除以十的余数等于五张牌除以十的余数,那么其他三张牌必然总和为十的倍数。那么这个余数就是牛数。

[plain]view plaincopy

  1. function cardTool.getNiubyCards(cards)
  2. local lave = 0 --余数
  3. for i = 1,#cards do
  4. lave = lave + cards[i].card_count
  5. end
  6. lave = lave % 10
  7. for i = 1,#cards - 1 do
  8. for j = i + 1,#cards do
  9. if(cards[i].card_count+cards[j].card_count)%10 == lave then
  10. if lave == 0 then
  11. return 10
  12. else
  13. return lave
  14. end
  15. end
  16. end
  17. end
  18. return 0
  19. end

这样我们所有分支牌型的判定逻辑就都实现了,下面写出接口

[plain]view plaincopy

  1. function cardTool.getTypebyCards(cards)
  2. cardTool.sortByCardsValue(cards)
  3. local cardtype = CardType.NOT_NIU
  4. if cardTool.is_small_niu(cards) then
  5. cardtype = CardType.SMALL_NIU
  6. return cardtype
  7. end
  8. if cardTool.is_bomb(cards) then
  9. cardtype = CardType.BOMB
  10. return cardtype
  11. end
  12. if cardTool.is_gold_niu(cards) then
  13. cardtype = CardType.GOLD_NIU
  14. return cardtype
  15. end
  16. if cardTool.is_silver_niu(cards) then
  17. cardtype = CardType.SILVER_NIU
  18. return cardtype
  19. end
  20. cardtype=cardTool.getNiubyCards(cards)
  21. return cardtype
  22. end

翻译函数:

[plain]view plaincopy

  1. function cardTool.getCardTypeNamebyType(CardType)
  2. if CardType==0 then
  3. return "没牛"
  4. end
  5. if CardType==1 then
  6. return "牛一"
  7. end
  8. if CardType==2 then
  9. return "牛二"
  10. end
  11. if CardType==3 then
  12. return "牛三"
  13. end
  14. if CardType==4 then
  15. return "牛四"
  16. end
  17. if CardType==5 then
  18. return "牛五"
  19. end
  20. if CardType==6 then
  21. return "牛六"
  22. end
  23. if CardType==7 then
  24. return "牛七"
  25. end
  26. if CardType==8 then
  27. return "牛八"
  28. end
  29. if CardType==9 then
  30. return "牛九"
  31. end
  32. if CardType==10 then
  33. return "牛牛"
  34. end
  35. if CardType==11 then
  36. return "银牛"
  37. end
  38. if CardType==12 then
  39. return "金牛"
  40. end
  41. if CardType==13 then
  42. return "炸弹"
  43. end
  44. if CardType==14 then
  45. return "五小牛"
  46. end
  47. return "异常牌型"
  48. end

我们依然引用之前的测试函数来查看一下输出:

[plain]view plaincopy

  1. print_t(cardTool.getCardTypeNamebyType(cardTool.getTypebyCards(cards1)))
  2. print_t(cardTool.getCardNamebyCards(cards1))
  3. print_t(cardTool.getCardTypeNamebyType(cardTool.getTypebyCards(cards2)))
  4. print_t(cardTool.getCardNamebyCards(cards2))

[plain]view plaincopy

  1. 牛牛
  2. 梅花3方块8方块9黑桃J红桃K
  3. 牛五
  4. 黑桃6红桃9方块10梅花J方块K

以上就是牌型判定相关的处理函数,下一章我们实现牌型比较的相关逻辑。