Sequence one

Problem Description
Search is important in the acm algorithm. When you want to solve a problem by using the search method, try to cut is very important.
Now give you a number sequence, include n (<=1000) integers, each integer not bigger than 2^31, you want to find the first P subsequences that is not decrease (if total subsequence W is smaller than P, than just give the first W subsequences). The order of subsequences is that: first order the length of the subsequence. Second order the sequence of each integer’s position in the initial sequence. For example initial sequence 1 3 2 the total legal subsequences is 5. According to order is {1}; {3}; {2}; {1,3}; {1,2}. {1,3} is first than {1,2} because the sequence of each integer’s position in the initial sequence are {1,2} and {1,3}. {1,2} is smaller than {1,3}. If you also can not understand , please see the sample carefully.

Input
The input contains multiple test cases.
Each test case include, first two integers n, P. (1



Output
For each test case output the sequences according to the problem description. And at the end of each case follow a empty line.

Sample Input
3 5 
1 3 2 
3 6 
1 3 2 
4 100 
1 2 3 2

Sample Output
1 3 
1 2 

1 3 
1 2 

1 2 
1 3 
2 3 
2 2 
1 2 3 
1 2 2 
题意:给你一个任意数列,让你求出所有的递增子序列;
解题思路:深搜,以长度为搜索的变量,从1-n,n为当前搜索的长度;每搜索到一个序列输出一个序列;后面这几个题越来越难写了0.0;
感悟:不能看题解,越看越毁啊!
代码:
#include
#include
#include
#include
#include
#define maxn 1001
using namespace std;
int n,p,pos[maxn],ans,len,pot[maxn],op[maxn];
bool flag;
void printf(int len)
{
    for(int i=0;i
        printf(i?" %d":"%d",pot[i]);
    printf("\n");
}
bool check(int s,int e)
{
    for(int i=s+1;i
    if(pos[i]==pos[e])
        return false;//如果这个数在前面出现过了就不能用了
    return true;
}

void dfs(int cur,int t)//cur表示当前需要派到第几位了,t表示当前搜索到第几位了
{
    if(ans>=p) return;//大于p的就不需要搜了
    if(cur==len)
    {
        ans++;
        flag=true;
        printf(len);//将数组输出
        return;
    }
    for(int i=t;i
    {
        if((cur&&pot[cur-1]<=pos[i])||!cur)
        //1  不是第一位的并且可以用这个数
        //2  是第一位的
        {
            if(!cur&&!check(-1,i))//第0位没法比较这个数在前没出现没出现过
            //所以只能用-1来比较
                continue;
            if(cur&&!check(op[cur-1],i))//这才能比较
                continue;
            pot[cur]=pos[i];
            op[cur]=i;//记录到第几位了
            dfs(cur+1,i+1);//不是从t+1开始搜的,而是从你找到这个数的下一位开始搜的
        }
    }
    return ;
}
int main()
{
    //freopen("in.txt", "r", stdin);
    while(scanf("%d%d",&n,&p)!=EOF)
    {
        memset(pos,0,sizeof pos);
        memset(pot,0,sizeof pot);
        for(int i=0;i
            scanf("%d",&pos[i]);
        ans=0;
        for(int i=1;i
        {
            flag=false;
            len=i;
            dfs(0,0);
            if(ans>=p||!flag) break;
        }
        printf("\n");
    }
    return 0;
}

转载于:https://www.cnblogs.com/wuwangchuxin0924/p/5781602.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值