用JAVA面向对象特性描述现实生活斗地主的过程

最近用面向对象描述现实生活中斗地主的过程

要求如下:

1.一副扑克牌,三个人斗地主,判断是否可以叫地主:有王 || 2个以上的2 || 有炸弹

2.结合底牌判断谁最适合拿底牌(看谁配出的炸弹最多,如果配出的个数相同,则看谁配出的炸弹最大)

代码如下:

import static java.lang.Math.*;// 静态引用,在本文件中可以直接使用Math类中的静态方法,而不用Math.;

 class Test1011
{
	public static void main(String args[])
	{
		// 初始化一副牌
		Pai p = new Pai();
		// 定义三个人数组
		Person person[] = new Person[3];

		// 初始化斗地主三个人
		for (int i = 0; i < person.length; i++)
		{
			person[i] = new Person(17, "玩家" + (i + 1));
		}

		// 轮流给三个人发牌
		for (int i = 0; i < 17; i++)
		{
			for (int j = 0; j < person.length; j++)
			{
				person[j].getPai(p.getPai());
			}
		}

		// 分别输出三个人的牌,并进行判断是否满足叫地主的条件
		for (int i = 0; i < person.length; i++)
		{
			// 1.打印牌
			PrintArr.print(person[i].getPais());
			// 2.判断
			int res = person[i].isCall();
			switch (res)
			{
			case 1:
				System.out.println(" " + person[i].getName() + ":有王叫地主");break;
			case 2:
				System.out.println(" " + person[i].getName() + ":有两个以上的2叫地主");break;
			case 3:
				System.out.println(" " + person[i].getName() + ":有炸弹叫地主");break;
			default :
				System.out.println(" " + person[i].getName() + ":没有资格叫地主");
			}
			System.out.println();
		}
		// 找出三张底牌
		String diPais[] = new String[3];
		System.out.print("三张底牌是:");
		for (int i = 0; i < diPais.length; i++)
		{
			diPais[i] = p.getPai();
			System.out.print(diPais[i] + " ");
		}
		System.out.println();
		
		// 结合底牌检查
		for (int i = 0; i < person.length; i++)
		{
			person[i].checkDiPais(diPais);
		}
		// 对人进行排序
		PrintArr.sort(person);

		if (person[0].getBomCount() > 0)
		{
			// 炸弹的数量
			int bomCount = person[0].getBomCount();
			// 炸弹的值
			int bomNumber = person[0].getBomNumber();
			String name = person[0].getName();// 玩家的名字
			String s = null;

			switch (bomNumber)
			{
			case 16:
				s = "王";break;
			case 15:
				s = "2";break;
			case 14:
				s = "A";break;
			case 13:
				s = "k";break;
			case 12:
				s = "Q";break;
			case 11:
				s = "J";break;
			default :
				s = bomNumber + "";
			}

			System.out.println(name + "最适合拿底牌,可以配出:" + bomCount + "个炸弹,最大的炸弹是:" + s + "炸");
		} else
		{
			System.out.println("都不适合拿底牌");
		}
	}
}

class PrintArr
{
	/* 
	* 对人进行排序
	* 规则:
	* 1.炸弹个数多的排在前面
	* 2.如果两个配出的炸弹个数一样,则比较谁配出的炸弹最大
	*/
	public static void sort(Person person[])
	{
		for (int i = 0; i < person.length - 1; i++)
		{
			int index = i;
			for (int j = i + 1; j < person.length; j++)
			{
				if (person[j].getBomCount() > person[index].getBomCount())
				{
					index = j;
				} else if (person[j].getBomCount() == person[index].getBomCount() && person[j].getBomNumber() > person[index].getBomNumber())
				{
					index = j;
				}
			}
			Person temp = person[i];
			person[i] = person[index];
			person[index] = temp;
		}
	}
	// 对字符串数组进行排序
	public static void sort(String arr[])
	{
		for (int i = 0; i < arr.length - 1; i++)
		{
			int index = i;
			for (int j = i + 1; j < arr.length; j++)
			{
				if (arr[j].charAt(1) < arr[index].charAt(1))
				{
					index = j;
				}
			}

			String temp = arr[i];
			arr[i] = arr[index];
			arr[index] = temp;
		}
	}
	// 打印字符串数组
	public static void print(String arr[])
	{
		sort(arr);// 排序
		for (int i = 0; i < arr.length; i++)
		{
			
			System.out.print(arr[i] + " ");
		}
		System.out.println();
	}
}

class Person
{
	private String pais[];// 牌
	private String name;// 名字
	private int num = 0;// 每个人牌的数量,抽一张牌加1
	private int bomCount = 0;// 炸弹的数量,统计与底牌结合的属性
	private int bomNumber = 0;// 炸弹的值,只是记录最大的炸弹

	public Person(int size, String name)
	{
		
		this.name = name;
		pais = new String[size];
	}
	
