最短部分文字列を見つけるために、ネットワーク全体には何の問題もありません。< @ _ @ >
最初はわずか18ポイント。私はそれに頼っています、私がクラスAにいたときにそれを少し最適化しました、そしてそれはACであることがわかりました[Hey from it〜]
サブは 、文字列の連続部分です。 サブシーケンスは 、連続的又はないかもしれない文字列の一部であるが、要素の順序が維持されています。たとえば、文字列が与えられた atpaaabpabtt
場合、pabt
は部分文字列であり、 は部分列 pat
です。
文字列Sと部分列Pが与えられると、Pを含むSの最短の部分文字列が見つかるはずです。そのような解が一意でない場合は、左端の部分列を出力します。
部分文字列は文字列の連続部分であり、部分文字列は文字列内の文字の順序を維持するサブセットであり、連続または不連続にすることができます。たとえば、与えられた文字列 atpaaabpabtt
、pabt
部分文字列、および pat
はサブ配列です。
文字列Sと部分列Pが与えられた場合、この質問では、Pを含むS内の最短の部分文字列を見つけるように求められます。解が一意でない場合は、開始点から左端の解が出力されます。
入力フォーマット:
各入力ファイルには、2行で構成される1つのテストケースが含まれています。最初の行にはSが含まれ、2番目の行はPです。Sは空ではなく、104以下の英字で構成されています。PはSの空でないサブシーケンスであることが保証されています。
入力により、最初の行に文字列Sが、2番目の行にPが表示されます。Sは空ではなく、104個以下の小文字の英字で構成されます。PはSの空でないサブ列であることが保証されています。
出力フォーマット:
いずれの場合も、Pを含むSの最短の部分文字列を出力します。そのような解が一意でない場合は、左端の部分文字列を出力します。
Pを含むSの最短の部分文字列を1行に出力します。解が一意でない場合は、開始点から左端の解が出力されます。
入力サンプル:
atpaaabpabttpcat
pat
サンプル出力:
pabt
分析:
非常に簡単で、暴力の方法は問題を解決します。まず、文字列内のすべての部分文字列の最初の文字を見つけて、配列で記録します。配列の長さは、文字列内で可能な部分文字列の数です。次に、文字列を1つずつ検索し、最小の長さのサブ列を出力します。
コード:
#include<bits/stdc++.h> //好东西,实在是令人省心
using namespace std;
int main(){
string s,p;
cin>>s>>p;
vector<int> v;
for(int i=0;i<s.size();i++)
if(s[i]==p[0]) v.push_back(i);//找出整个字符串和子串第一个字符相同的所有元素的下标
int minlen=s.size()+1,mini=0;
for(int i=0;i<v.size();i++){//s中可能的子串数
int cnt=1;//已经找完第一个了
for(int j=v[i]+1;j<s.size();j++){
if(s[j]==p[cnt]) cnt++; //找子串的第1~p.size()-1个字符
if(cnt==p.size()){//找完了
if(j-v[i]<minlen){
minlen=j-v[i];
mini=v[i];
}
break;
}
}
}
for(int i=mini;i<=mini+minlen;i++)
cout<<s[i];
return 0;
}
実際、私が言いたいのは、詳細が最も重要であるということです!!!それをしたとき、私は目がくらみました。私はいつも私をjと見なし、jを私と見なしました。私は言葉を失いました。。。
率直に言って、それは論理的な問題です。。。
でも確かに、私が苦手なのは複雑なロジックの問題です〜