算法设计题4.3 等差数列

问题描述
    如果可以给定一个整数序列,可以把它分割为若干个等差数列。比如给定一个序列(8,6,4,2,1,4,7,10,2)可以被分割为( 8,6,4, 2)、( 1,4,7)和( 2)三个等差数列。不幸的是有些整数序列中包含缺失值,用-1 代替,缺失值的可以取大于0 的任意整数值。这种情况下随着缺失值的取值的变化,序列的分割情况也会发生变化。
编程任务
    给定一个整数序列 a = (a1,a2,...,an), ai 由正整数和-1 组成,-1 表示缺失值。求这个序列最少可以组成多少个等差数列
数据输出
    输出只有一行,最少的等差序列数。

python版:

n = int(input())
a = list(map(int, input().split()))
i = 0
ans = 0
while i < n:
    ans += 1
    i1 = i
    while i1 < n and a[i1] == -1:
        i1 += 1
    if i1 == n:
        break
    i2 = i1 + 1
    while i2 < n and a[i2] == -1:
        i2 += 1
    if i2 == n:
        break
    dist = i2 - i1
    step = (a[i2] - a[i1]) // dist
    if (a[i2] - a[i1]) % dist != 0 or (step > 0 and a[i1] - (i1 - i) * step <= 0):
        i = i2
        continue
    i3 = i2 + 1
    while i3 < n:
        nxt = a[i2] + step * (i3 - i2)
        if nxt <= 0 or (a[i3] != -1 and a[i3] != nxt):
            break
        i3 += 1
        
    i = i3
print(ans)

 C ++ 版:

#include<iostream>
#include<cstdio>
using namespace std;
__int64 a[200010],d;
int n;
int cnt=0;
int k=1;
int i,j;
int main(){
    cin>>n;
    for(i=1;i<=n;i++)
        scanf("%I64d",&a[i]);
    while(k<=n){
        cnt++;
        i=k;   
        while(a[i]==-1)i++;//找到第一个不为-1的数作为等差序列的开始   
        j=i+1;   
        while(a[j]==-1)j++;//找到第二个不为-1的数作为等差序列的结束
        if(j>n)
            break;
        d=(a[j]-a[i])/(j-i);
        if((a[j]-a[i])%(j-i)||a[j]-d*(j-k)<=0){
            k=j;
            continue;
        }
        k=j+1;
        while(k<=n&&a[j]+d*(k-j)>0&&(a[k]==-1||a[k]==a[j]+d*(k-j))){
            k++;
        }
    }
    cout<<cnt<<endl;
    return 0;
}
        

 

 

posted @ 2016-11-26 15:20  陈泽泽  阅读(1255)  评论(2编辑  收藏  举报