题目:
输入格式:
输出格式:
一个整数代表答案
数据范围
输入样例
5
11 121 22 12 2023
输出样例
1
样例解释
删除 2222,剩余 11,121,12,202311,121,12,2023 是接龙数列。
算法一:二维dp
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
const int N = 1e5+10;
int n;
int dp[N][10];
string s[N];
int main()
{
cin>>n;
for(int i=1;i<=n;i++)
cin>>s[i];
for(int i=1;i<=n;i++)
{
int a=s[i][0]-'0';
int b=s[i].back()-'0';
for(int j=0;j<=9;j++)
{
dp[i][j]=dp[i-1][j];//继承或者保留之前的结果
if(j==b)
dp[i][b]=max(dp[i][b],dp[i-1][a]+1);
}
}
int maxd=0;
for(int i=1;i<=9;i++)
maxd=max(maxd,dp[n][i]);
cout<<n-maxd<<endl;
return 0;
}
算法二:优化为滚动数组
#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
using namespace std;
const int N = 1e5+10;
int dp[2][10];
string s[N];
int main()
{
int n;
cin>>n;
for(int i=1;i<=n;i++)
cin>>s[i];
for(int i=1;i<=n;i++)
{
int a=s[i][0]-'0';
int b=s[i].back()-'0';
for(int j=0;j<=9;j++)
{
dp[i%2][j]=dp[(i-1)%2][j];
if(j==b)
dp[i%2][j]=max(dp[i%2][j],dp[(i-1)%2][a]+1);
}
}
int maxd=0;
for(int i=0;i<=9;i++)
maxd=max(maxd,dp[n%2][i]);
cout<<n-maxd<<endl;
return 0;
}
算法三:优化为一维数组
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
const int N = 10;
int dp[N];
int main()
{
int n;
cin>>n;
int maxd=0;
for(int i=0;i<n;i++)
{
string s;
cin>>s;
int a=s[0]-'0';
int b=s.back()-'0';
dp[b]=max(dp[b],dp[a]+1);
maxd=max(maxd,dp[b]);
}
cout<<n-maxd<<endl;
return 0;
}