- TreeMap可以有序,HashMap无法有序
import java.util.Scanner;
import java.util.*;
public class Main {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int n = in.nextInt(),a,b;
//TreeMap可以有序,HashMap无法有序,以下代码->TreeMap重写Comparator的compare函数,利用key进行排序
TreeMap<Integer,Integer> tm = new TreeMap<>(new Comparator<Integer>(){
public int compare(Integer a, Integer b){
return a-b;
}
});
while(n-->0){
a = in.nextInt();
b = in.nextInt();
if (tm.containsKey(a)){
tm.put(a,tm.get(a)+b);
}else{
tm.put(a,b);
}
}
//map遍历方式:lambda:推荐
tm.forEach((key,value)->{
System.out.println(key+" "+value);
});
}
}
- 遍历map
1.8以下推荐写法,感觉挺方便
for(Map.Entry<Integer,String> entry:map.entrySet()){
System.out.println(entry.getKey());
System.out.println(entry.getValue());
};
Iterator<Map.Entry<String,String>> iterator=map.entrySet().iterator();
while(iterator.hasNext()){
Map.Entry<String, String> entry=iterator.next();
if(entry.getKey().equals("2")){
iterator.remove();
}
}
lambda表达式,注意{}中不能赋值普通变量,具体原因还未探知
map.forEach((key,value)->{
System.out.println(key);
System.out.println(value);
});
- 并查集
常见/(quick)模板
public class Union_find {
private int[] root = null;
public Union_find(int row, int col) {
root = new int[row * col];
for (int i = 0; i < row * col; i++) {//构建索引对照列表
root[i] = i;
}
}
//Find the root of x
public int Find(int x) {//递归寻找最远祖先
if (x == root[x]) {
return root[x];
}
/*1*/return Find(root[x]);
// /*2*/以下是find quick方法,找到的同时,把自己的祖先值也变了,替换上述的return语句
//root[x] = Find(root[x]);
// return roox[x];
}
//Union two elements into one root
public void Union(int x, int y) {
int rootx = Find(x);
int rooty = Find(y);
if (rooty != rootx){//如果x和y不是同一个祖先,就将其中一个element的祖先设为另一个,后面在递归中也能找到
root[rootx] = rooty;
}
}
}
union find 权重rank
public class Union_find_rank {
private int[] root = null;
private int[] rank = null;
public Union_find_rank(int row, int col) {
root = new int[row * col];
rank = new int[row * col];
for (int i = 0; i < row * col; i++) {//构建索引对照列表
root[i] = i;
rank[i] = 0;
}
}
//Find the root of x
public int Find(int x) {//递归寻找最远祖先
if (x == root[x]) {
return root[x];
}
return Find(root[x]);
// 以下是find quick方法,找到的同时,把自己的祖先值也变了,替换上述的return语句
//root[x] = Find(root[x]);
// return roox[x];
}
//Union two elements into one root
public void Union(int x, int y) {
int rootx = Find(x);
int rooty = Find(y);
if (rooty != rootx){//如果x和y不是同一个祖先,就将其中一个element的祖先设为另一个,后面在递归中也能找到
if (rank[rootx] > rank[rooty]){//如果x子树比y子树高,就将y放到x下
root[rooty] = rootx;
} else if (rank[rootx] < rank[rooty]) {//如果x子树比y子树矮,就将x放到y下
root[rootx] = rooty;
}else {//如果两个并查集树高度相等
root[rooty] = rootx;
rank[rootx] += 1;
}
}
}
}
- kmp,needle是否在haystack中,在则返回第一个下标,否则返回-1
public static int strStr(String haystack, String needle) {
int[] prefix = new int[needle.length()];//前缀表,最长相等前后缀
getPrefix(prefix, needle);
System.out.println(Arrays.toString(prefix));
int i = 0, j = 0;
while (i < haystack.length()) {
if (haystack.charAt(i) == needle.charAt(j)) {
j++;
i++;
} else {
while (haystack.charAt(i) != needle.charAt(j) && j != 0) {//如果一直不匹配,则j要一直往前
j = prefix[j - 1];
}
if (haystack.charAt(i) == needle.charAt(j)) {
j++;
}
i++;
}
if (j == needle.length()) {
return i - needle.length();
}
}
return -1;
}
private static void getPrefix(int[] prefix, String needle) {//求前缀表
Arrays.fill(prefix, 0);
for (int index = 1; index < needle.length(); index++) {
// for (int i = 0, j = index; i < index && j > 0; i++, j--) {
// if (needle.substring(0, i + 1).equals(needle.substring(j, index + 1))) {
// prefix[index] = Math.max(prefix[index], i + 1);
// }
// }
for (int i = index, j = 1; i >= 0 && j <= index; i--, j++) {//i是前缀尾,j是后缀头
if (needle.substring(0, i).equals(needle.substring(j, index + 1))) {
prefix[index] = i;
break;
}
}
}
}
- 差分数组
(以leetcode1109,航班预定题目为例)
class Solution {
public int[] corpFlightBookings(int[][] bookings, int n) {
int[] seats = new int[n];
Arrays.fill(seats,0);
Difference dd = new Difference(seats);
for (int i=0;i<bookings.length;i++){
dd.increment(bookings[i][0]-1,bookings[i][1]-1,bookings[i][2]);
}
return dd.result();
}
class Difference{
private int[] difference;
public Difference(int[] nums) {
difference = new int[nums.length];
System.arraycopy(nums, 0, this.difference, 0, nums.length);
}
public void increment(int i,int j,int val){ //对差分数组的i和j+1位置修改,即可修改原数组i到j之间的所有值
difference[i] += val;
if (j+1 < difference.length){
difference[j+1] -= val;
}
}
public int[] result(){//从差分数组得到原始数组(在更新的原始数组上计算)
int[] result = new int[difference.length];
result[0] = difference[0];
for (int i=1;i<difference.length;i++){
result[i] = difference[i] + result[i-1];
}
return result;
}
}
}