题目描述:一个{1, ..., n}的子集S被称为JZP集,当且仅当对于任意S中的两个数x,y,若(x+y)/2为整数,那么(x+y)/2也属于S。例如,n=3,S={1,3}不是JZP集,因为(1+3)/2=2不属于S。但是{1,2,3}的其他子集都属于S,所以n=3时有7个JZP集给定n,求JZP集的个数。

  输入:第一行为T,表示输入数据组数。每组数据包含一行整数n。限制条件:1<=T<=10^5,1<=n<=10^7

  输出:对第i组数据,输出Case #i:然后输出JZP集的个数。

  这道题目考的知识主要是素数筛选,直接对每个n,求对应的JZP集肯定是会超时的(开始我也是如此,以为很简单的一道题,没想到一提交就是超时),后来用递推的思路改进下才pass。下面分享下我的答题思路:

  首先,先从简单的情况分析:

  n = 1时,JZP1 = {{},{1}} ,个数为2;

  n = 2时,JZP2 = {{}, {1}, {2}, {1,2}},个数为4

  n = 3时,JZP3 = {{}, {1}, {2}, {1,2}, {3}, {2,3}, {1,2,3}},个数为7

  n = 4时,JZP4 = {{}, {1}, {2}, {1,2}, {3}, {2,3}, {1,2,3}, {4}, {3,4}, {1,4}, {2,3,4},{1,2,3,4}},个数为12

  n = 5时,JZP5 = ...

  从上面的JZP集合来看,一个{1...n}的集合中满足JZP的集合有:空集{},只有一个元素的集合{k}(1 <= k <= n),包含两个或两个以上元素的集合{a1,a2,a3...ak}(2 <= ak <= n,ak - ak-1 = 2 * x + 1, 0 <= x <= (n - 2)/ 2),也就是说每个满足条件的集合中的元素是等差数列,数列的差值可以取值为1,3,5,7,9...2*x+1(0 <= x <= (n - 2)/ 2)。

  根据上面的思路,对每个差值1,3,5,7,9...2*x+1(0 <= x <= (n - 2)/ 2),在找出{1...n}的集合中找出满足这个差值的最大等差数列,即{1,2,3,4...n}(差值为1);{1,4,7,10...},{2,5,8,11...},{3,6,9,12...}(差值为3);{1,6,11,16...},{2,7,12,17...},{3,8,13,18},{4,9,14,19..},{5,10,15,20...}(差值为5)...。然后再这些集合中选出2个或2个以上的相邻元素作为子集合就是满足题目的JZP集。所以一个{1...n}的集合中JZP集合的个数为:1 + n + {n * (n - 1) / 2} + {(n % 3) * (n / 3) * ( n / 3 + 1) / 2  + (3 - n % 3) * (n / 3) * ( n / 3 - 1) / 2} + {(n % 5) * (n / 5) * ( n / 5 + 1) / 2  + (5 - n % 5) * (n / 5) * ( n / 5 - 1) / 2} + ...。

  所以对于一个给定的n,我们可以直接求出JZP集的个数,时间复杂度为O(n),再看题目有T组数据,所以总的复杂度是O(n * T),而1<=T<=10^5,1<=n<=10^7,显然复杂度过大,容易想到的方法是提前求出n为1~10^7所对应的JZP集个数,并存在数组中,后面对每组数据,直接查数组就可以了。现在关键是怎么求n为1~10^7所对应的JZP集个数,如果还是按前面的方法对每个数n都直接求对应的JZP集的个数,复杂度为O(n^2),显然这是会超时的。可不可以利用前面n-1对应的JZP集的个数求n对应的JZP集的个数呢?如果可以这样就减少了重复计算的次数,假设dp[n - 1]表示n - 1对应的JZP集的个数,现在分析dp[n]与dp[n - 1]的关系,n相对于n-1增加的JZP集有{n},差值为1的数列中增加的JZP集为n - 1,差值为3的数列中增加的JZP集为 (n - 1) / 3,...,所以dp[n] = dp[n - 1] + 1 + (n - 1) + (n - 1) / 3 + (n - 1) / 5 + ... + 1,关键是求(n - 1) + (n - 1) / 3 + (n - 1) / 5 + ... + 1了,假设temp[n] = (n - 1) + (n - 1) / 3 + (n - 1) / 5 + ... + 1,那么temp[n] = temp[n - 1] + cn(n - 1),其中cn(n - 1)是整除n - 1的所有奇数的个数,现在问题简化为求一个数能被多少个奇数整除,用暴力肯定不行,想想这个和素数的思路差不多,素数筛选的方法能用O(nlogn)的复杂度求出1~n中的每个数被奇数整除的个数,也就是整个算法的复杂度是O(nlogn),这个时间复杂度应该够了。

  有了上面的分析,实现代码就简单了,具体代码如下:

 #include <iostream>
using namespace std; long long dp[];
long long cn[];
int main()
{
int t, n;
long long ans, cnt; for (int j = ; j <= ; j += )
{
for (int i = j; i <= ; i += j)
cn[i]++;
}
dp[] = ;
cnt = ;
for (int j = ; j <= ; j++)
{
cnt += cn[j - ];
dp[j] = dp[j - ] + cnt + ;
}
cin >> t;
for (int i = ; i < t; i++)
{
cin >> n;
cout << "Case #" << i + << ":" << endl << dp[n] << endl;
}
return ;
}

