二分
建议看看小弟在 => 数的范围 <= 发布的有关二分的题解, 搭配食用
https://www.acwing.com/solution/acwing/content/11358/
// package 第四讲枚举与模拟与排序;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.Arrays;
public class Main {
static BufferedReader br;
static int N = (int) 1e5 + 10;
static int n, A[], B[], C[];
static void init() throws NumberFormatException, IOException {
br = new BufferedReader(new InputStreamReader(System.in));
A = new int[N];
B = new int[N];
C = new int[N];
n = Integer.parseInt(br.readLine().trim());
String[] ss = br.readLine().trim().split(" ");
for (int i = 0; i < n; i++) {
A[i + 1] = Integer.valueOf(ss[i]);
}
ss = br.readLine().trim().split(" ");
for (int i = 0; i < n; i++) {
B[i + 1] = Integer.valueOf(ss[i]);
}
ss = br.readLine().trim().split(" ");
for (int i = 0; i < n; i++) {
C[i + 1] = Integer.valueOf(ss[i]);
}
}
public static void main(String[] args) throws NumberFormatException,
IOException {
init();
long res = 0;
// 1. 使用sort+二分优化
// res += (A中小于B[j]的个数) * (C中大于B[j]的个数)
Arrays.sort(A, 1, n + 1);
Arrays.sort(B, 1, n + 1);
Arrays.sort(C, 1, n + 1);
for (int j = 1; j <= n; j++) {
int a = 0, b = 0, x = B[j];
// 查找a
int l = 1, r = n;
while (l < r) {
int mid = l + r + 1 >> 1;
if (A[mid] < x) {
l = mid;
} else {
r = mid - 1;
}
}
if (A[l] >= x) { // 二分很有可能没有找到答案,记得判断
a = 0;
} else {
a = l;
}
// 查找b
l = 1;
r = n;
while (l < r) {
int mid = l + r >> 1;
if (x < C[mid]) {
r = mid;
} else {
l = mid + 1;
}
}
if (C[l] <= x) {
b = 0;
} else {
b = n - l + 1;
}
res += 1L * a * b; // 注意: 如果乘数不转long会爆
}
System.out.println(res);
}
}