CCF-201803-3-URL映射(python3)100分

问题描述

  本题中 URL 映射功能的配置由若干条 URL 映射规则组成。当一个请求到达时,URL 映射功能会将请求中的 URL
地址按照配置的先后顺序逐一与这些规则进行匹配。当遇到第一条完全匹配的规则时,匹配成功,得到匹配的规则以及匹配的参数。若不能匹配任何一条规则,则匹配失败。
  本题输入的 URL 地址是以斜杠 / 作为分隔符的路径,保证以斜杠开头。其他合法字符还包括大小写英文字母、阿拉伯数字、减号 -、下划线
_ 和小数点 .。例如,/person/123/ 是一个合法的 URL 地址,而 /person/123? 则不合法(存在不合法的字符问号 ?)。另外,英文字母区分大小写,因此 /case/ 和 /CAse/ 是不同的 URL 地址。   对于 URL
映射规则,同样是以斜杠开始。除了可以是正常的 URL 地址外,还可以包含参数,有以下 3 种:   字符串 <
str>:用于匹配一段字符串,注意字符串里不能包含斜杠。例如,abcde0123。   整数 <
int>:用于匹配一个不带符号的整数,全部由阿拉伯数字组成。例如,01234。   路径 <
path>:用于匹配一段字符串,字符串可以包含斜杠。例如,abcd/0123/。   以上 3
种参数都必须匹配非空的字符串。简便起见,题目规定规则中 < str> 和 < int>
前面一定是斜杠,后面要么是斜杠,要么是规则的结束(也就是该参数是规则的最后一部分)。而 < path>
的前面一定是斜杠,后面一定是规则的结束。无论是 URL 地址还是规则,都不会出现连续的斜杠。

啊 多数都是废话 看一下就好 不过有 刚开始有三点坑的地方

1 * 前面一定是斜杠,后面要么是斜杠,要么是规则的结束(也就是该参数是规则的最后一部分)*
2 地址按照配置的先后顺序逐一与这些规则进行匹配。

第三点就有点 让人想想就忧桑
在这里面

输出格式   
输入共 m 行,第 i 行表示 qi 的匹配结果。如果匹配成功,设匹配了规则 pj ,则输出对应的
rj。同时,如果规则中有参数,则在同一行内依次输出匹配后的参数。注意整数参数输出时要把前导零去掉。相邻两项之间用一个空格字符分隔。如果匹配失败,则输出404

注意 输出是要把前导零去掉。。

那上张图看看 结果
这里写图片描述
对是对了 代码也不长
但是
时间空间感觉还是不少
等 以后再优化一下吧
毕竟 python 嘛 简单 好用
但是肯定效率比不上c++

吼接下来就是上代码了

import re
import collections
#读取数据
num=input()
m,n=int(num.split()[0]),int(num.split()[1])
example_list=['']*(m+n)
for i in range(m+n):
    example_list[i]=input()
#输入一条规则 输出正则表达式
def cut_rule(rule):
    result=''
    for i in re.findall(r'(/[^/]*)',rule):
        #按照/.的格式分割
        if re.match(r"/\<int\>",i):
            result+="/(\d+)"
        elif re.match(r'/\<str\>',i):
            result+="/(\w+)"
        elif re.match(r'/\<path\>',i):
            result+="/([\w/.]*)"
        else:
            result+=i
        #同时处理 了 正常的URL和结尾的处的/ 或者 ' ' 
    return result+'$'
#稍微包装了一下
def get_rule(rule_list):
    resultMap=collections.OrderedDict()
    for r in rule_list:
         resultMap[r.split(' ')[1]]=cut_rule(r.split(' ')[0])
    return resultMap
#主函数 
for test in example_list[m:n+m]:
    for name,rule in get_rule(example_list[0:m]).items():
        a=re.match(rule,test)
        if a:
            print(name,end=' ')
            for i in a.groups():
                print(int(i) if i.isdigit() else i,end=' ')
            #输出 去掉前导零的 数字
            print()
            break
    else:
        print(404)

啊 真是 人生苦短 我用python 啊
整体上 关于正则表达式的运用 并不是太难
难点在于 阅读理解 。。
尤其注意 输出格式 和 规则 的描述 以及
题目 中 的 “注意”
吼 就是这样子
好吧其实打算用C++做的 也写完了 不过用的正则表达式
但是吧 CCF 官网 不支持 C++ 的正则表达式 。。
我上次了n次 每次都是 编译错误 一脸懵逼
所以用了python 写的 之后 学习一下python的re模块是如何把正则表达式解析 的然后 再 用c++练习一下

猜你喜欢

转载自blog.csdn.net/weixin_39722329/article/details/81739114