zoukankan      html  css  js  c++  java
  • 小奇分糖果

    【题目背景】
    小奇将糖果都装回了同一个口袋里,现在它想把糖果分到一些口袋中,以便送给
    它的小伙伴。
    【问题描述】
    小奇有 n 个口袋,标号从 1 到 n。第 1 个口袋装着 m 个糖果,现在小奇要对糖果
    进行移动,使得第 i 个口袋正好有 a i 个糖果。
    小奇手头有一个半自动分糖机。每次它可以选择两个标号 a,b(要求口袋 a 的
    糖果数为偶数),然后分糖机会将口袋 a 中的糖果分成相等数量的两份,然后将
    其中的一份取出来放入口袋 b。
    小奇想知道,如何操作能达到它的目标呢?
    【输入格式】
    第一行包含一个正整数 T,表示数据组数。
    每组数据的第一行包含两个正整数 n,m。
    第二行有 n 个非负整数,a 1 ,a 2 ...a n ,保证∑a i = m。
    【输出格式】
    对于每组数据,第一行输出一个字符串,若可以通过适当的操作达到小奇的目标,
    输出 yes,否则输出 no。
    第二行为一个非负整数 p,表示你给出的方案的操作次数,如果上一行为 no,则 p
    为 0。
    接下来的 p 行,依次给出操作方案,每行两个整数 a,b,表示一次操作。
    (方案可能有很多种,你只需输出任意一种即可,对方案的最优性不作要求。若存
    在解,则最优解的 p 不会超过 1000000,为防止输出文件过大,你的方案中 p 不
    得大于 1000000。)
    【样例输入】
    3
    2 4
    1 3
    3 24
    3 6 15
    2 5
    1 4
    【样例输出】
    yes
    21 2
    1 2
    yes
    3
    1 3
    1 2
    1 3
    no
    0
    【数据范围】
    对于 30%的数据,若数据有解,则最少操作步数不超过 10。
    对于另外 20%的数据,将 ai 排序后的序列{b n },满足:
    b 1 = b 2 = ... = b n

    b 1 = b 2, b i = 2b i-1 (i >= 3)
    对于 100%的数据 n <= 10000,1 <= m <= 2^31。
    【评分标准】
    对于每个测试点,按照下列标准评分。
    若有某组数据可行性判断错误或输出格式不符合要求,得 0 分。
    所有数据可行性判断均正确,得 4 分。
    所有数据可行性判断均正确,且均给出了合法方案,得 10 分。

    令$d=gcd(a_i)$,可以证明若$m=d*2^{k}$问题才有解

    否则无解

    如果$b_i=a_i/d$为奇数,那么就需要合并

    然后$d$就会$d=d*2$,一直到$d=m$

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cstring>
     4 #include<cmath>
     5 #include<algorithm>
     6 using namespace std;
     7 typedef long long lol;
     8 int a[10001],cnt,n,m,l[1000001],r[1000001];
     9 int gcd(int a,int b)
    10 {
    11   if (!b) return a;
    12   return gcd(b,a%b);
    13 }
    14 void dfs(int t)
    15 {int i;
    16   int tot=0,q[10001];
    17   if (t==m) return;
    18   for (i=1;i<=n;i++)
    19     if ((a[i]/t)%2) q[++tot]=i;
    20   for (i=1;i<=tot;i+=2)
    21     {
    22       if (a[q[i]]>a[q[i+1]]) swap(q[i],q[i+1]);
    23       a[q[i+1]]-=a[q[i]];
    24       a[q[i]]*=2;
    25       l[++cnt]=q[i];r[cnt]=q[i+1];
    26     }
    27   dfs(t*2);
    28 }
    29 void work()
    30 {int i,t=0;
    31   cin>>n>>m;
    32   cnt=0;
    33   for (i=1;i<=n;i++)
    34     scanf("%d",&a[i]);
    35   for (i=1;i<=n;i++)
    36     {
    37       t=gcd(a[i],t);
    38     }
    39   int x=m/t;
    40   while (x%2==0) x/=2;
    41   if (x!=1)
    42     {
    43       cout<<"no
    ";
    44       cout<<"0
    ";
    45       return;
    46     }
    47   dfs(t);
    48   cout<<"yes
    ";
    49   cout<<cnt<<endl;
    50   for (i=cnt;i;i--)
    51     printf("%d %d
    ",l[i],r[i]);
    52 }
    53 int main()
    54 {int T;
    55   cin>>T;
    56   while (T--)
    57     {
    58       work();
    59     }
    60 }
  • 相关阅读:
    pch”预编译头文件来自编译器的其他版本,或者预编译头为 C++ 而在 C 中使用它(或相反) and vs找不到路径
    VC++获得当前系统时间的几种方案
    无法解析的外部符号 __imp____glutInitWithExit@12,该符号在函数 _glutInit_ATEXIT_HACK@8 中被引用
    error C2381: “exit” : 重定义
    vs2019 link glaux.lib 无法解析的外部符号,是缺少一个Lib
    操作系统算法整理+汇总
    vs2019配置glm包
    第二题 既约分数
    死磕Spring之IoC篇
    精尽Spring Boot源码分析
  • 原文地址:https://www.cnblogs.com/Y-E-T-I/p/8653356.html
Copyright © 2011-2022 走看看