简化代码:
SELECT 'ok' WHERE '/articles/new/' ~ '^/articles/(?!new)([\w-]+)/$';
例子,我想要的:
'/articles/new/' => ''
'/articles/new-york/' => 'ok'
'/articles/other-string/' => 'ok'
然后,出了什么问题:
'/articles/new/' => ''
'/articles/new-york/' => '' /* Wrong */
'/articles/other-string/' => 'ok'
那么,我怎样才能只屏蔽这个词呢?
优化
在 PostgreSQL 数据库中,我有一个表 (page
),它有列 path, title, file, regex_path etc.
path
列中的值如下所示:
/
/articles/
/articles/:category-code/
/articles/:category-code/:article-code/
/articles/:category-code/:article-code/edit/
/articles/new/
/members/
/members/:username/
:
表示它是一个参数(PHP根据regex_path获取名称和内容——第一个版本)
数据库从外部 (PHP) 获取一个值 (URL)。示例:
/ /* Main page */
/articles/ /* List all article */
/articles/it/ /* List articles in IT category */
/articles/it/ipad-mini-2/ /* Article */
/articles/it/ipad-mini-2/edit/ /* Edit article */
/articles/new/ /* New article */
/members/ /* Member list */
/members/someone/ /* Member datasheet */
如何选择值 (URL) 与路径匹配的正确行(最快的方式,无需正则表达式)?
例子
在: /articles/it/ipad-mini-2/
出行,其中path
为:/articles/:category-code/:article-code/
最佳答案
这样更快:
SELECT *
FROM tbl
WHERE txt LIKE '/articles/%'
AND txt <> '/articles/new/'; -- only exclude this exact string
获取以“/articles/”开头的所有内容,但排除“/articles/new/”
或者,排除整个分支:
...
AND txt NOT LIKE '/articles/new/%';
要么包括“/articles/new-york/”,因为在这里,“new”后面没有紧跟着“/”。
性能测试
正则表达式通常比 LIKE
更昂贵或 =
或 <>
.
用 EXPLAIN ANALYZE
测试.或者 EXPLAIN (ANALYZE, TIMING OFF)
来抑制噪音。见:
我进行了测试以证实我的说法。它比正则表达式快 10 - 20 倍。
'^/articles(?!/new/)/([\w-]+)/$' -- Daniel's solution
.. 应该简化为(更快一点):
'^/articles/(?!new/)[\w-]+/$'
db<> fiddle here
<子>旧sqlfiddle
第二个正则表达式的解释:
^
... 字符串的开始
/articles/
... 文字匹配
(?!new/)
... negative lookahead匹配后面没有字符串 'new/' 的地方
[\w-]
... bracket expression包含 class shorthand \w
加上破折号 -
+
... 1 次或多次
/
... 文字匹配
$
... 字符串结束
关于正则表达式 url block 指定的词和优化,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17572830/