题意:
n个数,求出这些数中满足 ai >= aj 的 ai % aj 的最大值。
排序去重,然后对于每一个a[i], 如果找到a[i] 的一个倍数 k*a[i] (k > 1)的位置,那么它之前的第一个数字就是一个使a[j] % a[i] 最大的可能的解。
这样,枚举a[i] 所有的倍数,求最大的答案即可。
如何找出 k * a[i] 的位置呢?因为数组是有序的,所以可以用二分查找。
枚举所有 a[i] 的倍数最坏的复杂度是 n/1 + n/2 + n/3 + .... n/n = nlogn,加上二分查找的复杂度是 n*logn*logn。
lower_bound(a+1, a+1+n, x) - (a+1),可以二分查找在区间 a[1...n] 找到小于 x 的最大值的位置。
#include <iostream> #include <cstdlib> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> using namespace std; #define maxn 200000 + 100 int main() { int n, a[maxn]; scanf("%d", &n); for (int i = 1; i <= n; i++) scanf("%d", &a[i]); sort(a+1, a+1+n); n = unique(a+1, a+1+n)-(a+1); //去重 int ans = 0; for (int i = 1; i <= n; i++) { for (int j = a[i]; j <= a[n]; j += a[i]) { int x = lower_bound(a+1+i, a+1+n, j+a[i])-(a+1); ans = max(a[x]%a[i], ans); } } printf("%d ", ans); }