Lesha and array splitting CodeForces - 754A

One spring day on his way to university Lesha found an array A. Lesha likes to split arrays into several parts. This time Lesha decided to split the array A into several, possibly one, new arrays so that the sum of elements in each of the new arrays is not zero. One more condition is that if we place the new arrays one after another they will form the old array A.

Lesha is tired now so he asked you to split the array. Help Lesha!

Input

The first line contains single integer n (1 ≤ n ≤ 100) — the number of elements in the array A.

The next line contains n integers a1, a2, ..., an ( - 103 ≤ ai ≤ 103) — the elements of the array A.

Output

If it is not possible to split the array A and satisfy all the constraints, print single line containing "NO" (without quotes).

Otherwise in the first line print "YES" (without quotes). In the next line print single integer k — the number of new arrays. In each of the next k lines print two integers li and ri which denote the subarray A[li... ri] of the initial array A being the i-th new array. Integers li, ri should satisfy the following conditions:

    l1 = 1
    rk = n
    ri + 1 = li + 1 for each 1 ≤ i < k.

If there are multiple answers, print any of them.

Example
Input

3
1 2 -3

Output

YES
2
1 2
3 3

Input

8
9 -12 3 4 -4 -10 7 3

Output

YES
2
1 2
3 8

Input

1
0

Output

NO

Input

4
1 2 3 -5

Output

YES
4
1 1
2 2
3 3
4 4

题意:
就是让这个数列分为几个小部分,每一部分相加都不为0,将每一部分的下标的最左和最右分别输出。

思路:
一共有两种:
一:只需要考虑这个数列相加等于0不?如果不等于0则让其整个一部分为一部分,如果等于0的话则让分为两部分,第一个不是0的数之前微一部分,之后又微一部分,全为0的话输出NO。

代码:

#include<iostream>
#include<cstdio>
using namespace std;
int a[105];
int main()
{
    int t;
    while(scanf("%d",&t)!=EOF)
    {
        int sum=0,x=0;
        for(int i=1;i<=t;i++)
        {
            scanf("%d",&a[i]);
            sum+=a[i];
            if(a[i]==0)
                x++;
        }
        if(x==t)
        {
           cout<<"NO"<<endl;
           continue;
        }
        if(sum==0)
        {
            for(int i=1;i<=t;i++)
            {
                if(a[i]!=0)
                {
                    cout<<"YES"<<endl;
                    cout<<"2"<<endl;
                    cout<<"1"<<" "<<i<<endl;
                    cout<<i+1<<" "<<t<<endl;
                    break;
                }
            }
        }
        else
        {
            cout<<"YES"<<endl;
            cout<<"1"<<endl;
            cout<<"1"<<" "<<t<<endl;
        }
    }
}

二:显而易见只有全0的时候不存在分法,其他的肯定都存在。现在我们来看,如果这个串首位不为0,那么我们将其作为开头,看他的下一位是否是0,如果是0,则一直包含,直到遇到下一个不为0的数;如果这个串的首位是0,那么我们要看这个0的位置是不是总串的首位,如果是,那么找到后面第一个不为0的数作为这个字串的末尾,如果这个0不是总串的首位,则将其包含到前一个字串的末尾(以 0 0 1 0 0这个例子做理解)

代码:

#include<iostream>
#include<cstdio>
#include<string.h>
using namespace std;
int a[105];
int main()
{
    int t;
    while(scanf("%d",&t)!=EOF)
    {
        int x=0;
        for(int i=1;i<=t;i++)
        {
            scanf("%d",&a[i]);
            if(a[i]==0)
                x++;
        }
        if(x==t)
        {
            cout<<"NO"<<endl;
            continue;
        }
        int sum=1;
        int ans=0;
        int f[105][2];
        memset(f,0,sizeof(f));
        for(int i=1;i<=t;i++)
        {
            f[sum][0]=i;
            if(a[i]!=0)
            {
                while(a[i+1]==0&&i<t)
                {
                    i++;
                }
                f[sum++][1]=i;
            }
            else
            {
                if(i==1)
                {
                    while(i<t)
                    {
                        i++;
                        if(a[i]!=0)
                        {
                            f[sum++][1]=i;
                            break;
                        }
                    }
                }
                else
                {
                    f[sum-1][1]++;
                }
            }
        }
        cout<<"YES"<<endl;
        cout<<sum-1<<endl;
        for(int i=1;i<sum;i++)
        {
            cout<<f[i][0]<<" "<<f[i][1]<<endl;
        }
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值