微软笔试8.26,附上题目和自己的解法,求大伙帮找下缺漏
Task1
- 题目
- 思路
对撞指针。用一个数组来统计字符串中每个字母出现的次数,如果数组中每个元素出现的次数都为偶数,则代表该字符串符合题目要求。左右指针对撞,如果当前l和r所指的字符的出现次数都为偶数,则判断当前子串是否符合要求,符合则返回当前字符串长度;不符合,左右指针都向中间靠拢一步,对应的字符出现次数数组中的值减一;如果l和r所指字符出现次数都为奇数,则判断是否所指字符是否相等,如果相等则移动任意一个指针,对应次数减一;如果不相等,左右都移动然后次数减一 - code
//对撞指针
public int task1(String S) {
int l = 0, r = S.length() - 1;
int[] count = new int[26];
for (int i = 0; i < S.length(); i++) {
count[S.charAt(i) - 'a']++;
}
while (l < r) {
if (count[S.charAt(l) - 'a'] % 2 == 0 && count[S.charAt(r) - 'a'] % 2 == 0 && isOk(count))
return r - l + 1;
if (S.charAt(l) == S.charAt(r) && count[S.charAt(l) - 'a'] % 2 != 0) {
count[S.charAt(l) - 'a']--;
l++;
} else if (count[S.charAt(l) - 'a'] % 2 == 0 && count[S.charAt(r) - 'a'] % 2 == 0 && !isOk(count) ||
count[S.charAt(l) - 'a'] % 2 != 0 && count[S.charAt(r) - 'a'] % 2 != 0
) {
count[S.charAt(l) - 'a']--;
count[S.charAt(r) - 'a']--;
l++;
r--;
} else if (count[S.charAt(l) - 'a'] % 2 != 0) {
count[S.charAt(l) - 'a']--;
l++;
} else {
count[S.charAt(r) - 'a']--;
r--;
}
}
return 0;
}
private boolean isOk(int[] count) {
for (int j : count) {
if (j % 2 == 1)
return false;
}
return true;
} Task2
- 题目
思路
用一个map来存储坐标对应的点的集合,然后遍历数组,判断map中是否含有A[i] + k * M (k=1,2,3...,A[i] + k * M <= 坐标最大值)的点,如果有就将这些点全部放在一个集合里面,记录集合的最大长度,即为所求code
public int task2(int[] A, int M) {
//坐标为k的点的集合
HashMap<Integer, HashSet<Integer>> map = new HashMap<>();
int max = Integer.MIN_VALUE;
for (int i = 0; i < A.length; i++) {
HashSet<Integer> set = map.getOrDefault(A[i], new HashSet<>());
set.add(i);
map.put(A[i], set);
max = Math.max(max, A[i]);
}
int ans = 1;
for (int i = 0; i < A.length; i++) {
HashSet<Integer> set = new HashSet<>();
for (int x = A[i] + M; x <= max; x = x + M) {
if (map.containsKey(x)) {
//取并集
set.addAll(map.get(A[i]));
set.addAll(map.get(x));
}
}
ans = Math.max(set.size(), ans);
}
return ans;
} Task3
- 题目
思路
就是求A和B merge后的最小未出现的正数,不算太难,这里用list来存Ccode
public int task3(int[] A, int[] B) { LinkedList<Integer> list = new LinkedList<>(); for (int i = 0; i < A.length; i++) { list.add(Math.max(A[i], B[i])); } int ans = Integer.MAX_VALUE; for (int x : A) { if (!list.contains(x)) ans = Math.min(x, ans); } for (int x : B) { if (!list.contains(x)) ans = Math.min(x, ans); } for (int i = 1; i <= ans; i++) { if (!list.contains(i)) { ans = i; break; } } return ans; }
总结
我认为解法中还有很多缺漏,虽然每道题样例都过了,但是应该都不完全对,欢迎大伙有更好的思路和解法分享
#微软笔试#