zoukankan      html  css  js  c++  java
  • 52张扑克牌的Suit(花色)和Rank(牌面大小)排序算法

    前阵子去某家公司笔试,发现有一道扑克牌排序的算法题,题目的大致意思是从一个给定的扑克牌文件读取内容,里面的内容是每行一个扑克牌牌面值,如♠J,♥Q,♣A,♦10等,要求对该文本进行两种排序,一种是按Suit,另一种是Rank;
    如果原文本值为:
    ♠2
    ♠J
    ♥10
    ♠3
    ♣7
    ♦9
    ♠9
    ♦6
    ♠Q
    ♣4
    ♣6
    ♦A
    则Suit输出方式为:♠Q ♠J ♠9 ♠3 ♠2 ♥10 ♦A ♦9 ♦6 ♣7 ♣6 ♣4 (此处suit的大小按照:♠,♥,♦,♣)
    而Rank输出则为: ♦A ♠Q ♠J ♥10 ♠9 ♦9 ♣7 ♦6 ♣6 ♣4 ♠3 ♠2   

    具体算法如下:
    首先定义一个公共类Common,用于读取和写入文件:
      

    View Code
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.IO;
    
    namespace Test.Porker
    {
        public class Common
        {
           public static List<string> ReadFile(string srcFileName)
           {
               var list = new List<string>();
               using (var sr = new StreamReader(srcFileName, Encoding.UTF8))
               {
                   string s = "";
                   while ((s = sr.ReadLine()) != null)
                   {
                       list.Add(s);
                   }
               }
               return list;
           }
    
           public static void WriteFile(string desFileName,List<string> list)
           {
               using (var sw = new StreamWriter(desFileName, true, Encoding.UTF8))
               {
                   foreach (var item in list)
                   {
                       sw.WriteLine(item);                   
                   }
               }
           }
    
         public static void GenerateRandPoker()  
         {  
            List<string> list = new List<string>();  
            for (int i = 2; i <= 14; i++)  
            {  
                if (i <= 10)  
                {  
                    list.Add("" + i);
                    list.Add("" + i);  
                    list.Add("" + i);  
                    list.Add("" + i);  
                }  
                else if (i == 11)  
                {  
                    list.Add("♠J");  
                    list.Add("♣J");  
                    list.Add("♥J");  
                    list.Add("♦J");  
                }  
                else if (i == 12)  
                {  
                    list.Add("♠Q");  
                    list.Add("♣Q");  
                    list.Add("♥Q");  
                    list.Add("♦Q");  
                }  
                else if (i == 13)  
                {  
                    list.Add("♠K");  
                    list.Add("♣K");  
                    list.Add("♥K");  
                    list.Add("♦K");  
                }  
                else if (i == 14)  
                {  
                    list.Add("♠A");  
                    list.Add("♣A");  
                    list.Add("♥A");  
                    list.Add("♦A");  
                }  
            }  
      
            Random r = new Random();  
            for (int i = 0; i < 100; i++)  
            {  
                int n = r.Next(0, 51);  
                int m = r.Next(0, 51);  
                if (n != m)  
                {  
                    string tmp = list[m];  
                    list[m] = list[n];  
                    list[n] = tmp;  
                }  
            }
    
            WriteFile(@"d:\CardSuit.txt", list);
           
        }  
    
        }
    }

    然后添加两个类,分别为SuitSort:

    View Code
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    
    namespace Test.Porker
    {
        public class SuitSort
        {
            public List<string> SuitList { get; set; }
    
            public SuitSort(List<string> list)
            {
                SuitList = list;
            }
    
            public void SortSuitList()
            {
                SuitList.Sort(SuitComparer);            
            }
    
            private static int SuitComparer(string porkerA,string porkerB)
            {
                var a = GetPorkerNumber(porkerA);
                var b = GetPorkerNumber(porkerB);
    
                return a-b;
    
            }
    
            private static int GetPorkerNumber(string porker)
            {
                if (string.IsNullOrEmpty(porker))
                {
                    return 0;
                }
    
                var suitValue = 0; 
                char c = porker[0];
                //此处排序首先考虑的是花色,于是先把花色乘以一个常数区分开来
                switch (c)
                {
                    case '':
                        suitValue = 100;
                        break;
                    case '':
                        suitValue = 200;
                        break;
                    case '':
                        suitValue = 300;
                        break;
                    case '':
                        suitValue = 400;
                        break;
                    default:
                        break;
                }            
    
                var numStr = porker.Substring(1);
                var number = 0;
                //给几个特殊牌赋予一个整数值
                switch (numStr)
                {
                    case "A":
                        number = 14;
                        break;
                    case "K":
                        number = 13;
                        break;
                    case "Q":
                        number = 12;
                        break;
                    case "J":
                        number = 11;
                        break;                
                    default:
                        number =Convert.ToInt32(numStr);
                        break;
                }    
                
                //保证了每个花色都不是在一个数字区间段
                number = (15 - number) + suitValue;           
    
                return number;
            }
        }
    }

    RankSort:

    View Code
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    
    namespace Test.Porker
    {
        public class RankSort
        {        
                public List<string> RankList { get; set; }
    
                public RankSort(List<string> list)
                {
                    RankList = list;
                }
    
                public void SortRankList()
                {
                    RankList.Sort(SuitComparer);
                }
    
                private static int SuitComparer(string porkerA, string porkerB)
                {
                    var a = GetPorkerNumber(porkerA);
                    var b = GetPorkerNumber(porkerB);
    
                    return a - b;
                }
    
                private static int GetPorkerNumber(string porker)
                {
                    if (string.IsNullOrEmpty(porker))
                    {
                        return 0;
                    }
                    var numStr = porker.Substring(1);
                    var number = 0;
                    //给几个特殊牌赋予一个整数值
                    switch (numStr)
                    {
                        case "A":
                            number = 14;
                            break;
                        case "K":
                            number = 13;
                            break;
                        case "Q":
                            number = 12;
                            break;
                        case "J":
                            number = 11;
                            break;
                        default:
                            number = Convert.ToInt32(numStr);
                            break;
                    }
                    
                    //利用15-牌面数值,已达到大的排前面,小的排后面
                    //此处为了区别同一数字的不同花色,在此乘以了一个常数100()一副扑克的牌数总数即可
                    number = (15 - number) * 100;
    
                    //不同的花色再加上一个偏移量,此处根据需要设置花色的大小,我这里的suit排序顺序为:黑、红、方、梅
                    char c = porker[0];
                    switch (c)
                    {
                        case '':
                            number += 1;                        
                            break;
                        case '':
                            number += 2;                        
                            break;
                        case '':
                            number += 3;                        
                            break;
                        case '':
                            number += 4;                       
                            break;
                        default:
                            break;
                    }
    
                    return number;
                }
        }
    }

    这样对于扑克排序的算法基本完成,下面即是验证;首先调用公共类里面的GenerateRandPoker随机生成一副乱序扑克,然后实例化两个类对象进行排序并输出:

    View Code
         static void Main(string[] args)
            {            
    
                Common.GenerateRandPoker();
                var fileName = @"D:\CardSuit.txt";
    
                SuitPorkerTest(fileName);
                RankPorkerTest(fileName);
    
                Console.ReadLine();
            }
    
            static void SuitPorkerTest(string fileName)
            {            
                var destFilename = @"D:\SortedSuitCard.txt";
                var list = Common.ReadFile(fileName);
                SuitSort suitObj = new SuitSort(list);
    
                suitObj.SortSuitList();
                Common.WriteFile(destFilename, suitObj.SuitList);
            }
    
            static void RankPorkerTest(string fileName)
            {            
                var destFilename = @"D:\SortedRankCard.txt";
                var list = Common.ReadFile(fileName);
                RankSort rankObj = new RankSort(list);
    
                rankObj.SortRankList();
                Common.WriteFile(destFilename, rankObj.RankList);
    
    
            }

    扑克文件为:

    ♣2
    ♦Q
    ♠K
    ♥6
    ♠4
    ♥7
    ♥8
    ♦2
    ♠6
    ♥2
    ♥J
    ♣K
    ♥A
    ♦3
    ♣5
    ♠A
    ♥Q
    ♦8
    ♦K
    ♦J
    ♦7
    ♦5
    ♦10
    ♥3
    ♥5
    ♣10
    ♣3
    ♥9
    ♠10
    ♣9
    ♥4
    ♠8
    ♠7
    ♣8
    ♥K
    ♣Q
    ♠5
    ♦4
    ♣A
    ♣J
    ♠2
    ♠J
    ♥10
    ♠3
    ♣7
    ♠9
    ♦9
    ♦6
    ♠Q
    ♣4
    ♣6
    ♦A
    ♦9
    ♠Q
    ♥3
    ♣6
    ♠J
    ♦K
    ♦J
    ♣10
    ♦5
    ♥2
    ♦4
    ♠9
    ♣7
    ♦6
    ♦7
    ♣8
    ♥4
    ♠7
    ♦Q
    ♣3
    ♥10
    ♥5
    ♣J
    ♥9
    ♦10
    ♣2
    ♦8
    ♦2
    ♥K
    ♠5
    ♥Q
    ♦3
    ♣Q
    ♣A
    ♣5
    ♠3
    ♠A
    ♥6
    ♠6
    ♥J
    ♣9
    ♣4
    ♠10
    ♠8
    ♠4
    ♣K
    ♠2
    ♠K
    ♥7
    ♥A
    ♥8
    ♦A

    Suit排序结果为:

    ♠A,♠K,♠Q,♠J,♠10,♠9,♠8,♠7,♠6,♠5,♠4,♠3,♠2,♥A,♥K,♥Q,♥J,♥10,♥9,♥8,♥7,♥6,♥5,♥4,♥3,♥2,♦A,♦K,♦Q,♦J,♦10,♦9,♦8,♦7,♦6,♦5,♦4,♦3,♦2,♣A,♣K,♣Q,♣J,♣10,♣9,♣8,♣7,♣6,♣5,♣4,♣3,♣2

    Rank排序结果为:

    ♠A,♥A,♦A,♣A,♠K,♥K,♦K,♣K,♠Q,♥Q,♦Q,♣Q,♠J,♥J,♦J,♣J,♠10,♥10,♦10,♣10,♠9,♥9,♦9,♣9,♠8,♥8,♦8,♣8,♠7,♥7,♦7,♣7,♠6,♥6,♦6,♣6,♠5,♥5,♦5,♣5,♠4,♥4,♦4,♣4,♠3,♥3,♦3,♣3,♠2,♥2,♦2,♣2

    此处参考了 52张扑克牌排序算法 方法,在此引用和学习,希望见谅!

      

    凡事对得起自己!
  • 相关阅读:
    行为型模式之备忘录模式
    行为型模式之中介者模式
    行为型模式之迭代器模式
    行为型模式之解释器模式
    行为型模式之命令模式
    行为型模式之职责链模式
    结构型模式之代理模式
    结构型模式之享元模式
    进入Linux的新世界
    302转向与网址劫持(转)
  • 原文地址:https://www.cnblogs.com/aeron/p/2802905.html
Copyright © 2011-2022 走看看