2019-08-187-3 保持真实

在计算机科学中,堆是一个专门的基于树的数据结构,它本质上是一个完全树。

堆的一些性质:在最小堆中,对于任何给定的结点 C,如果 P 是 C 的父结点,那么结点 P 的值小于或等于 C 的值。堆的“顶部”的结点称为根结点。

通常,我们可以用数组 h​1​​,h​2​​,......,h​n​​ 存储大小为 n 的堆,其中 h​i​​ 表示第 i 个结点的值。

根结点是第 1 个结点,第 i(2≤i≤n) 个结点的父结点是第 ⌊​2​​i​​⌋ 个结点。

Alice 和 Bob 正在最小堆上玩游戏。

两人轮流移动,Alice 先移动。

在每个人的回合里,这个人可以选择一个没有孩子的结点,把这个结点从堆中移开,同时获得同等于这个结点的值的分数。

当堆空时,游戏结束。

假设两人都足够聪明,Alice 和 Bob 的最终得分会是多少?

输入格式:

输入的第一行包含整数 T(1≤T≤10000),表示测试用例的数量。

在每个测试用例中,第一行中有一个整数 n(1≤n≤100000),表示节点数。

在第二行中,有 n 个整数 h​1​​,h​2​​,......,h​n​​,1≤h​i​​≤10​9​​,h​⌊​2​​i​​⌋​​≤h​i​​),表示每个节点的关键字。

保证 ∑n≤10​6​​。

输出格式:

对于每个测试用例,打印包含两个整数 A 和 B 的单行,表示 Alice 和 Bob 的最终得分。

输入样例:

1

3

1 2 3

输出样例:

4 2

#include

#define int long long

using namespace std;

int x[1000010],y[1000010];

signed main()

{

    int n,b=0,c=0,a;

    cin>>n;

    while(n--)

    {

        b=0;

        c=0;

        int sum=0,t=0,res=0;

        cin>>a;

        for(int i=0;i

        {

            cin>>x[i];

        }

        sort(x,x+a);

        int q=0;

        //cout<

        for(int i=a-1;i>=0;i--)

        {

            if(q==1)

            {

                c+=x[i];

                q=0;

            }

            else if(q==0)

            {

                b+=x[i];

                q=1;

            }

        }

        printf("%lld %lld\n",b,c);

    }

    return 0;

}

你可能感兴趣的:(2019-08-187-3 保持真实)