CF994B

B. Knights of a Polygonal Table

time limit per test

1 second

memory limit per test

256 megabytes

input

standard input

output

standard output

Unlike Knights of a Round Table, Knights of a Polygonal Table deprived of nobility and happy to kill each other. But each knight has some power and a knight can kill another knight if and only if his power is greater than the power of victim. However, even such a knight will torment his conscience, so he can kill no more than kk other knights. Also, each knight has some number of coins. After a kill, a knight can pick up all victim’s coins.

Now each knight ponders: how many coins he can have if only he kills other knights?

You should answer this question for each knight.

Input

The first line contains two integers nn and kk (1≤n≤105,0≤k≤min(n−1,10))(1≤n≤105,0≤k≤min(n−1,10)) — the number of knights and the number kk from the statement.

The second line contains nn integers p1,p2,…,pnp1,p2,…,pn (1≤pi≤109)(1≤pi≤109) — powers of the knights. All pipi are distinct.

The third line contains nn integers c1,c2,…,cnc1,c2,…,cn (0≤ci≤109)(0≤ci≤109) — the number of coins each knight has.

Output

Print nn integers — the maximum number of coins each knight can have it only he kills other knights.

Examples

input

Copy

4 2
4 5 9 7
1 2 11 33

output

Copy

1 3 46 36 

input

Copy

5 1
1 2 3 4 5
1 2 3 4 5

output

Copy

1 3 5 7 9 

input

Copy

1 0
2
3

output

Copy

3 

Note

Consider the first example.

  • The first knight is the weakest, so he can’t kill anyone. That leaves him with the only coin he initially has.
  • The second knight can kill the first knight and add his coin to his own two.
  • The third knight is the strongest, but he can’t kill more than k=2k=2 other knights. It is optimal to kill the second and the fourth knights: 2+11+33=462+11+33=46.
  • The fourth knight should kill the first and the second knights: 33+1+2=3633+1+2=36.

In the second example the first knight can’t kill anyone, while all the others should kill the one with the index less by one than their own.

In the third example there is only one knight, so he can’t kill anyone.

其实这个题也比较明了,基本上样例解释就告诉我们了做法

就是贪心做法,一个骑士能杀的其他骑士只能是其他的骑士,所以我们就先让所有的骑士来按武力值来排个序,就能保证上面的条件。那么我们只需要保证啥前面的k个金币数最大的就能达到再加上自己有的硬币就是答案了

题目最后要求我们要按原有顺序输出,那么最后记得按照顺序输出就行(好像在说废话

首先是我自己的实现代码:

#include <iostream>
#include <cstdio>
#include <cmath>
#include <ctype.h>
#include <algorithm>
#include <cstring>
#include <map>
#include <set>
#include <sstream>
#include <queue>
#define ll long long
#define re return

using namespace std;

struct nope
{
    ll p;
    ll c;
    ll id;
    ll ans;
}a[100000 + 10];

ll n, k;

// priority_queue<int> q; //下一份代码留有大用

bool cmp1(nope a, nope b){ //按力量从小到大
    return a.p < b.p;
}

bool cmp2(nope a, nope b){ //编号从小到大
    return a.id < b.id;
}

int main(){
    cin >> n >> k;
    for (ll i = 1; i <= n; i++){
        cin >> a[i].p;
        a[i].id = i;
    }

    for (ll i = 1; i <= n; i++){
        cin >> a[i].c;
    }

    if(k == 0){ //特判一下,如果不特判,看完后面的代码就会发现解决不了k=0的情况
        for (ll i = 1; i <= n; i++){
            cout << a[i].c << " ";
        }
        return 0;
    }

    sort(a + 1, a + n + 1, cmp1);

    ll max_sum = a[1].c; //前k个的最大和
    ll min_c[200]; //存前k个中最小的那个,来更新答案
    min_c[1] = a[1].c;
    a[1].ans = a[1].c; //没得杀

    for (ll i = 2; i <= k + 1;  i++){ //前k个只能杀他前面的,所以不能只枚举到k,要到k + 1
        a[i].ans = a[i - 1].ans + a[i].c; //其实就是一个前缀和
        if(i != k + 1){
            min_c[i] = a[i].c; //前k个的值
            max_sum += a[i].c; //前k个的和
        }
    }
    
    sort(min_c + 1, min_c + k + 1); //把我们存的目前最大的k个金币存好(用min做数组名的原因是想找这k个中最小的那个

    for (ll i = k + 2; i <= n; i++){
        if(min_c[1] < a[i - 1].c){ //有没有必要杀第i - 1个,i个是他自己不能杀;杀i-1的收益打还是不杀他的收益大
            max_sum = max_sum - min_c[1] + a[i - 1].c; //需要把最小的那个剔除掉然后加上新的这个大硬币才难个更新max_sum
            min_c[1] = a[i - 1].c;
            sort(min_c + 1, min_c + 1 + k); //不用担心复杂度,k最大才10
        }
        a[i].ans = max_sum + a[i].c;
    }

    sort(a + 1, a + 1 + n, cmp2); //id排序输出
    for (ll i = 1; i <= n; i++){
        cout << a[i].ans << " ";
    }
    return 0;
}

然后我从题解学了一个方法。

当时也想着用单调队列来解决的,开始对于使用方法有点不熟就没用

#include <iostream>
#include <cstdio>
#include <cmath>
#include <ctype.h>
#include <algorithm>
#include <cstring>
#include <map>
#include <set>
#include <sstream>
#include <queue>
#include <vector>
#define ll long long
#define re return

using namespace std;

struct nope
{
    ll p;
    ll c;
    ll id;
    ll ans;
}a[100000 + 10];

ll n, k;

priority_queue<int> q;
vector<int> v; //不定数组可以不用在意长度直接往后加就行

bool cmp1(nope a, nope b){ //按力量从小到大
    return a.p < b.p;
}

bool cmp2(nope a, nope b){ //编号从小到大
    return a.id < b.id;
}

int main(){
    cin >> n >> k;
    for (ll i = 1; i <= n; i++){
        cin >> a[i].p;
        a[i].id = i;
    }

    for (ll i = 1; i <= n; i++){
        cin >> a[i].c;
    }

    sort(a + 1, a + n + 1, cmp1);

    a[1].ans = a[1].c;
    q.push(a[1].c); //我们把第一个骑士,也就是最小的骑士的答案来准备好,好更新后面的答案
    // v.push_back(a[1].c); //这里不能提前放进去,否则会造成1被多杀一次
    for(int i = 2; i <= n; i++){
        ll y = q.size();
        ll t = min(k, y);
        a[i].ans = a[i].c;
        for (int j = 1; j <= t; j++){
            int x = q.top();
            q.pop();
            v.push_back(x);
        }
        for (int j = 0; j < v.size(); j++)
        {
            a[i].ans += v[j];
            q.push(v[j]);
        }
        v.clear();
        q.push(a[i].c);//把这个人的钱放进去,因为下个人才能杀当前这个
    }

    sort(a + 1, a + 1 + n, cmp2);
    for (ll i = 1; i <= n; i++){
        cout << a[i].ans << " ";
    }
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值