前言:
关于一道字符串问题 想了整整一天(不断报错W( ̄_ ̄)W) 太折磨了 家人们 谁懂啊o(╥﹏╥)o
问题描述
现在有一些由英文字符组成的大小写敏感的字符串,你的任务是找到一个最长的字符串x,使得对于已经给出的字符串中的任意一个y,x或者是y的子串,或者x中的字符反序之后得到的新字符串是y的子串
输入
输入的第一行是一个整数t (1 <= t <= 10),t表示测试数据的数目。对于每一组测试数据,第一行是一个整数n (1 <= n <= 100),表示已经给出n个字符串。接下来n行,每行给出一个长度在1和100之间的字符串。
输出
对于每一组测试数据,输出一行,给出题目中要求的字符串x的长度。
样例输入
2 3 ABCD BCDFF BRCD 2 rose orchid
样例输出
2 2
解决方案:
提示:先找出最短的字符串,然后利用最短字符串从长到短产生搜索子串及其反序子串,然后进行匹配检测,难点应该是从长到短产生搜索子串时不能有遗漏..
那么 :
取子串可用strncpy(str1,str2+i,n)内置函数(str1表示取出的子串,str2+i表示从i开始在str2中取长度为n的字符串)
反序子串可用strrev(str)函数,但是有些编译器不支持strrev函数,所以我们不妨自己写一个strrev函数
//由于有些编译器不支持strrev,所以自己写一个strrev函数
char *strrev(char *str)
{
char *p1, *p2;
if (! str || ! *str)
return str;
for (p1 = str, p2 = str + strlen(str) - 1; p2 > p1; ++p1, --p2)
{
*p1 ^= *p2;
*p2 ^= *p1;
*p1 ^= *p2;
}
return str;
}
最后上代码 一把辛酸泪O(∩_∩)O哈哈~
#include<bits/stdc++.h>
using namespace std;
int t,n;
char a[15][105];
//由于有些编译器不支持strrev,所以自己写一个strrev函数
char *strrev(char *str)
{
char *p1, *p2;
if (! str || ! *str)
return str;
for (p1 = str, p2 = str + strlen(str) - 1; p2 > p1; ++p1, --p2)
{
*p1 ^= *p2;
*p2 ^= *p1;
*p1 ^= *p2;
}
return str;
}
int search(char *sourcestr){
int substrlen,found;
int mi1=strlen(sourcestr);
substrlen=strlen(sourcestr);
char str1[105],str2[105];
while(substrlen>0){
for(int j=0;j<=mi1-substrlen;j++){
strncpy(str1,sourcestr+j,substrlen);
strncpy(str2,sourcestr+j,substrlen);
str1[substrlen]=str2[substrlen]='\0';
*str2=*strrev(str2);
//关于指针有些不太明白
found=1;
for(int k=1;k<=n;k++){
if(strstr(a[k],str1)==NULL && strstr(a[k],str2)==NULL){
found=0;
break;
}
}
if(found==1){
return substrlen;
}
}
substrlen--;
}
}
int main(){
//freopen("text.txt","r",stdin);
cin>>t;
while(t--){
cin>>n;
int mi=101;
char source[105];
for(int j=1;j<=n;j++){
cin>>a[j];
if(strlen(a[j])<mi){
mi=strlen(a[j]);
strcpy(source,a[j]);
}
}
int cnt=search(source);
cout<<cnt<<'\n';
}
return 0;
}
重新写了一遍,最后漏了一种情况,只有一个字符相同时的情况,调了将近两小时O(∩_∩)O哈哈~
#include<bits/stdc++.h>
using namespace std;
int main(){
int t;
cin>>t;
while(t--){
int n;
cin>>n;
string str[105];
int k=0,mi=100;
for(int i=0;i<n;i++){
cin>>str[i];
if(str[i].length()<mi){
mi=str[i].length();
k=i;
}
}
int ma=0;
for(int i=0;i<mi;i++){
for(int j=i;j<mi;j++){//for(int j=i+1;j<mi;j++)是错的,因为可能是只有一个字符相同的情况o(╥﹏╥)o
char a[105];
int su=0;
for(int x=i;x<=j;x++)a[su++]=str[k][x];
a[su]='\0';//防止数组最后乱码
char b[105];
strcpy(b,a);
int len=strlen(a);
for(int y=0;y<len;y++){
b[y]=a[len-y-1];
}
int flag=1;
for(int p=0;p<n;p++){
if(str[p].find(a)==-1&&str[p].find(b)==-1)flag=0;
}
if(flag==1&&j-i+1>ma)ma=j-i+1;
}
}
cout<<ma<<'\n';
}
return 0;
}
总结:
好好学习 天天代码^_^