如何从 URL 中删除后退路径/父路径


How to remove backpath/parentpath from the URL?

>输入:

http://foo/bar/baz/../../qux/

期望输出:

http://foo/qux/

这可以使用正则表达式来实现(除非有人可以提出更有效的替代方案(。

如果是前向查找,则简单如下:

/'.'.'/[^'/]+/

虽然我不熟悉如何对第一个"/"进行向后查找(即不做/[a-z0-9-_]+'/'.'./(。

我想到的解决方案之一是使用strrev然后应用正则表达式(第一个示例(,然后执行strrev。虽然我相信有一种更有效的方法。

这不是我见过的最清晰的问题,但如果我明白你在问什么,我认为你只需要像这样切换你所拥有的东西:

/[^'/]+/'.'./

。然后用/替换它

这样做,直到没有更换,你应该有你想要的

编辑

您的尝试似乎尝试匹配正斜杠/和两个点'.'.后跟斜杠/(或'/ - 它们都应该匹配相同的内容(,然后[^/]+一个或多个非斜杠字符,以斜杠/结尾。翻转它,您希望找到一个斜杠,后跟一个或多个非斜杠字符和一个终止斜杠,然后是两个点和一个最后一个斜杠。

您可能会困惑地认为正则表达式引擎会解析和使用事物(因此您不希望使用不后跟正确点数的目录名称(,但这不是它通常的工作方式 - 正则表达式引擎在替换或返回任何内容之前匹配整个表达式。因此,您可以有两个点后跟一个目录名称,或者一个目录名称后跟两个点 - 这对引擎没有影响。

如果你尝试使用斜杠封闭的Perl风格的语法,那么你当然需要使用'/来匹配你尝试匹配的任何斜杠,例如中间的斜杠,但我也建议匹配和替换url中的封闭斜杠: 我认为PHP会像

preg_replace('/'/[^'/]+'/'.'.'//', '/', $input)

(??

从技术上讲,您想要的是替换'/path1/path2/....的段。/../' by '/' 需要做的是匹配 'pathx/'^n'../'^n 这绝对不是正则表达式(上下文自由 Lenguaje(...但是大多数正则表达式库都支持一些非常规的 lenguajes,并且可以(通过大量努力(管理这些语言。

解决该问题的一种简单方法是保留在正则表达式中并循环几次,替换 '/[^./]+/.。/' by ''

如果你仍然要在一步中完成,则需要前瞻和分组,但很难写出来,(我不太习惯,但我会尝试(

编辑:

我只在 1 个正则表达式中找到了解决方案......但应使用 PCRE 正则表达式

([^/.]+/(?1)?'.'./)

我的解决方案基于以下链接:使用正则表达式 (PCRE( 匹配 a^n b^n c^n (例如 "aaabbbccc"(

(请注意,点在第一部分是"禁止的",你不能有path.1/path.2/如果你抱怨是相当复杂的,因为你应该承认它们但禁止'../' 在第一部分有效

此子表达式用于允许路径名,如"path1/">

[^/.]+/

此子表达式用于允许双点。

'.'./

您可以在https://www.debuggex.com/(记得将其设置为PCRE模式(

这是一个工作副本:https://eval.in/52675