416D Population Size

来源:互联网 发布:柴庆丰事件知乎 编辑:程序博客网 时间:2024/06/06 20:42


题目 :    http://codeforces.com/problemset/problem/416/D


思路:从上一个等差数列的结尾加一处开始找两个非-1的数,算出公差。如果公差为小数或者该公差导致前面的一串-1中有可能会有数变成非正数,就将第一个非-1的数和前面的一堆-1和两数间的一堆-1作为第一个数列,再以第二个非-1的数开头找等差数列。否则就再向后找可以合并到这个等差数列的数加入这个数列,找不到了就从这个等差数列的结尾加一处再找等差数列。


最开始我想不出来,然后看了提示,按照提示写了。过了样例后提交了17次,然后再79个点死活过不去了。

主要是犯了这些错误:

    1、开头、结尾是-1时处理不当

    2、公差为小数时没有考虑

    3、应该用long long 型存储

                  ……





然后看了别人的程序,思路差不多,写的有些不同。我原来的程序是对每个数判断看能否加入前一个等差数列,而那个程序是按上面的思路写的,对于前面的-1变得小于等于0的情况处理的也好一些。我又写了一遍,然后就过了。


#include<stdio.h>#include<iostream>using namespace std;long long n;long long a[200005]= {0};long long sum=0;int main() {scanf("%I64d",&n);for(long long i=1; i<=n; i++) {scanf("%I64d",&a[i]);}long long i=1;while(i<=n) {sum++;long long firstnum=0,nextnum=0;for(long long j=i; j<=n; j++) {if(a[j]>=0) {if(firstnum==0) {firstnum=j;} else {nextnum=j;break;}}}if(nextnum==0) {break;}if((a[nextnum]-a[firstnum])%(nextnum-firstnum)!=0) {i=nextnum;continue;}long long d=(a[nextnum]-a[firstnum])/(nextnum-firstnum);if(a[nextnum]-(nextnum-i)*d<=0) {i=nextnum;continue;}long long x=a[nextnum];for(i=nextnum+1; i<=n; i++) {if(x+d<=0) {break;}if(a[i]==-1||a[i]==x+d) {x+=d;} else {break;}}}printf("%I64d",sum);return 0;}


1 0
原创粉丝点击