D1. Candy Party (Easy Version)

D1. Candy Party (Easy Version)

This is the easy version of the problem. The only difference is that in this version everyone must give candies to exactly one person and receive candies from exactly one person. Note that a submission cannot pass both versions of the problem at the same time. You can make hacks only if both versions of the problem are solved.

After Zhongkao examination, Daniel and his friends are going to have a party. Everyone will come with some candies.

There will be n people at the party. Initially, the i-th person has ai candies. During the party, they will swap their candies. To do this, they will line up in an arbitrary order and everyone will do the following exactly once:

  • Choose an integer p (1pn) and a non-negative integer x, then give his 2x candies to the p-th person. Note that one cannot give more candies than currently he has (he might receive candies from someone else before) and he cannot give candies to himself.

Daniel likes fairness, so he will be happy if and only if everyone receives candies from exactly one person. Meanwhile, his friend Tom likes average, so he will be happy if and only if all the people have the same number of candies after all swaps.

Determine whether there exists a way to swap candies, so that both Daniel and Tom will be happy after the swaps.

Input

The first line of input contains a single integer t (1t1000) — the number of test cases. The description of test cases follows.

The first line of each test case contains a single integer n (2n2105) — the number of people at the party.

The second line of each test case contains n integers a1,a2,,an (1ai109) — the number of candies each person has.

It is guaranteed that the sum of n over all test cases does not exceed 2105.

Output

For each test case, print "Yes" (without quotes) if exists a way to swap candies to make both Daniel and Tom happy, and print "No" (without quotes) otherwise.

You can output the answer in any case (upper or lower). For example, the strings "yEs", "yes", "Yes", and "YES" will be recognized as positive responses.

Example

input

复制代码
6
3
2 4 3
5
1 2 3 4 5
6
1 4 7 1 5 4
2
20092043 20092043
12
9 9 8 2 4 4 3 5 1 1 1 1
6
2 12 7 16 11 12
复制代码

output

Yes
Yes
No
Yes
No
No

Note

In the first test case:

  • The first person gives 1 candy to the third person;
  • The second person gives 2 candies to the first person;
  • The third person gives 1 candy to the second person.

Then all people have 3 candies.

In the second test case:

  • The fifth person gives 4 candies to the first person, from now on the first person has 5 candies;
  • The first person gives 2 candies to the third person;
  • The third person gives 2 candies to the fifth person;
  • The fourth person gives 2 candies to the second person;
  • The second person gives 1 candy to the fourth person.

Then all people have 3 candies. Note that at first the first person cannot give 2 candies to the third person, since he only has a1=1 candy. But after the fifth person gives him 4 candies, he can do this, because he currently has 1+4=5 candies.

In the third test case, it's impossible for all people to have the same number of candies.

In the fourth test case, the first person gives 1024 candies to the second person, and the second person gives 1024 candies to the first person as well.

 

