- 进击的奶牛
挖掘机里腌萝卜,咿呀咿呀哟
- @ 2025-12-6 9:15:42
问题描述 农夫约翰建造了一座有 n 间牛舍的小屋,牛舍排在一条直线上,第 i 间牛舍在 xi 的位置,但是约翰的 m 头牛是斗牛,脾气非常暴躁,因此经常相互攻击。约翰为了防止牛之间互相伤害,因此决定把每头牛都放在离其它牛尽可能远的牛舍。也就是要最大化最近的两头牛之间的距离。约翰决定自己给每头牛分配一个隔间,使任意两头牛之间的最小距离尽可能的大,那么,这个最大的最小距离是多少呢?
输入格式 第一行用空格分隔的两个整数 n 和 m。第二行为 n 个用空格隔开的整数,表示位置 xi 。 (2 ≤ n ≤ 100000,0 < xi ≤ 1000000000,2 ≤ m ≤ n )
输出格式 输出仅一个整数,表示最大的最小距离值。
输入输出样例 输入数据 1 5 3 1 2 8 4 9 输出数据 1 3
1 条评论
-
-
#include #include #include using namespace std;
// 验证当前最小距离mid是否能放下m头牛 bool check(const vector& pos, int m, int mid) { int count = 1; // 已放置的牛数,第一个位置先放1头 int last = pos[0]; // 上一头牛的位置 for (int i = 1; i < pos.size(); ++i) { if (pos[i] - last >= mid) { count++; last = pos[i]; if (count == m) break; // 提前终止,优化效率 } } return count >= m; }
int main() { ios::sync_with_stdio(false); // 关闭同步,加速输入输出 cin.tie(nullptr);
int n, m; cin >> n >> m; vector<int> positions(n); for (int i = 0; i < n; ++i) { cin >> positions[i]; } // 排序牛舍位置(贪心的前提) sort(positions.begin(), positions.end()); // 二分边界:最小距离1,最大距离为首尾牛舍差值 int left = 1; int right = positions.back() - positions[0]; int ans = 0; while (left <= right) { int mid = left + (right - left) / 2; // 避免溢出(替代(left+right)/2) if (check(positions, m, mid)) { ans = mid; // 记录可行解 left = mid + 1; // 尝试更大的距离 } else { right = mid - 1; // 距离太大,尝试更小的 } } cout << ans << endl; return 0;}
- 1
信息
- ID
- 1954
- 时间
- 1000ms
- 内存
- 256MiB
- 难度
- 8
- 标签
- 递交数
- 22
- 已通过
- 13
- 上传者