最长公共递增子序列(C++实现)

原创 2012年03月25日 12:29:14

典型的动态规划题目,可以吧题目转化为最长公共子序列问题,输入一个序列,然后将其排序,储存在另一个数组中。

然后求两个数组的最长公共子序列,求出的最长公共子序列即为输入序列的最长递增子序列。本文还有一个关键部分就

是输出所有的最长递增子序列,代码中使用了一个path[N+1][N+1]数组记录过程,并用回溯的方法输出。

#include <iostream>

#include<string>
using namespace std;
const int N = 100;
int dp[N+1][N+1] ;
int path[N+1][N+1];//记录路径
char str1[N],str2[N];
void  print(int t,int i,int j)//是用回溯的方法输出,输出path[i][j]为0的点
{
    if(t == 0)
        return ;
    if(path[i][j] == 0)
    {
        print(dp[i-1][j-1],i-1,j-1);
        cout<<str2[j-1];
    }
    if(path[i][j] == 1)
        print(dp[i-1][j],i-1,j);
    if(path[i][j] == 2)
        print(dp[i][j-1],i,j-1);
}
int LCSL(int len)
{
    int i , j ;
    for( i = 0 ; i <= len; i++ )//初始化
    {
        dp[i][0] = 0 ;dp[0][i] = 0 ;
    }
    for( i = 1 ; i<= len ; i++)
        for( j = 1 ; j <= len ; j++)
        {
            if(str1[i - 1] == str2[j - 1])
            {
                dp[i][j] = dp[i - 1][ j - 1] + 1;
                path[i][j] = 0;//左上
            }
            else
            {
                if(dp[i - 1][ j ] >= dp[i][j - 1])
                {
                    dp[i][j] = dp[i - 1][ j ];
                    path[i][j] = 1;//上
                }
                else
                {
                    dp[i][j] = dp[i][j - 1];
                    path[i][j] = 2;//右
                }
            }
        }
    for(i=0;i<=len;i++) //输出dp[][]和path[][],括号里为path[][]
    {
        for(j=0;j<=len;j++)
            cout<<dp[i][j]<<"("<<path[i][j]<<")"<<" ";
        cout<<endl;
    }
    for(i=0;i<=len;i++)
    {
        for(j=0;j<=len;j++)
        {
            if(dp[i][j] == dp[len][len] && path[i][j] == 0)
            {
                print(dp[len][len],i,j);
                cout<<endl;
            }
        }
    }
    return dp[len][len];
}
void sort(int num)
{
    for(int i=0;i<num-1;i++)
        for(int j=0;j<num-1-i;j++)
        {
            if(str2[j]>str2[j+1])
            {
                char ch;
                ch = str2[j];
                str2[j] = str2[j+1];
                str2[j+1] = ch;
            }
        }
}
int main()
{
    int num;
    cout<<"输入字符个数:";
    cin>>num;
    cout<<"输入"<<num<<"个字符"<<endl;
    for(int i=0;i<num;i++)
    {
        cin>>str1[i];
        str2[i] = str1[i];
    }
    sort(num);
    LCSL(num);
    system("pause");
      return 0;
}

版权声明:本文为博主原创文章,未经博主允许不得转载。

相关文章推荐

ZCMU—1957

1957: 乌鸦坐飞机 Time Limit: 2 Sec  Memory Limit: 128 MB Submit: 83  Solved: 6 [Submit][Status][Web ...

动态规划之最长递增子序列 最长不重复子串 最长公共子序列

【前言】动态规划:与分治法相似,即通过组合子问题来求解原问题,不同的是分治法是将问题划分为互不相交的子问题,递归求解子问题,再将他们组合起来求出原问题的解。 动态规划则应用于子问题重叠的情况,通常用来...

最长递增子序列(原创)

最长递增子序列【实验目的】1 掌握动态规划和LCS的相关算法2 利用动态规划的思想实现最长递增子序列3 分析实验结果,总结算法的时间和空间复杂度。思考是否能将算法的时间复杂度提高到O(nlgn)【系统...

用C++求最长递增子序列

给定一个无序整数序列,怎样求其最长递增子序列?#include #include void MaxIncreaseQueue(const std::deque & source,std::deque ...

C++计算整数序列的最长递增子序列的长度

给定一个整数序列,计算其中的最长递增子序列的长度,这是一个典型的动态规划的算法。比如8个整数的序列 186 186 150 200 160 130 197 200,最长递增子序列是 150 160 1...

C++ 最长递增子序列问题

最长递增子序列问题:在一列数中寻找一些数,这些数满足:任意两个数a[i]和a[j],若i动态规划求一序列的最长子序列的长度,那么将问题变为在序列中求以a[k]为终点的最长上升子序列的长度aLen[k]...

最长递增子列、最长公共子序列 python实现

DP算法:最长公共子序列:把问题分成两种情况来讨论:1. 如果S1[i] == S2[j]。就是i,j对应位置上的字符相等。那么可以得出M[i,j] = M[i-1,j-1]+1;为什么呢?可以想象的...

最长递增子序列优化算法(时间复杂度为nlgn)C++实现

最长递增子序列优化算法(时间复杂度为nlgn) // 最长递增子序列优化算法.cpp : Defines the entry point for the console application. ...

最长单调递增公共子序列(路径记录+poj2127+zoj2432)Greatest Common Increasing Subsequence

Greatest Common Increasing Subsequence Time Limit: 10000MS   Memory Limit: 65536K Total Submis...
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:深度学习:神经网络中的前向传播和反向传播算法推导
举报原因:
原因补充:

(最多只允许输入30个字)