阿里测评题目:跑得快
题目描述
单牌:一张一张的出牌,大小顺序是2>A>K>Q>J>10>9>8>7>6>5>4>3。
顺子:5张以上连续的单牌,最大JQKA2,最小A2345
对子:成双出牌,大小顺序:2对>A对>K对>Q对>J对>10对>9对>8对>7对>6对>5对>4对>3对。
连对:两个及以上相连的对子比如:2233 778899 其中2233也可以连,但是是最小的连队,AA2233是最小的三连对。
三带一:三张相同的牌可带一张单牌,最大三个2,三个对应牌大过对方即可,带1个的随机。
炸弹:四个相同的牌,可以大过其他牌,最大四个2
为简化起见
1,输入输出,10用字符I表示,且所有字符都大写
2,出牌时,对于能大过的请输出最小的能大过的牌即可
3,本次答题可以暂不考虑三带一规则
要求
编译器版本: Java 1.8.0_66
请使用标准输入输出(System.in, System.out);已禁用图形、文件、网络、系统相关的操作,如java.lang.Process , javax.swing.JFrame , Runtime.getRuntime;不要自定义包名称,否则会报错,即不要添加package answer之类的语句;您可以写很多个类,但是必须有一个类名为Main,并且为public属性,并且Main为唯一的public class,Main类的里面必须包含一个名字为’main’的静态方法(函数),这个方法是程序的入口
时间限制: 3S (C/C++以外的语言为: 5 S) 内存限制: 128M (C/C++以外的语言为: 640 M)
输入:
共2行 第一行是你最初抓的13张牌 第二行表示你上家出的牌
输出:
如果能大过,则输出你的出牌,否则输出0
输入范例:
6788999IJKKAA
3344
输出范例:
8899
题目解析
其实这个题目相当的简单,但是在40分钟内编完也不是一件容易的事情,因为代码量还是比较大的。
首先考虑:
- 各种牌型大不过,就要考虑有没有炸弹,如果有则出炸弹,否则出0
- 牌型分析:
- 单牌,1张
- 对子,2张
- 顺子,5+
- 连对,偶数张,且都是成对出现,4+
- 三带一,4张,3张一样,一张不同
- 炸弹,4张一样的
- 针对单牌和对子可以作为一种情况考虑,考虑都是一个key,只不过一个是重复一次,一个是两次
- 对于顺子和连对也可以作为一种情况考虑,考虑的就是一个连起来的数值集合,不同的是顺子要求的是5+张连续的,只重复一次,而连对则是要求3+连续的,只重复离两次。
- 按照34…JQKA2建立合适的映射,达到一个利用字符串比较牌型大小的结果。
代码:
package Test;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class Run {
public static final String ERROR = "0";
public static void main(String[] args) {
String data1 = "67KK889999IJKKAA";
String data2 = "A2345";
String result = runFast(data1, data2);
System.out.println(runFast(data1, data2));
}
/**
* 牌型分析:
* 1.单牌, 1张
* 2.对子, 2张
* 3.顺子, 5+
* 4.连对,偶数张,且都是成对出现,4+
* 5.三带一,4张,3张一样
* 6.炸弹,4张,一样
*
* @param data1
* @param data2
* @return
*/
public static String runFast(String data1, String data2) {
String[] booms = hasBoom(data1);
if (data2.length() == 1 || data2.length() == 2) {
return runFastOneOrTwo(data1, data2, booms);
} else if (data2.length() == 4) {
if (isBoom(data2)) {
return runFastBoom(data1, data2, booms);
} else if (isPair(data2)) {
return runFastPair(data1, data2, booms, 2);
}
return runFastThreeWithOne(data1, data2, booms);
} else if (isPair(data2)) {
return runFastPair(data1, data2, booms, 2);
}
//只剩下顺子的情况
return runFastPair(data1, data2, booms, 1);
}
/**
*
* @param data1
* @param key
* @param length
* @return
*/
private static String getMin(String data1, char key, int length){
String encode = sortEveryChar(createMap(data1));
StringBuilder builder = new StringBuilder();
builder.append('0');
for (int i = 1; i < encode.length(); i++) {
int b = encode.charAt(i) - encode.charAt(i - 1);
if (b != 0){
builder.append('1');
}else {
builder.append('0');
}
}
String keyString = builder.toString();
int start = 0;
int end = 0;
for (int i = 0; i < keyString.length(); i++) {
end = keyString.indexOf('1', start + 1);
if (end == -1){
break;
}else if (encode.charAt(start) > key && end - start >= length){
return encode.substring(start, end);
}else{
start = end;
}
}
return null;
}
private static String runFastThreeWithOne(String data1, String data2, String[] booms) {
char key = getMultiOne(data2);
String result = getMin(data1, key, data2.length());
if (result != null){
String encode = sortEveryChar(createMap(data1));
if (result.charAt(0) == encode.charAt(0) && result.length() == 4){
return resolveMap(result);
}else if (result.charAt(0) == encode.charAt(0) && result.length() == 3){
return resolveMap(result + encode.charAt(3));
}else if (result.charAt(0) != encode.charAt(0)){
return resolveMap(result.substring(0, 3) + encode.charAt(0));
}
}else if (booms != null){
return resolveMap(booms[0]);
}
return ERROR;
}
private static char getMultiOne(String data2) {
String encode = sortEveryChar(createMap(data2));
return encode.charAt(1);
}
public static String asString(char[] arr){
StringBuilder builder = new StringBuilder();
for (char a :
arr) {
builder.append(a);
}
return builder.toString();
}
public static String generateString(char start, int length, int times){
StringBuilder builder = new StringBuilder();
for (int i = 0; i < length; i++) {
for (int j = 0; j < times; j++) {
char temp = (char) (start + i);
builder.append(temp);
}
}
return builder.toString();
}
private static String runFastPair(String data1, String data2, String[] booms, int threshold) {
String key = getKey(createMap(data1), 'B', 'N', threshold);
String dataKey = getKey(createMap(data2), 'B', 'N', threshold);
int keyLen = data2.length() / threshold;
char[] arr = new char[keyLen];
Arrays.fill(arr, '1');
String flag = asString(arr);
if (dataKey.contains(flag)){
//33++
int dest = dataKey.indexOf(flag);
int pos = key.indexOf(flag, dest + 1);
if (pos != -1){
char start = (char) (pos + 'B');
return resolveMap(generateString(start, keyLen, threshold));
}
}else if (dataKey.endsWith("11")){
if (key.startsWith(flag.substring(0, keyLen - 1))){
//2233的类型
return resolveMap(generateString('N', 1, threshold)
+ generateString('B', keyLen - 1, threshold));
}else{
int pos = key.indexOf(flag);
if (pos != -1){
char start = (char) (pos + 'B');
return resolveMap(generateString(start, keyLen, threshold));
}
}
}else if (dataKey.endsWith("1") && key.contains(flag)){
//2233
int pos = key.indexOf(flag);
char start = (char) (pos + 'B');
return resolveMap(generateString(start, keyLen, threshold));
}
return booms == null ? ERROR : resolveMap(booms[0]);
}
private static String getKey(String map, char start, char end, int threshold) {
String encode = sortEveryChar(map);
int[] arr = new int[end - start + 1];
for (int i = 0; i < encode.length(); i++) {
arr[encode.charAt(i) - 'B'] ++;
}
StringBuilder builder = new StringBuilder();
for (int anArr : arr) {
if (anArr >= threshold){
builder.append('1');
}else{
builder.append('0');
}
}
return builder.toString();
}
private static String runFastBoom(String data1, String data2, String[] booms) {
char key = createMap(data2).charAt(0);
if (booms != null){
for (int i = 0; i < booms.length; i++) {
if (booms[i].charAt(0) > key){
return resolveMap(booms[i]);
}
}
}
return ERROR;
}
private static String runFastOneOrTwo(String data1, String data2, String[] booms) {
String result = getMin(data1, createMap(data2).charAt(0), data2.length());
if (result != null){
return resolveMap(result.substring(0, data2.length()));
}else if (booms != null){
return resolveMap(booms[0]);
}
return ERROR;
}
public static String sortEveryChar(String src) {
char[] arr = src.toCharArray();
Arrays.sort(arr);
StringBuilder builder = new StringBuilder();
for (char anArr : arr) {
builder.append(anArr);
}
return builder.toString();
}
public static String[] hasBoom(String src) {
String encode = sortEveryChar(createMap(src));
List<String> result = new ArrayList<>();
for (int i = 0; i < encode.length() - 4; i++) {
String temp = encode.substring(i, i + 4);
if (isBoom(temp)) {
result.add(temp);
}
}
if (result.size() == 0){
return null;
}
String []arr = new String[result.size()];
for (int i = 0; i < result.size(); i++) {
arr[i] = result.get(i);
}
return arr;
}
public static boolean isBoom(String src) {
for (int i = 0; i < src.length(); i++) {
if (src.charAt(i) != src.charAt(0)) {
return false;
}
}
return true;
}
public static boolean isPair(String src) {
char a = 'A';
String encode = createMap(src);
for (int i = 0; i < encode.length(); i++) {
a ^= encode.charAt(i);
}
return a == 'A';
}
public static String createMap(String src) {
StringBuilder builder = new StringBuilder();
for (int i = 0; i < src.length(); i++) {
char temp = src.charAt(i);
if (temp >= '3' && temp <= '9') {
int c = temp - '3';
temp = (char) (c + 'B');
builder.append(temp);
} else if (temp == 'Q') {
builder.append('K');
} else if (temp == 'K') {
builder.append('L');
} else if (temp == 'A') {
builder.append('M');
} else if (temp == '2') {
builder.append('N');
}else{
builder.append(temp);
}
}
return builder.toString();
}
public static String resolveMap(String src) {
StringBuilder builder = new StringBuilder();
for (int i = 0; i < src.length(); i++) {
char temp = src.charAt(i);
if (temp >= 'B' && temp <= 'H') {
int c = temp - 'B';
temp = (char) (c + '3');
builder.append(temp);
} else if (temp == 'K') {
builder.append('Q');
} else if (temp == 'L') {
builder.append('K');
} else if (temp == 'M') {
builder.append('A');
} else if (temp == 'N') {
builder.append('2');
} else if (temp == 'I' || temp == 'J'){
builder.append(temp);
}
}
return builder.toString();
}
}