【 NO.1 句子中的无效单词数】
解题思路
签到题。
代码展现
class Solution {
public int countValidWords(String sentence) {
String[] words = sentence.split(" "); int count = 0; for (var word : words) { char[] chars = word.trim().toCharArray(); boolean invalid = false; int index = -1; for (int i = 0; i < chars.length && !invalid; i++) { char c = chars[i]; if ('0' <= c && c <= '9') { invalid = true; } else if (c == '-') { if (index == -1) { index = i; } else { invalid = true; } } else if (isNotAlpha(c) && i != chars.length - 1) { invalid = true; } } if (invalid || index == 0 || index == chars.length - 1) { continue; } if (index > 0 && (isNotAlpha(chars[index - 1]) || isNotAlpha(chars[index + 1]))) { continue; } count++; } return count;
}
boolean isNotAlpha(char c) {
return 'a' > c || c > 'z';
}
}
【 NO.2 下一个更大的数值均衡数】
解题思路
枚举即可。
代码展现
class Solution {
public int nextBeautifulNumber(int n) {
for (int i = n + 1; ; i++) { if (balance(i)) { return i; } }
}
private boolean balance(int num) {
int[] cnt = new int[10]; for (; num > 0; num /= 10) { cnt[num % 10]++; } for (int i = 0; i < 10; i++) { if (cnt[i] != 0 && cnt[i] != i) { return false; } } return true;
}
}
【 NO.3 统计最高分的节点数目】
解题思路
首先进行一次 DFS 求出每个节点的子树大小,而后进行一次 DFS 求出每个节点的分数。
留神计算分数须要用 Long 类型,防止乘法溢出。
代码展现
class Solution {
Long maxScore;
Map<Long, Integer> count;
public int countHighestScoreNodes(int[] parents) {
List<List<Integer>> children = new ArrayList<>(); for (int i = 0; i < parents.length; i++) { children.add(new ArrayList<>()); } for (int i = 1; i < parents.length; i++) { children.get(parents[i]).add(i); } int[] sum = new int[parents.length]; calcSum(0, sum, children); maxScore = 0L; count = new HashMap<>(); calcMaxScore(0, sum, children); return count.get(maxScore);
}
private void calcMaxScore(int cur, int[] sum, List<List<Integer>> children) {
long score = 1; for (var nxt : children.get(cur)) { score *= sum[nxt]; } if (sum[0] - sum[cur] > 0) { score *= sum[0] - sum[cur]; } count.put(score, count.getOrDefault(score, 0) + 1); maxScore = Math.max(maxScore, score); for (var nxt : children.get(cur)) { calcMaxScore(nxt, sum, children); }
}
private void calcSum(int cur, int[] sum, List<List<Integer>> children) {
sum[cur] = 1; for (var nxt : children.get(cur)) { calcSum(nxt, sum, children); sum[cur] += sum[nxt]; }
}
}
【 NO.4 并行课程 III】
解题思路
简直是树型 DP 模板题,比较简单。令 finish(i) 示意实现课程 i 的最短时间,则 finish(i) = max(finish(j)) + time[i],其中 j 是 i 的前置课程。
代码展现
class Solution {
public int minimumTime(int n, int[][] relations, int[] time) {
List<List<Integer>> prev = new ArrayList<>(); for (int i = 0; i < n; i++) { prev.add(new ArrayList<>()); } for (int[] rel : relations) { prev.get(rel[1] - 1).add(rel[0] - 1); } int[] mem = new int[n]; int result = 0; for (int i = 0; i < n; i++) { result = Math.max(result, finish(i, prev, time, mem)); } return result;
}
private int finish(int cur, List<List<Integer>> prev, int[] time, int[] mem) {
if (mem[cur] > 0) { return mem[cur]; } if (prev.get(cur).size() == 0) { return time[cur]; } for (int p : prev.get(cur)) { mem[cur] = Math.max(mem[cur], finish(p, prev, time, mem) + time[cur]); } return mem[cur];
}
}