2018-03-03 URL映射【字符串匹配】【90分】

呜呜呜我好菜o(╥﹏╥)o 找了好久好久了,90分,剩下的那十分不知道在哪

这几点要注意:

1.不需要考虑字符的合法性。题里边提到了,后边注意里边还专门说了保证输入的规则都是合法的。我以为他的意思是不保证输入的地址是合法的,还专门判断了一下地址是否合法,后来事实证明没必要

2.注意规则的最后是'/',还有待匹配字符串最后是'/'两种情况组合

3.考虑待匹配字符串比规则短的情况

4.一些自测样例

1 3
/articles/2003/ special_case_2003
/articles/2003
/articles/2003/
/articles/2004/2003
输出
404
special_case_2003
404
#include<iostream>
#include<vector>
using namespace std;

struct rule {
	string ri;   //规则的名字
	vector<string> pi;  //规则的具体内容
	bool flag1;  //判断最后一个是否为/
} rules[101];


int main() {
	int n,m;
	cin>>n>>m;
	for(int i=0; i<n; i++) {
		string r,p;
		cin>>p>>r;
		rules[i].ri=r;
		if(p[p.length()-1]=='/') {  //最后一个字母是/
			rules[i].flag1=true;
		} else {
			rules[i].flag1=false;
		}
		//将规则按/分段,加入中
		string temp="";
		for(int j=0; j<p.length(); j++) {
			if(p[j]=='/') {
				for(j++; j<p.length(); j++) {
					if(p[j]=='/') {
						rules[i].pi.push_back(temp);
						temp="";
						j--;
						break;
					} else {
						temp+=p[j];
					}
				}
			}
		}
		if(temp!="") { //规则最后没有 /
			rules[i].pi.push_back(temp);
			temp="";
		}

//		for(int j=0;j<rules[i].pi.size();j++){
//			cout<<rules[i].pi[j]<<endl;
//		}
	}
	vector<string> res;
	int flag=0;   //=0表示匹配成功,1表示失败
	for(int i=0; i<m; i++) { //m条待匹配
		string str;
		cin>>str;
		string temp;
		string tempstr=str;
		for(int k=0; k<n; k++) { //k条规则
			str=tempstr;
			if(str[str.length()-1]=='/') { //待匹配的最后一个字母是'/'
				if(rules[k].flag1) {  //该规则的最后一个字母是'/'
					if(rules[k].pi[rules[k].pi.size()-1]=="<int>" || rules[k].pi[rules[k].pi.size()-1]=="<str>") {  //删除待匹配字符串的最后一个/
						str=string(str,0,str.length()-1);
					} else if(rules[k].pi[rules[k].pi.size()-1]=="<path>" ) { //错误,<path>后边不能跟/
						flag=1;
						continue;;
					}

					else {  //最后一个是普通字符串,/可以匹配
						str=string(str,0,str.length()-1);
					}
				} else {    //待匹配字符串的最后一个字母是'/',但该规则的最后一个字母不是'/'
					if(rules[k].pi[rules[k].pi.size()-1]=="<path>" ) ;
					else {
						flag=1;
						continue;
					}

				}
			} else {  //待匹配的最后一个字母不是'/'
				if(rules[k].flag1) {
					flag=1;
					continue;
				} 
			}
			int cur=0;   //第k条规则的pi的第cur
			flag=0;
			res.clear();
			for(int j=0; j<str.length();) {
				if(cur>=rules[k].pi.size()) {
					flag=1;
					break;
				}
				if(rules[k].pi[cur]=="<int>") {   //匹配一个不带符号的整数
					temp="";
//					if(str[j]=='/'){
					for(j++; j<str.length(); j++) {
						if(str[j]=='/') {
							break;
						} else if(str[j]>='0' && str[j]<='9') { //满足整数条件
							temp+=str[j];
						} else {  //不是数字,不匹配
							flag=1;
							break;
						}
					}
//					}
					if(flag==1) {
						break;
					}

					while(temp[0]=='0') {  //去掉前导零
						temp=string(temp,1);
					}
					res.push_back(temp);
					cur++;
				} else if(rules[k].pi[cur]=="<str>") { //匹配一段字符串,字符串里不能包含斜杠
					temp="";
//					if(str[j]=='/'){
					for(j++; j<str.length(); j++) {
						if(str[j]=='/') {
							break;
						} else {
							temp+=str[j];
						}
					}
//					}
					res.push_back(temp);
					cur++;
				} else if(rules[k].pi[cur]=="<path>") { //匹配一段字符串,字符串可以包含斜杠
					temp="";
					for(j++; j<str.length(); j++) { //直接到结束了
						temp+=str[j];
					}
					res.push_back(temp);
					cur++;
				} else { //普通路径 url
					temp="";
//					if(str[j]=='/'){
					for(j++; j<str.length(); j++) {
						if(str[j]=='/') {
							break;
						} else {
							temp+=str[j];
						}
					}
//					}
					if(temp==rules[k].pi[cur]) ;
					else {
						flag=1;
					}
					cur++;
				}
				if(flag==1) break;   //不匹配,直接停止,匹配下一条规则
				else continue;       //成功匹配,继续匹配该规则的下一块
			}
			if(cur!=rules[k].pi.size()) {
				flag=1;
			}
			if(flag==0) {
				cout<<rules[k].ri;
				for(int p=0; p<res.size(); p++) {
					cout<<" "<<res[p];
				}
				cout<<endl;
				break;    //匹配成功一条就不匹配了
			}
		}
		if(flag==1) {
			cout<<"404"<<endl;
		}
	}
	return 0;
}

 

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值