	// 得到一张牌
	public void getPai(String pai)
	{
		this.pais[num++] = pai;
	}
	
	// 得到每种牌的数量,用于统计每个人牌的情况
	public int[] getEveryPaiNum()
	{
		int nums[] = new int[14];
		char pm = '\u0000';
		for (int i = 0; i < this.pais.length; i++)
		{
			pm = pais[i].charAt(1);
			switch (pm)
			{
			case '王':
				nums[0]++;break;
			case 'A':
				nums[1]++;break;
			case 'J':
				nums[11]++;break;
			case 'Q':
				nums[12]++;break;
			case 'K':
				nums[13]++;break;
			case '1':
				nums[10]++;break;
			default :
				nums[pm - '0']++;
			}
		}
		return nums;
	}

	/*
	* 判断是否满足叫地主的条件
	* 
	* return 0(不满足叫地主的条件)1(有王叫地主) 2(有两个以上的2)3(有炸弹叫地主)
	*/
	public int isCall()
	{
		int nums[] = this.getEveryPaiNum();
		int res = 0;

		for (int i = 0; i < nums.length; i++)
		{
			switch (i)
			{
			case 0:
				if (nums[i] > 0)
				{
					res = 1;
				}break;
			case 2:
				if (nums[i] > 2)
				{
					res = 2;
				}
			default :
				if (nums[i] == 4)
				{
					res = 3;
				}
			}
		}

		return res;
	}

	// 检查底牌与自己牌的结合情况
	public void checkDiPais(String diPais[])
	{
		// 得到原来牌的情况
		int nums[] = this.getEveryPaiNum();
		// 如果原来的牌有炸弹则清零
		for (int i = 0; i < nums.length; i++)
		{
			// 王炸清零
			if (i == 0)
			{
				if (nums[i] == 2)
				{
					nums[i] = 0;
				}
			}
			// 其他的炸弹
			else
			{
				if (nums[i] == 4)
				{
					nums[i] = 0;
				}
			}
		}
		// 结合底牌的统计
		char pm = '\u0000';
		for (int i = 0; i < diPais.length; i++)
		{
			pm = diPais[i].charAt(1);
			switch (pm)
			{
			case '王':
				nums[0]++;break;
			case 'A':
				nums[1]++;break;
			case 'J':
				nums[11]++;break;
			case 'Q':
				nums[12]++;break;
			case 'K':
				nums[13]++;break;
			case '1':
				nums[10]++;break;
			default :
				nums[pm - '0']++;
			}
		}
		
		// 1.先看3-10 , J Q K的情况
		for (int i = 3; i < 14; i++)
		{
			if (nums[i] == 4)
			{
				this.bomCount++;
				this.bomNumber = i;
			}
		}
		// 2.倒序统计 A 2 王 的情况
		if (nums[0] == 2)
		{
			this.bomCount++;
			this.bomNumber = 16;// 王炸
		} else if (nums[2] == 4)
		{
			this.bomCount++;
			this.bomNumber = 15;// 2炸
		} else if (nums[1] == 4)
		{
			this.bomCount++;
			this.bomNumber = 14;// A炸
		}
	}

	public String[] getPais()
	{
		return this.pais;
	}
	public int getNum()
	{
		return this.num;
	}
	public String getName()
	{
		return this.name;
	}
	public int getBomCount()
	{
		return this.bomCount;
	}
	public int getBomNumber()
	{
		return this.bomNumber;
	}
}

class Pai
{
	private String[] pais;
	private int num;

	public Pai()
	{
		this.num = 54;
		this.pais = new String[num];
		// 初始化牌
		initPais();
	}
	/* 
	* 初始化一副牌的方法
	* 
	* 一张牌是一个字符串:由花色和牌面组成(如:方A)
	*/
	public void initPais()
	{
		String huase[] = {"方", "草", "红", "黑"};
		// 生成四种花色的牌,每种花色分别为13张
		for (int i = 0; i < 52; i++)
		{
			int indexH = i/13;// 花色的下标
			int pm = i%13;// 牌面的值
			String pai = huase[indexH];
			switch (pm)
			{
			case 0:
				pai += "A";break;
			case 10:
				pai += "J";break;
			case 11:
				pai += "Q";break;
			case 12:
				pai += "K";break;
			default :
				pai += (pm + 1);break;
			}
			this.pais[i] = pai;
		}
		this.pais[52] = "小王";
		this.pais[53] = "大王";
	}
	
	/*
	* 随机抽取一张牌
	*/
	public String getPai()
	{
		// 随机产生一个牌的下标
		int index = (int)floor(random() * this.num);
		String pai = this.pais[index];
		// 把index后面的牌一次向前移动
		for (int i = index; i < this.num - 1; i++)
		{
			this.pais[i] = this.pais[i + 1];
			
		}
		// 将牌的数量减减
		this.num--;
		return pai;
	}
	public String[] getPais()
	{
		return this.pais;
	}
	public int getNum()
	{
		return this.num;
	}
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值