解题思路

  由于最后每个人分到的糖果数量一样,因此如果ni=1nai那么无解。定义平均数m=i=1nain,那么最终每个人分到的糖果数量就是m

  在这个版本中要求每个人都必须给恰好一个人分糖果,同时必须收到恰好一个人的糖果,如果第i个人给第j个人糖果那么连一条从ij的有向边ij,那么就会得到由若干个长度至少为2的环构成的图。这是因为每个节点的出度和入度都恰好为1,且没有自环。

  由于每个人给出以及收到的糖果数量都是2x的形式,因此最终每个人都要满足xi2xi+2yi=m,其中2xi表示第i个人给出的糖果数量,2yi表示第i个人收到的糖果数量。如果有ai=m那么只需满足2xi=2yi,而可以取任意值。下面主要讨论aim的情况。

  如果aim,那么有aim=2xi2yi,对于被减数和减数都是2的整次幂这种形式,模拟一下可以发现得到的结果在二进制下连续的1至多有1段。比如(11100)2(111)2(0)2都是合法的结果,而(11001)2(1010)2都不是合法的结果。因此在枚举时如果发现aim不满足这个条件,那么无解。

  假设每个aim都满足上面的条件(一样不考虑ai=m的情况),定义由xi构成的集合S={xx=xi,xiyii[1,n]},以及由yi构成的集合T={yy=yi,xiyii[1,n]},如果S=T,那么必然有解,否则无解。如果S=T,对于S中每个元素xi总是可以在T中找到值相同的元素yj,并且必有ij,此时从ij连一条有向边,权值为xi,表示第i个人给第j个人xi个糖果,那么就会构造出一种分发方案,每个人都恰好给一个人糖果和收到一个人的糖果,且最后每个人的糖果数量均为m

  还有个细节就是还需满足每个人给出的糖果不得超过当前获得的糖果数量这个条件。这个证明其实还是比较难的,比赛的时候只要最后有S=T那么就猜有解直接交了,没考虑到这个条件,现在来补一下证明。由于每个人给糖果的顺序可以是任意的,那么在每个环中只要选择的起点满足ai2xi0,那么剩下的节点由于满足aj+2yj2xj=m>0aj+2yj>2xj,因此这个条件就得到满足。可以证明环中最大的ai必然满足ai2xi0

  选择环中最大的ai,此时必然有ai>m,假设第i个人给第j个人糖果,那么有1ajai,我们要得到(1)ai2xi+2yi=m(2)aj2xj+2xi=m

  假设ai2xi<0,那么必然有2yi<2xi,即yi+1xi

  如果xi<xj(1)(2)aiaj2xi+2xj+2yi2xi=0aiaj+(2xj22xi)+2yi>0=0aiaj<0ai<aj

  与aiaj矛盾了。

  如果xi>xj(2)(1)ajai2xj+2xi+2xi2yi=0aj=ai+(2xj+2yi)2xi+1ajai+(2xi1+2xi1)2xi+1ajai2xiaj0

  与aj1矛盾了。

  因此在每个环中选择最大的ai作为起点,那么在交换时每个人给出的糖果数量一定不会超过当前的糖果数量。

  最后再考虑回ak=m的情况,只需插在环中任意两个点间即可,比如ixij,那么可以构造ixikxij

  另外一个细节就是如何判定某个数x在二进制下连续的1是否至多有1段。只需判断x+lowbit(x)在二进制下1的个数是否不超过1即可。

  AC代码如下,时间复杂度为O(nlogA)

复制代码
 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 
 4 typedef long long LL;
 5 
 6 const int N = 2e5 + 10;
 7 
 8 int a[N];
 9 int cnt[31];
10 
11 int lowbit(int x) {
12     return x & -x;
13 }
14 
15 void solve() {
16     int n;
17     scanf("%d", &n);
18     LL m = 0;
19     for (int i = 0; i < n; i++) {
20         scanf("%d", a + i);
21         m += a[i];
22     }
23     if (m % n) {
24         printf("NO\n");
25         return;
26     }
27     m /= n;
28     memset(cnt, 0, sizeof(cnt));
29     for (int i = 0; i < n; i++) {
30         if (a[i] == m) continue;
31         int x = abs(a[i] - m);
32         if (__builtin_popcount(x + lowbit(x)) > 1) {
33             printf("NO\n");
34             return;
35         }
36         int l = __lg(lowbit(x)), r = __lg(x + lowbit(x));
37         if (a[i] < m) cnt[l]++, cnt[r]--;    // a[i] - 2^l + 2^r
38         else cnt[r]++, cnt[l]--;    // a[i] - 2^r + 2^l
39     }
40     for (int i = 1; i <= 30; i++) {
41         if (cnt[i]) {
42             printf("NO\n");
43             return;
44         }
45     }
46     printf("YES\n");
47 }
48 
49 int main() {
50     int t;
51     scanf("%d", &t);
52     while (t--) {
53         solve();
54     }
55     
56     return 0;
57 }
复制代码

 

参考资料

  Codeforces Round 896 (Div. 1, Div. 2) Editorial:https://codeforces.com/blog/entry/116642

posted @   onlyblues  阅读(53)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 单线程的Redis速度为什么快?
· 展开说说关于C#中ORM框架的用法!
· Pantheons:用 TypeScript 打造主流大模型对话的一站式集成库
· SQL Server 2025 AI相关能力初探
· 为什么 退出登录 或 修改密码 无法使 token 失效
历史上的今天:
2022-09-14 匹配价值
Web Analytics
点击右上角即可分享
微信分享提示