ZOJ 3715 (贪心)

At the beginning of the semester in kindergarten, the n little kids (indexed from 1 to n, for convenience) in class need to elect their new leader.

The ith kid will vote for his best friend fi (where 1 ≤ fi ≤ n, and it's too shame to vote for yourself, so fi ≠ i). And the kid who gets the most votes will be the leader. If more than one kids who get the largest number of votes, there will be multiple leaders in the new semester.

Little Sheldon (the kid with index 1) is extremely vain, and he would like to be theONLY leader. (That means the number of votes he gets should strictly larger than any other.) Soon Sheldon found that if he give ci candies to the ith kid, the ithkid would regard Sheldon as the new best friend, and of course vote for Sheldon.

Every kid including Sheldon loves candies. As an evil programmer, please help the evil Sheldon become the ONLY leader with minimum cost of candies. By the way, Sheldon should vote for any one he wants EXCEPT himself.

Input

There are multiple test cases. The first line of input contains an integer T (T ≤100) indicating the number of test cases. Then T test cases follow.

The first line of each case contains one integer: n (3 ≤ n ≤ 100) -- the number of kids in class.

The second line contains n-1 integers: fi (1 ≤ fi ≤ nfi ≠ i, and 2 ≤ i ≤ n) -- represents that the best friend of ith kid is indexed with fi.

The third line contains n-1 integers: ci (1 ≤ ci ≤ 1000, and 2 ≤ i ≤ n) -- represents that if Sheldon gave ci candies to the ith kid, the ith kid would vote Sheldon, instead of their old best friend fi, as the new semester leader.

<h4< dd="">
Output

For each test case, print the minimal cost of candies to help Sheldon become theONLY leader.

<h4< dd="">
Sample Input
2
4
1 1 2
1 10 100
3
3 2
1 10
<h4< dd="">
Sample Output
0
11
<h4< dd="">
Hint

In the first case,

  • If Sheldon vote for 2nd kid, the 2nd kid and Sheldon will both have 2 votes. In this case, Sheldon have to pay 100 candies to the 4th kid, and get 3 votes to win;
  • If Sheldon vote for 3rd or 4th kid, Sheldon will win with 2 votes without sacrifice any candy.


题意:有n个人要选一个领导,1号想通过买通别人投自己,来让自己成为领导,现给出编号2~n的人投票对象,以及买通他所需花费,求1号能当选领导所需最小花费,票不能投给自己。

思路:很容易就想到两种取法,1.买通投了 和1号票数相同 的人

  2.买通没投给1号,且花费最小 的人

最终状态肯定是确定的,也就是最终1号的票数,n<=100,所以可以枚举最终状态。

最终状态肯定是只能是1号的状态,所以就要把其他人的状态都控制低于这个值,而且优先选花费最小的。

当然,以这样的思路去做的话,要保证1号自己达到了这个值,没有的话选最小花费的。


n 比较小,暴力枚举所有a的最终票数


#include <iostream>
#include <bits/stdc++.h>
using namespace std;
const int N = 110;
const int inf = 0x3f3f3f3f;
typedef long long LL;
struct node
{
    int c, id, v;
}p[N], u[N];
int vis[N], val[N];
int cmp(node x,node y)
{
    if(x.c!=y.c) return x.c<y.c;
    return x.id<y.id;
}

int cmp1(node x,node y)
{
    return x.c<y.c;
}

int main()
{
    int t;
    scanf("%d", &t);
    while(t--)
    {
        int n;
        memset(val,0,sizeof(val));
        scanf("%d", &n);
        for(int i=2;i<=n;i++)
        {
            scanf("%d", &p[i].v);
            p[i].id=i;
            val[p[i].v]++;
        }
        for(int i=2;i<=n;i++)
        {
            scanf("%d", &p[i].c);
            u[i]=p[i];
        }
        sort(p+2,p+n+1,cmp);
        sort(u+2,u+n+1,cmp1);
        int ans=inf;
        for(int i=max(2,val[1]);i<=n;i++)
        {
            int tmp=0, num=val[1];
            memset(vis,0,sizeof(vis));
            for(int j=2;j<=n;j++)
            {
                if(val[j]<i) continue;
                int cnt=val[j]-i+1;
                for(int k=2;k<=n;k++)
                {
                    if(!cnt) break;
                    if(p[k].v==j)
                    {
                        vis[k]=1;
                        tmp+=p[k].c;
                        cnt--,num++;
                    }
                }
            }
            if(num<i)
            {
                for(int j=2;j<=n;j++)
                {
                    if(p[j].v==1||vis[j]) continue;
                    if(num==i) break;
                    tmp+=p[j].c,num++;
                }
            }
            ans=min(ans,tmp);
        }
        cout<<ans<<endl;
    }
    return 0;
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值