2014年百度之星程序设计大赛 - 初赛(第二轮)JZP Set的更多相关文章

  1. 2014年百度之星程序设计大赛 - 初赛(第二轮)Chess

    题目描述:小度和小良最近又迷上了下棋.棋盘一共有N行M列,我们可以把左上角的格子定为(1,1),右下角的格子定为(N,M).在他们的规则中,“王”在棋盘上的走法遵循十字路线.也就是说,如果“王”当前在 ...

  2. HDU 4834 JZP Set(数论+递推)(2014年百度之星程序设计大赛 - 初赛(第二轮))

    Problem Description 一个{1, ..., n}的子集S被称为JZP集,当且仅当对于任意S中的两个数x,y,若(x+y)/2为整数,那么(x+y)/2也属于S.例如,n=3,S={1 ...

  3. HDU 4833 Best Financing(DP)(2014年百度之星程序设计大赛 - 初赛(第二轮))

    Problem Description 小A想通过合理投资银行理财产品达到收益最大化.已知小A在未来一段时间中的收入情况,描述为两个长度为n的整数数组dates和earnings,表示在第dates[ ...

  4. HDU 4832 Chess(DP+组合数学)(2014年百度之星程序设计大赛 - 初赛(第二轮))

    Problem Description 小度和小良最近又迷上了下棋.棋盘一共有N行M列,我们可以把左上角的格子定为(1,1),右下角的格子定为(N,M).在他们的规则中,“王”在棋盘上的走法遵循十字路 ...

  5. 2014年百度之星程序设计大赛 - 初赛(第一轮) hdu Grids (卡特兰数 大数除法取余 扩展gcd)

    题目链接 分析:打表以后就能发现时卡特兰数, 但是有除法取余. f[i] = f[i-1]*(4*i - 2)/(i+1); 看了一下网上的题解,照着题解写了下面的代码,不过还是不明白,为什么用扩展g ...

  6. 2014年百度之星程序设计大赛 - 资格赛 第二题 Disk Schedule

    双调欧几里得旅行商问题是一个经典动态规划问题.<算法导论(第二版)>思考题15-1和北京大学OJ2677都出现了这个题目. 旅行商问题描写叙述:平面上n个点,确定一条连接各点的最短闭合旅程 ...

  7. HDU6383 2018 “百度之星”程序设计大赛 - 初赛(B) 1004-p1m2 (二分)

    原题地址 p1m2 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 131072/131072 K (Java/Others)Total ...

  8. HDU6380 2018 “百度之星”程序设计大赛 - 初赛(B) A-degree (无环图=树)

    原题地址 degree Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 131072/131072 K (Java/Others)Tot ...

  9. HDU 6118 度度熊的交易计划 【最小费用最大流】 (2017"百度之星"程序设计大赛 - 初赛(B))

    度度熊的交易计划 Time Limit: 12000/6000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total S ...

随机推荐

  1. 怎么统计指定文件夹下含有.xml格式的文件数目

    如何统计指定文件夹下含有.xml格式的文件数目?如题 ------解决思路----------------------Directory.GetFiles(@"路径", " ...

  2. Firefox页面缩放

    这一段firefox只能缩放文字,不能实现整个页面的缩放,各种尝试,最后发现是勾选了view--zoom--zoom text only!!(按alt键调出菜单)

  3. Ionic实战 自动升级APP(Android版)

    Ionic 框架介绍 Ionic是一个基于Angularjs.可以使用HTML5构建混合移动应用的用户界面框架,它自称为是"本地与HTML5的结合".该框架提供了很多基本的移动用户 ...

  4. bzoj3048+3049+3050

    这套月赛题不是特别难 T1:离散化+单调队列,队列里出现数的种类不超过K+1,找最大的num[a[i]] T2:一眼可以看出BFS+状压DP,还要SPFA预处理出各个块之间的dis T3:线段树,没什 ...

  5. 如何给GridView添加网格

    如何给gridview的单元格加上分割线 原文链接:http://www.jcodecraeer.com/a/anzhuokaifa/androidkaifa/2013/1227/1582.html ...

  6. Unity学习疑问记录之向量基础

    这里写得非常好了: http://blog.gamerisker.com/archives/347.html

  7. Form表单中的get和post的区别

    method="get/post",两种方式的区别 Form中的get和post方法,在数据传输过程中分别对应了GET和POST方法.二者主要区别如下: 1.Get将表单中数据的按 ...

  8. ABP理论学习之Abp Session

    返回总目录 本篇目录 介绍 注入Session 使用Session属性 介绍 当应用程序要求用户登录时,那么应用程序也需要知道当前用户正在执行的操作.虽然ASP.NET本身在展现层提供了Session ...

  9. UI控件(UIScrollView)

    @implementation ViewController - (void)viewDidLoad { [super viewDidLoad]; //创建一个scrollview UIScrollV ...

  10. 我的面板我做主 -- 淘宝UWP中自定义Panel的实现

    在Windows10 UWP开发平台上内置的XMAL布局面板包括RelativePanel.StackPanel.Grid.VariableSizedWrapGrid 和 Canvas.在开发淘宝UW ...