文章目录



区间问题

区间选点

6)贪心._贪心

#include<iostream>
#include<algorithm>

using namespace std;

const int N = 100010;

int n;
struct Range{

int l, r;
bool operator < (const Range & W) const{

return r < W.r;
}
}range[N];

int main(){

scanf("%d", &n);

for(int i = 0; i < n; i++) scanf("%d%d", &range[i].l, &range[i].r);

sort(range, range + n);

int res = 0, ed = -2e9;

for(int i = 0; i < n; i++){

if(range[i].l > ed){

res++;
ed = range[i].r;
}
}

printf("%d\n", res);

return 0;
}

最大不相交区间数量

#include<iostream>
#include<algorithm>

using namespace std;

const int N = 100010;

int n;
struct Range{

int l, r;
bool operator < (const Range & W) const{

return r < W.r;
}
}range[N];

int main(){

scanf("%d", &n);

for(int i = 0; i < n; i++) scanf("%d%d", &range[i].l, &range[i].r);

sort(range, range + n);

int res = 0, ed = -2e9;

for(int i = 0; i < n; i++){

if(ed < range[i].l){

res++;
ed = range[i].r;
}
}

printf("%d\n", res);

return 0;
}

区间分组

6)贪心._i++_02

#include<iostream>
#include<algorithm>
#include<queue>

using namespace std;

const int N = 100010;

int n;
struct Range{

int l, r;
bool operator < (const Range & W) const{
return l < W.l;
}
}range[N];

int main(){

scanf("%d", &n);

for(int i = 0; i < n; i++){

int l, r;
scanf("%d%d", &l, &r);
range[i] = {l, r};
}

sort(range, range + n);

priority_queue<int, vector<int>, greater<int>> heap;

for(int i = 0; i < n; i++){

auto r = range[i];
if(heap.empty() || heap.top() >= r.l) heap.push(r.r);
else{

heap.pop();
heap.push(r.r);
}
}

printf("%d\n", heap.size());

return 0;
}

区间覆盖

6)贪心._i++_03

#include<iostream>
#include<algorithm>

using namespace std;

const int N = 100010;

int n;
struct Range{

int l, r;
bool operator < (const Range & W) const{

return l < W.l;
}
}range[N];

int main(){

int st, ed;

scanf("%d%d", &st, &ed);
scanf("%d", &n);

for(int i = 0; i < n; i++){

int l, r;
scanf("%d%d", &l, &r);
range[i] = {l, r};
}

sort(range, range + n);

int res = 0;
bool success = false;

for(int i = 0; i < n; i++){

int j = i, r = -2e9;

// 双指针扫描
while(j < n && range[j].l <= st){

r = max(r, range[j].r);
j++;
}

if(r < st){

res = -1;
break;
}

res++;

if(r >= ed){

success = true;
break;
}

st = r;
i = j - 1;
}

if(!success) res = -1;
printf("%d\n", res);

return 0;
}

Huffman树

合并果子

#include<iostream>
#include<algorithm>
#include<queue>

using namespace std;

int main(){

int n;
scanf("%d", &n);

priority_queue<int, vector<int>, greater<int>> heap;

while(n--){

int x;
scanf("%d", &x);
heap.push(x);
}

int res = 0;
while(heap.size() > 1){

int a = heap.top(); heap.pop();
int b = heap.top(); heap.pop();
res += a + b;
heap.push(a + b);
}

printf("%d\n", res);

return 0;
}

排序不等式

排队打水

6)贪心._i++_04

#include<iostream>
#include<algorithm>

using namespace std;

typedef long long ll;

const int N = 100010;

int n;
int t[N];

int main(){

scanf("%d", &n);

for(int i = 0; i < n; i++) scanf("%d", &t[i]);

sort(t, t + n);

ll res = 0;

for(int i = 0; i < n; i++) res += t[i] * (n - i - 1);

printf("%lld\n", res);

return 0;
}

绝对值不等式

货仓选址

6)贪心._i++_05

#include<iostream>
#include<algorithm>

using namespace std;

const int N = 100010;

int n;
int q[N];

int main(){

scanf("%d", &n);

for(int i = 0; i < n; i++) scanf("%d", &q[i]);

sort(q, q + n);

int res = 0;
for(int i = 0; i < n; i++) res += abs(q[i] - q[n / 2]);

printf("%d\n", res);

return 0;
}

推公式

耍杂技的牛

6)贪心._#include_06

#include<iostream>
#include<algorithm>

using namespace std;

typedef pair<int, int> PII;

const int N = 50010;

int n;
PII cow[N];

int main(){

scanf("%d", &n);
for(int i = 0; i < n; i++){

int s, w;
scanf("%d%d", &w, &s);
cow[i] = {w + s, w};
}

sort(cow, cow + n);

int res = -2e9, sum = 0;
for(int i = 0; i < n; i++){

int s = cow[i].first - cow[i].second, w = cow[i].second;
res = max(res, sum - s);
sum += w;
}

printf("%d\n", res);

return 0;
}