卡牌手牌排序算法问题:如何实现先花色后点数排序?
解决手牌先花色后点数的排序问题
嘿,我来帮你搞定这个排序问题!你现在的代码已经能按花色分组,但同花色内的点数乱序,核心问题就是同花色的牌没有按点数从小到大的顺序提取。下面给你两种可行的解决方案,适配不同的代码风格:
方案一:改进现有统计数组的方式
你的代码里用到了hold数组,应该是用来标记某花色某点数的牌是否存在。那只需要在遍历的时候,先按固定的花色顺序走,每个花色下再从最小点数到最大点数依次检查,这样就能保证同花色内的点数有序了。
假设你的花色定义是:梅花=0、方块=1、红桃=2、黑桃=3;点数1代表A,13代表K,代码可以改成这样:
void player::handsort() { // 初始化hold数组,标记各花色各点数是否存在(点数1~13,所以开14个位置) bool hold[4][14] = {false}; // 假设你的手牌存在vector<Card> hands里,Card包含ty(花色)和num(点数)属性 vector<Card> sortedHands; // 第一步:统计所有手牌的花色和点数 for (auto& card : hands) { hold[card.ty][card.num] = true; } // 第二步:按花色优先级遍历,同花色内按点数从小到大取牌 // 先处理梅花 for (int num = 1; num <= 13; ++num) { if (hold[0][num]) { // 找到对应牌加入排序后的列表(如果需要保留原始牌的其他属性,就从hands里找出来) for (auto& card : hands) { if (card.ty == 0 && card.num == num) { sortedHands.push_back(card); break; } } } } // 再处理方块 for (int num = 1; num <= 13; ++num) { if (hold[1][num]) { for (auto& card : hands) { if (card.ty == 1 && card.num == num) { sortedHands.push_back(card); break; } } } } // 红桃、黑桃同理,按你需要的花色顺序添加 // 最后替换原始手牌 hands.swap(sortedHands); }
方案二:用std::sort自定义比较规则(更简洁)
如果你的项目用的是C++,直接用标准库的sort函数,自定义一个比较逻辑,先比花色,花色相同再比点数,代码会更简洁:
// 先定义花色的优先级(按你想要的排序顺序,比如梅花<方块<红桃<黑桃) int getSuitPriority(int suit) { // 这里对应你的花色编码,比如梅花=0,方块=1,红桃=2,黑桃=3 return suit; } // 定义点数的大小关系(A=1 < 2 < ... < 10 < J=11 < Q=12 < K=13) int getRankValue(int rank) { // 如果你的点数已经是1~13的数值,直接返回就行;如果是其他编码,这里做映射 return rank; } void player::handsort() { std::sort(hands.begin(), hands.end(), [](const Card& a, const Card& b) { // 第一步:比较花色优先级 if (getSuitPriority(a.ty) != getSuitPriority(b.ty)) { return getSuitPriority(a.ty) < getSuitPriority(b.ty); } // 第二步:花色相同,比较点数大小 return getRankValue(a.num) < getRankValue(b.num); }); }
为什么你的当前代码不行?
你现在的逻辑应该是把同花色的牌归到一组,但只是按原始手牌的顺序收集,没有对同花色内的点数做排序。比如原始手牌里梅花5在梅花1前面,那排序后梅花5就会先出现。而上面的两种方案,都是强制同花色内按点数从小到大的顺序输出,就能解决问题啦。
内容的提问来源于stack exchange,提问作者T-Wayne1
相关产品推荐
相关产品推荐

