华为OD(2021-04-18)
题目发下来,拖了一周,还是自己太菜没有达标!
第一题:找终点
题⽬描述:
给定⼀个正整数数组,设为 nums ,最⼤为100个成员,求从第⼀个成员开始,正好⾛到数组 最后⼀个成员,所使⽤的最少步骤数。 要求: 1、第⼀步必须从第⼀元素开始,且 1<=第⼀步的步⻓长 <= len/2 ;( len 为数组的⻓长度,需 要⾃⾏解析)。 2、从第⼆步开始,只能以所在成员的数字⾛相应的步数,不能多也不能少,如果⽬标不可达 返回-1,只输出最少的步骤数量。 3、只能向数组的尾部⾛,不能往回⾛。
输⼊描述:
给定⼀个正整数数组,设为 nums ,最⼤为100个成员,求从第⼀个成员开始,正好⾛到数组 最后⼀个成员,所使⽤的最少步骤数。 要求: 1、第⼀步必须从第⼀元素开始,且 1<=第⼀步的步⻓长 <= len/2 ;( len 为数组的⻓长度,需 要⾃⾏解析)。 2、从第⼆步开始,只能以所在成员的数字⾛相应的步数,不能多也不能少,如果⽬标不可达 返回-1,只输出最少的步骤数量。 3、只能向数组的尾部⾛,不能往回⾛。
输⼊描述:
由正整数组成的数组,以空格分隔,数组⻓长度⼩于100,请⾃⾏解析数据数量。
输出描述:
输出描述:
正整数,表示最少的步数,如果不存在输出-1。
输⼊: 7 5 9 4 2 6 8 3 5 4 3 9
输出: 2
输⼊: 7 5 9 4 2 6 8 3 5 4 3 9
输出: 2
AC代码:
import java.util.Scanner; /** * 找终点 * * @author zhangbc * @version v1.0 * @date 2021/4/18 16:07 */ public class Main { public static void main(String[] args) { Scanner sc = new Scanner(System.in); String[] strings = sc.nextLine().split(" "); int[] array = new int[strings.length]; for (int i = 0; i < strings.length; i++) { array[i] = Integer.valueOf(strings[i]); } int dst = Integer.MAX_VALUE; // 计算第二步开始的最少步数达到终点 for (int i = 1; i < array.length / 2; i++) { int d = getNumber(array, i); // 第一步任意,不受限制 if (d != -1) { dst = Math.min(dst, d); } } dst = dst == Integer.MAX_VALUE ? -1 : dst; System.out.println(dst); } private static int getNumber(int[] array, int i) { int step = 1; while (i < array.length) { i += array[i]; step++; if (i == array.length - 1) { return step; } if (i > array.length - 1) { return -1; } } return -1; } }
第二题:报数游戏
题⽬描述:
100个⼈围成⼀圈,每个⼈有⼀个编码,编号从1开始到100,他们从1开始⼀次报数,报到为 M 的⼈⾃动退出圈圈,然后下⼀个⼈接着从1开始报数,直到剩余的⼈数⼩于 M 。请问最后剩 余的⼈在原先的编号为多少?
输⼊描述:
100个⼈围成⼀圈,每个⼈有⼀个编码,编号从1开始到100,他们从1开始⼀次报数,报到为 M 的⼈⾃动退出圈圈,然后下⼀个⼈接着从1开始报数,直到剩余的⼈数⼩于 M 。请问最后剩 余的⼈在原先的编号为多少?
输⼊描述:
输⼊⼀个整数参数 M
输出描述:
输出描述:
如果输⼊参数 M ⼩于等于1或者⼤于等于100,输出 “ ERROR! ”;否则按照原先的编号从⼩到 ⼤的顺序,以英⽂逗号分隔输出编号字符串。
输⼊:
输⼊:
3
4
输出:
输出:
58,91
34,45,97
代码只过0.8,有愿意的可以指点,不慎感激:
import java.util.ArrayList; import java.util.List; import java.util.Scanner; /** * 报数游戏 (80%) * * @author zhangbc * @version v1.0 * @date 2021/4/18 16:07 */ public class Main { public static void main(String[] args) { Scanner sc = new Scanner(System.in); int m = sc.nextInt(); int max = 100; if (m <= 1 || m >= max) { System.out.println("ERROR!"); System.exit(1); } List<Integer> array = new ArrayList<>(16); for (int i = 0; i < max; i++) { array.add(i + 1); } int k = 1, index = 0; while (array.size() >= m) { k++; index++; if (index >= array.size()) { index = index - array.size(); } if (k % m == 0) { System.out.println(array.get(index)); array.remove(index); k = 1; } } StringBuilder sb = new StringBuilder(); for (int j = 0; j < array.size(); j++) { sb.append(array.get(j)); if (j != array.size() - 1) { sb.append(","); } } System.out.println(sb.toString()); } }
第三题:字符串比较
题⽬描述:
给定字符串 A , B 和正整数 V , A 的⻓长度与 B 的⻓长度相等,请计算 A 满⾜如下条件的最⼤ 连续⼦串的⻓长度: 1、该连续⼦串在 A 和 B 中的位置和⻓长度均相同。 2、该连续⼦串 |A[i]-B[i]| 之和⼩于等于 V ,其中 |A[i]-B[i]| 表示两个字⺟ ASCII 码之差的绝对值。 输⼊描述: 输⼊为三⾏: 第⼀⾏为字符串 A ,仅包含⼩写字符, 。 第⼀⾏为字符串 B ,仅包含⼩写字符, 。 第⼀⾏为正整数 V , 。
输出描述:
输出描述:
字符串最⼤连续⼦串的⻓长度,要求该⼦串 |A[i]-B[i]| 之和⼩于等于 V 。
输⼊:
输⼊:
xxcdefg
cdefghi
5
输出:
输出:
2
由于第二题耗时较长,本题只剩30分钟,省题不细,事后补码。
import java.util.Scanner; /** * 字符串比较 (25%) * * 示例:xxcdefg * cdefghi * 5 * * @author zhangbocheng * @version v1.0 * @date 2021/4/18 16:07 */ public class Hw041803 { public static void main(String[] args) { Scanner sc = new Scanner(System.in); String a = sc.nextLine(); String b = sc.nextLine(); int v = sc.nextInt(); StringBuilder sb = new StringBuilder(); // 最长子串的起始位置,及其长度 int start = -1, end = -1, max = 0; // 步长差 int diff; int i = 0; while (i < a.length()) { diff = Math.abs(a.charAt(i) - b.charAt(i)); if (diff > v) { i++; continue; } // 当前子串起始位置及总差之和 int curStart = i, sum = diff; while (sum <= v && i < a.length()) { i++; if (i >= a.length()) { break; } diff = Math.abs(a.charAt(i) - b.charAt(i)); if (diff + sum > v) { break; } else { sum += diff; } } if (max < sum) { max = sum; start = curStart; end = i - 1; } } System.out.println(end - start + 1); } }