无需言 做自己 业 ,精于勤 荒于嬉.
- PCRE 正则语法 注释
-
发表日期:2021-07-01 08:57:01 | 来源: | 分类:PCRE 正则语法
-
注释
字符序列(?#标记开始一个注释直到遇到一个右括号。不允许嵌套括号。 注释中的字符不会作为模式的一部分参与匹配。
如果设置了 PCRE_EXTENDED 选项, 一个字符类外部的未转义的 # 字符就代表本行剩余部分为注释。
- PCRE 正则语法 性能
-
发表日期:2021-07-01 08:57:01 | 来源: | 分类:PCRE 正则语法
-
性能
模式中一些项可能比其他一些更加高效。 比如使用 [aeiou] 这样的字符类会比可选路径 (a|e|i|o|u) 高效。 一般而言, 用尽可能简单的构造描述需求是最高效的。 Jeffrey Friedl 书(精通正则表达式)中包含了很多关于正则表达式性能的讨论。
当一个模式以 .* 开始并且设置了 PCRE_DOTALL 选项时,模式通过PCRE隐式锚定, 因为它可以匹配字符串的开始。然而,如果 PCRE_DOTALL 没有设置,PCRE 不能做这个优化,因为.元字符不能匹配换行符,如果目标字符串包含换行符, 模式可能会从一个换行符后面开始匹配,而不是最开始位置。 比如,模式
(.*) second
匹配目标字符串 ”first\nand second”(\n 是一个换行符)第一个捕获子组结果是 ”and”。为了这样做, PCRE 尝试从目标字符串中每个换行符后开始匹配。如果你使用模式匹配没有换行符的目标字符串, 可以通过设置 PCRE_DOTALL 或以 ^.* 开始的模式明确指示锚定以获取最佳性能。 这样节省了 PCRE 沿目标字符串扫描查找换行符重新开始的时间。
小心模式中的无限重复嵌套。这在应用到不匹配字符串时可能会导致运行时间很长。 考虑模式片段
(a+)*
这个模式可以有 33 种方式匹配 ”aaaa”, 并且这个数字会随着字符串的长度的增加迅速增加. (*重复可以匹配0,1,2,3,4次, 并且除了0外每种情况+都有不同次数的匹配对应)。 当模式的剩余部分导致整个匹配失败的时候, PCRE原则上回尝试每种可能的变化, 这将会非常耗时。
对于一些简单的情况的优化是像
(a+)*b
这样紧接着使用原文字符串.。 在着手正式匹配工作之前,PCRE 检查目标字符串后面是否有 ”b” 字符, 如果没有就立即失败。然而当紧接着没有原文字符的时候这个优化是不可用的。 你可以比较观察(a+)*\d
和上面模式的行为差异。 前者在应用到整行的 ”a” 组成的字符串时几乎是立即报告失败, 而后者在目标字符串长于 20 个字符时,时间消耗就相当可观。
- PCRE 正则语法 后向引用
-
发表日期:2021-07-01 08:57:01 | 来源: | 分类:PCRE 正则语法
-
后向引用
在一个字符类外面, 反斜线紧跟一个大于 0 (可能还有一位数)的数字就是一个到模式中之前出现的某个捕获组的后向引用。
如果紧跟反斜线的数字小于 10, 它总是一个后向引用, 并且如果在模式中没有足够多的捕获组,将会引发一个错误。换而言之, 被引用的括号不能少于被引用的小于 10 的数量。 A "forward back reference" can make sense when a repetition is involved and the subpattern to the right has participated in an earlier iteration. 查看上面的”反斜线”部分查看具体的数字处理方式。
一个后向引用会直接匹配被引用捕获组在目标字符串中实际捕获到的内容, 而不是匹配子组模式的内容。因此,模式
(sens|respons)e and \1ibility
将会匹配 ”sense and sensibility” 和 ”response and responsibility”, 而不会匹配 ”sense and responsibility”。 如果在后向引用时被强制进行了大小写敏感匹配, 比如((?i)rah)\s+\1
匹配 ”rah rah”和”RAH RAH”,但是不会匹配 ”RAH rah”, 即使原始捕获子组自身是不区分大小写的。 译注: 这里其实要考虑的是后向引用期望得到的内容是和那个被引用的捕获子组得到的内容是完全一致的(当然, 我们可以通过在后向引用之前设定内部选项使其不区分大小写,或者增加模式修饰符, 同样可以达到不区分大小写的目的,但是, 这种做法实际上是从外部对其行为进行了控制。)可能会有超过一个的后向引用引用相同的子组。 一个子组可能并不会真正的用于特定的匹配,此时, 任何对这个子组的后向引用也都会失败。 比如, 模式
(a|(bc))\2
总是在匹配 ”a” 开头而不是 ”bc” 开头的字符串时失败。 因为可能会有多达 99 个后向引用, 所有紧跟反斜线后的数字都可能是一个潜在的后向引用计数。 如果模式在后向引用之后紧接着还是一个数值字符, 那么必须使用一些分隔符用于终结后向引用语法。 如果设置了 PCRE_EXTENDED 选项, 可以使用空格来做。其他情况下可以使用一个空的注释。如果一个后向引用出现在它所引用的子组内部, 它的匹配就会失败。比如, (a\1) 就不会得到任何匹配。然而这种引用可以用于内部的子模式重复。比如, 模式
(a|b\1)+
会匹配任意数量的 ”a” 组成的字符串以及 ”aba”, “ababba” 等等(译注: 因为子组内部有一个可选路径,可选路径中有一条路能够完成匹配,在匹配完成后, 后向引用就能够引用到内容了)。在每次子模式的迭代过程中, 后向引用匹配上一次迭代时这个子组匹配到的字符串。为了做这种工作, 模式必须满足这样一个条件,模式在第一次迭代的时候, 必须能够保证不需要匹配后向引用。 这种条件可以像上面的例子用可选路径来实现,也可以通过使用最小值为 0 的量词修饰后向引用的方式来完成。转义序列
\g
可以用于子模式的绝对引用和相对引用。 这个转义序列必须紧跟一个无符号数字或一个负数, 可以选择性的使用括号对数字进行包裹。 序列\1
,\g1
,\g{1}
之间是同义词关系。 这种用法可以消除使用反斜线紧跟数值描述反向引用时候产生的歧义。 这种转义序列有利于区分后向引用和八进制数字字符, 也使得后向引用后面紧跟一个原文匹配数字变的更明了,比如\g{2}1
。\g
转义序列紧跟一个负数代表一个相对的后向引用。比如:(foo)(bar)\g{-1}
可以匹配字符串 ”foobarbar”,(foo)(bar)\g{-2}
可以匹配 ”foobarfoo”。 这在长的模式中作为一个可选方案, 用来保持对之前一个特定子组的引用的子组序号的追踪。后向引用也支持使用子组名称的语法方式描述:
(?P=name)
、\k<name>
、\k’name’
、\k{name}
、\g{name}
、\g<name>
、\g'name'
。
- PCRE 正则语法 递归模式
-
发表日期:2021-07-01 08:57:01 | 来源: | 分类:PCRE 正则语法
-
递归模式
考虑匹配圆括号内字符串的问题,允许无限嵌套括号。如果不使用递归, 最好的方式是使用一个模式匹配固定深度的嵌套。它不能处理任意深度的嵌套。 perl 5.6 提供了一个实验性的功能允许正则表达式递归。 特殊项 (?R) 提供了递归的这种特殊用法。 这个PCRE模式解决了圆括号问题(假设 PCRE_EXTENDED 选项被设置了, 因此空白字符被忽略):
\( ( (?>[^()]+) | (?R) )* \)
首先,它匹配一个左括号。 然后它匹配任意数量的非括号字符序列或一个模式自身的递归匹配(比如, 一个正确的括号子串),最终,匹配一个右括号。
这个例子模式包含无限重复的嵌套,因此使用了一次性子组匹配非括号字符, 这在模式应用到模式不匹配的字符串时非常重要。比如, 当它应用到
(aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa()
时就会很快的产生”不匹配”结果。 然而,如果不使用一次性子组,这个匹配将会运行很长时间, 因为有很多途径让 + 和 * 重复限定分隔目标字符串, 并且在报告失败之前需要测试所有路径。所有捕获子组最终被设置的捕获值都是从递归最外层子模式捕获的值。 如果上面的模式匹配
(ab(cd)ef)
,捕获子组最终被设置的值为 ”ef”, 即顶级得到的最后一个值。如果增加了额外的括号\( ( ( (?>[^()]+) | (?R) )* ) \)
捕获到的字符串就是顶层括号的匹配内容 ”ab(cd)ef”。 如果在模式中有超过 15 个捕获括号, PCRE 在递归期间就会使用 pcre_malloc 分配额外的内存来存储数据, 随后通过 pcre_free 释放他们。如果没有内存可被分配,它就仅保存前 15 个捕获括号, 在递归内部无法给出内存不够用的错误。(?1)
、(?2)
等可以用于递归子组。 这同样可以用于命名子组:(?P>name)
或(?P&name)
。如果递归子组语法在它提到的子组括号外部使用(无论是子组数字序号还是子组名称), 这个操作就相当于程序设计语言中的子程序。 前面一些有一个例子指出模式
(sens|respons)e and \1ibility
匹配 ”sense and responsibility” 和 ”response and responsibility”,但是不匹配 ”sense and responsibility”。如果用模式(sens|respons)e and (?1)ibility
替代, 它会像匹配那两个字符串一样匹配 ”sense and responsibility”。 这种引用方式意义是紧接着匹配引用的子模式。(译注: 后向引用只匹配引用的子组之前匹配的结果, 这里的递归语法引用是拿引用的子模式重新匹配。)目标字符串的最大长度是 int 型变量可以存储的最大正整数。然而, PCRE 使用递归处理子组和无限重复。 这就是说对于某些模式可用的栈空间可能会受目标字符串限制。
- PCRE 正则语法 简介
-
发表日期:2021-07-01 08:57:00 | 来源: | 分类:PCRE 正则语法
-
简介
下面描述的是 PCRE 支持的正则表达式语法和语义。正则表达式在 perl 的文档 和另外一些书籍中也有讨论, 其中一些会有丰富的示例。O'Reilly(ISBN 1-56592-257-3) 出版的 Jeffrey Friedl 的《精通正则表达式》一书非常详细的讨论了这些内容。 这里的描述仅作为一个参考手册。
正则表达式是一个从左到右匹配目标字符串的模式。大多数字符自身就代表一个匹配 它们自身的模式。 作为一个简单的例子,模式
The quick brown fox
匹配目标字符串中与其相同的部分。
- PCRE 正则语法 Unicode 字符属性
-
发表日期:2021-07-01 08:57:00 | 来源: | 分类:PCRE 正则语法
-
Unicode 字符属性
自 PHP 5.1.0 起, 三个额外的转义序列在选用 UTF-8 模式时用于匹配通用字符类型。他们是:
- \p{xx}
- 一个有属性 xx 的字符
- \P{xx}
- 一个没有属性 xx 的字符
- \X
- 一个扩展的 Unicode 字符
上面
xx
代表的属性名用于限制 Unicode 通常的类别属性。 每个字符都有一个这样的确定的属性,通过两个缩写的字母指定。 为了与 Perl 兼容, 可以在左花括号 { 后面增加 ^ 表示取反。比如:\p{^Lu}
就等同于\P{Lu}
。如果通过
\p
或\P
仅指定了一个字母,它包含所有以这个字母开头的属性。 在这种情况下,花括号的转义序列是可选的;以下两个例子是等同的:\p{L} \pL
支持的 Unicode 属性 Property Matches Notes C
Other Cc
Control Cf
Format Cn
Unassigned Co
Private use Cs
Surrogate L
Letter 包含以下属性: Ll
、Lm
、Lo
、Lt
、Lu
.Ll
小写字母 Lm
Modifier letter Lo
Other letter Lt
Title case letter Lu
Upper case letter M
Mark Mc
Spacing mark Me
Enclosing mark Mn
Non-spacing mark N
Number Nd
Decimal number Nl
Letter number No
Other number P
Punctuation Pc
Connector punctuation Pd
Dash punctuation Pe
Close punctuation Pf
Final punctuation Pi
Initial punctuation Po
Other punctuation Ps
Open punctuation S
Symbol Sc
Currency symbol Sk
Modifier symbol Sm
Mathematical symbol So
Other symbol Z
Separator Zl
Line separator Zp
Paragraph separator Zs
Space separator InMusicalSymbols
等扩展属性在 PCRE 中不支持指定大小写不敏感匹配对这些转义序列不会产生影响,比如,
\p{Lu}
始终匹配大写字母。Unicode 字符集在具体文字中定义。使用文字名可以匹配这些字符集中的一个字符。例如:
-
\p{Greek}
-
\P{Han}
不在确定文字中的则被集中到
Common
。当前的文字列表中有:支持的文字 Arabic
Armenian
Avestan
Balinese
Bamum
Batak
Bengali
Bopomofo
Brahmi
Braille
Buginese
Buhid
Canadian_Aboriginal
Carian
Chakma
Cham
Cherokee
Common
Coptic
Cuneiform
Cypriot
Cyrillic
Deseret
Devanagari
Egyptian_Hieroglyphs
Ethiopic
Georgian
Glagolitic
Gothic
Greek
Gujarati
Gurmukhi
Han
Hangul
Hanunoo
Hebrew
Hiragana
Imperial_Aramaic
Inherited
Inscriptional_Pahlavi
Inscriptional_Parthian
Javanese
Kaithi
Kannada
Katakana
Kayah_Li
Kharoshthi
Khmer
Lao
Latin
Lepcha
Limbu
Linear_B
Lisu
Lycian
Lydian
Malayalam
Mandaic
Meetei_Mayek
Meroitic_Cursive
Meroitic_Hieroglyphs
Miao
Mongolian
Myanmar
New_Tai_Lue
Nko
Ogham
Old_Italic
Old_Persian
Old_South_Arabian
Old_Turkic
Ol_Chiki
Oriya
Osmanya
Phags_Pa
Phoenician
Rejang
Runic
Samaritan
Saurashtra
Sharada
Shavian
Sinhala
Sora_Sompeng
Sundanese
Syloti_Nagri
Syriac
Tagalog
Tagbanwa
Tai_Le
Tai_Tham
Tai_Viet
Takri
Tamil
Telugu
Thaana
Thai
Tibetan
Tifinagh
Ugaritic
Vai
Yi
\X
转义匹配了 Unicode 可扩展字符集(Unicode extended grapheme clusters)。 可扩展字符集是一个或多个 Unicode 字符,组合表达了单个象形字符。 因此无论渲染时实际使用了多少个独立字符,可以视该 Unicode 等同于.
, 会匹配单个组合后的字符。小于 PCRE 8.32 的版本中(对应小于 PHP 5.4.14 的内置绑定 PCRE 库),
\X
等价于(?>\PM\pM*)
。 也就是说,它匹配一个没有 ”mark” 属性的字符,紧接着任意多个由 ”mark” 属性的字符。 并将这个序列认为是一个原子组(详见下文)。 典型的有 ”mark” 属性的字符是影响到前面的字符的重音符。用 Unicode 属性来匹配字符的速度并不快, 因为 PCRE 需要去搜索一个包含超过 15000 字符的数据结构。 这就是为什么在 PCRE中 要使用传统的转义序列
\d
、\w
而不使用 Unicode 属性的原因。
- PCRE 正则语法 转义序列(反斜线)
-
发表日期:2021-07-01 08:57:00 | 来源: | 分类:PCRE 正则语法
-
转义序列(反斜线)
反斜线有多种用法。首先,如果紧接着是一个非字母数字字符,表明取消 该字符所代表的特殊涵义。这种将反斜线作为转义字符的用法在字符类 内部和外部都可用。
比如,如果你希望匹配一个 "*" 字符,就需要在模式中写为 "\*"。 这适用于一个字符在不进行转义会有特殊含义的情况下。 但是, 对于非数字字母的字符,总是在需要其进行原文匹配的时候在它前面增加一个反斜线, 来声明它代表自己,这是安全的。如果要匹配一个反斜线,那么在模式中使用 ”\\”。
注意:
反斜线在单引号和双引号 PHP 字符串 中都有特殊含义。因此要匹配一个反斜线 \,正则表达式写法是 \\, 然后 PHP 代码中需要转义写成 "\\\\" 或 '\\\\'。
如果一个模式被使用 PCRE_EXTENDED 选项编译, 模式中的空白字符(除了字符类中的)和未转义的#到行末的所有字符都会被忽略。 要在这种情况下使用空白字符或者#,就需要对其进行转义。
反斜线的第二种用途提供了一种对非打印字符进行可见编码的控制手段。 除了二进制的 0 会终结一个模式外,并不会严格的限制非打印字符(自身)的出现, 但是当一个模式以文本编辑器的方式编辑准备的时候, 使用下面的转义序列相比使用二进制字符会更加容易:
- \a
- 响铃字符(十六进制 07)
- \cx
- "control-x",x 是任意字符
- \e
- 转义 (十六进制 1B)
- \f
- 换页 (十六进制 0C)
- \n
- 换行 (十六进制 0A)
- \p{xx}
- 一个符合 xx 属性的字符,详细查看unicode properties 属性
- \P{xx}
- 一个不符合xx属性的字符,详细查看unicode properties 属性
- \r
- 回车 (十六进制 0D)
- \R
- 换行符:能匹配 \n、\r、\r\n
- \t
- 水平制表符 tab (十六进制 09)
- \xhh
- hh 十六进制编码的字符
- \ddd
- ddd八进制编码的字符,或者后向引用
\cx
的确切效果如下: 如果x
是一个小写字母,它被转换为大写。接着, 将字符的第6位(十六进制 40,右数第一个位为第0位)取反。 比如\cz
成为十六进制的1A,\c{
成为十六进制3B,\c;
成为十六进制7B。在”
\x
”后面,读取两个十六进制数(字母可以是大写或小写)。 在UTF-8模式, “\x{…}
”允许使用, 花括号内的内容是十六进制有效数字。 它将给出的十六进制数字解释为 UTF-8 字符代码。原来的十六进制转义序列,\xhh
, 匹配一个双字节的UTF-8字符,如果它的值大于127在”
\0
”之后, 读取两个八进制数。所有情况下,如果数少于2个,则直接使用。 序列 ”\0\x\07
” 指定了两个二进制 0 紧跟着一个 BEL 字符。 请确保初始的 0 之后的两个数字是合法的八进制数。处理一个反斜线紧跟着的不是0的数字的情况比较复杂。在字符类外部, PCRE 读取它并以十进制读取紧随其后的数字。 如果数值小于 10, 或者之前捕获到了该数字能够代表的左括号(子组), 整个数字序列被认为是后向引用。后向引用如何工作在后面描述, 接下来就会讨论括号子组。
在一个字符类里面,或者十进制数大于 9 并且没有那么多的子组被捕获, PCRE 重新读取反斜线后的第三个 8 进制数字,并且从最低的 8 位生成单字节值。 任何的后续数字都代表它们自身。例如:
- \040
- 空格的另外一种用法
- \40
- 当提供了少于40个子组时也认为是空格。
- \7
- 始终是后向引用
- \11
- 可能是后向引用,也可能是制表符
- \011
- 总是一个制表符
- \0113
- 一个制表符紧跟着一个3(因为每次最多只读取3个8进制位
- \113
- 八进制113代表的字符(since there can be no more than 99 back references)
- \377
- 8进制377是10进制255, 因此代表一个全1的字符
- \81
- 一个后向引用或者一个二进制 0 紧跟着两个数字 8 和 1(因为8不是8进制有效数字)
注意,八进制值的 100 或者更大的值必须没有前置的0引导, 因为每次最多读取3个8进制位.
所有序列定义的单字节值都可以在字符类内部或外部使用。另外,在字符类中, 序列 ”
\b
” 解释为退格字符(hex 08)。 字符类外它又有不同的意义(下面有描述)。反斜线的第三种用法是用来描述特定的字符类:
- \d
- 任意十进制数字
- \D
- 任意非十进制数字
- \h
- 任意水平空白字符
- \H
- 任意非水平空白字符
- \s
- 任意空白字符
- \S
- 任意非空白字符
- \v
- 任意垂直空白字符
- \V
- 任意非垂直空白字符
- \w
- 任意单词字符
- \W
- 任意非单词字符
上面每一对转义序列都代表了完整字符集中两个不相交的部分, 任意字符一定会匹配其中一个,同时一定不会匹配另外一个。
"空白字符"(whitespace)是 HT (9)、LF (10)、FF (12)、CR (13)、space (32)。 然而,若发生了本地化匹配,在代码点 128-255 范围内亦可能出现空白字符, 比如说 NBSP (A0)。
单词字符指的是任意字母、数字、下划线。 也就是说任意可以组成perl单词的字符。 字母和数字的定义通过PCRE字符表控制,可以通过指定地域设置使其匹配改变。比如, 在法国 (fr) 本地化设置中,一些超过 128 的字符代码被用于重音字母, 它们可以实用
\w
匹配。这些字符类序列在字符类内部或外部都可以出现。 他们每次匹配所代表的字符类型中的一个字符。 如果当前匹配点位于目标字符串末尾, 它们中的所有字符都匹配失败, 因为没有字符让它们匹配了。
反斜线的第四种用法是一些简单的断言。 一个断言指定一个必须在特定位置匹配的条件, 它们不会从目标字符串中消耗任何字符。 接下来我们会讨论使用子组的更加复杂的断言。 反斜线断言包括:
- \b
- 单词边界
- \B
- 非单词边界
- \A
- 目标的开始位置(独立于多行模式)
- \Z
- 目标的结束位置或结束处的换行符(独立于多行模式)
- \z
- 目标的结束位置(独立于多行模式)
- \G
- 在目标中首次匹配位置
这些断言不能出现在字符类中(但是注意, “
\b
”在字符类中有不同的意义, 表示的是退格(backspace)字符)一个单词边界表示的是在目标字符串中, 当前字符和前一个字符不同时匹配
\w
或\W
(一个匹配\w
, 一个匹配\W
), 或者作为字符串开始或结尾字符的时候当前字符匹配\w
。\A
,\Z
,\z
断言不同于传统的^
和$
(详见 锚), 因为他们永远匹配目标字符串的开始和结尾,而不会受模式修饰符的限制。 它们不受PCRE_MULTILINE,PCRE_DOLLAR_ENDONLY选项的影响。\Z
和\z
之间的不同在于当字符串结束字符时换行符时\Z
会将其看做字符串结尾匹配, 而\z
只匹配字符串结尾。\G
断言在指定了offset
参数的preg_match() 调用中, 仅在当前匹配位置在匹配开始点的时候才是成功的。 当offset
的值不为 0 的时候, 它与\A
是不同的。 译注:另外一点与\A
的不同之处在于使用 preg_match_all() 时, 每次匹配\G
只是断言是否是匹配结果的开始位置, 而\A
断言的则是匹配结果的开始位置是否在目标字符串开始位置。\Q
和\E
可以用于在模式中忽略正则表达式元字符。比如:\w+\Q.$.\E$
会匹配一个或多个单词字符,紧接着.$.
, 最后锚向字符串末尾。\K
可以用于重置匹配。 比如,foot\Kbar
匹配”footbar”。 但是得到的匹配结果是 ”bar”。但是,\K
的使用不会干预到子组内的内容, 比如(foot)\Kbar
匹配 ”footbar”,第一个子组内的结果仍然会是 ”foo”。译注: \K 放在子组和子组外面的效果是一样的。
- PCRE 函数 preg_grep 返回匹配模式的数组条目
-
发表日期:2021-07-01 08:56:56 | 来源: | 分类:PCRE 函数
-
示例1
<?php // 返回所有包含浮点数的元素$fl_array = preg_grep("/^(\d+)?\.\d+$/", $array); ?>
- PCRE 函数 preg_match_all 执行一个全局正则表达式匹配
-
发表日期:2021-07-01 08:56:56 | 来源: | 分类:PCRE 函数
-
示例1
<?php preg_match_all("|<[^>]+>(.*)</[^>]+>|U", "<b>example: </b><div align=left>this is a test</div>", $out, PREG_PATTERN_ORDER); echo $out[0][0] . ", " . $out[0][1] . "\n"; echo $out[1][0] . ", " . $out[1][1] . "\n"; ?>
示例2
<?php preg_match_all( '/(?J)(?<match>foo)|(?<match>bar)/', 'foo bar', $matches, PREG_PATTERN_ORDER); print_r($matches['match']); ?>
示例3
<?php preg_match_all("|<[^>]+>(.*)</[^>]+>|U", "<b>example: </b><div align=\"left\">this is a test</div>", $out, PREG_SET_ORDER); echo $out[0][0] . ", " . $out[0][1] . "\n"; echo $out[1][0] . ", " . $out[1][1] . "\n"; ?>
示例4
<?php preg_match_all('/(foo)(bar)(baz)/', 'foobarbaz', $matches, PREG_OFFSET_CAPTURE); print_r($matches); ?>
示例5
<?php preg_match_all("/\(? (\d{ 3} )? \)? (?(1) [\-\s] ) \d{ 3} -\d{ 4} /x", "Call 555-1212 or 1-800-555-1212", $phones); ?>
示例6
<?php //\\2是一个后向引用的示例. 这会告诉pcre它必须匹配正则表达式中第二个圆括号(这里是([\w]+))//匹配到的结果. 这里使用两个反斜线是因为这里使用了双引号.$html = "<b>bold text</b><a href=howdy.html>click me</a>"; preg_match_all("/(<([\w]+)[^>]*>)(.*?)(<\/\\2>)/", $html, $matches, PREG_SET_ORDER); foreach ($matches as $val) { echo "matched: " . $val[0] . "\n"; echo "part 1: " . $val[1] . "\n"; echo "part 2: " . $val[2] . "\n"; echo "part 3: " . $val[3] . "\n"; echo "part 4: " . $val[4] . "\n\n"; } ?>
示例7
<?php $str = <<<FOOa: 1b: 2c: 3FOO; preg_match_all('/(?P<name>\w+): (?P<digit>\d+)/', $str, $matches); /* 选择方式 */ // preg_match_all('/(?<name>\w+): (?<digit>\d+)/', $str, $matches); print_r($matches); ?>
- PCRE 函数 preg_replace 执行一个正则表达式的搜索和替换
-
发表日期:2021-07-01 08:56:56 | 来源: | 分类:PCRE 函数
-
示例1
<?php $string = 'April 15, 2003'; $pattern = '/(\w+) (\d+), (\d+)/i'; $replacement = '${ 1} 1,$3'; echo preg_replace($pattern, $replacement, $string); ?>
示例2
<?php $string = 'The quick brown fox jumps over the lazy dog.'; $patterns = array(); $patterns[0] = '/quick/'; $patterns[1] = '/brown/'; $patterns[2] = '/fox/'; $replacements = array(); $replacements[2] = 'bear'; $replacements[1] = 'black'; $replacements[0] = 'slow'; echo preg_replace($patterns, $replacements, $string); ?>
示例3
<?php ksort($patterns); ksort($replacements); echo preg_replace($patterns, $replacements, $string); ?>
示例4
<?php $patterns = array ('/(19|20)(\d{ 2} )-(\d{ 1,2} )-(\d{ 1,2} )/', '/^\s*{ (\w+)} \s*=/'); $replace = array ('\3/\4/\1\2', '$\1 ='); echo preg_replace($patterns, $replace, '{ startDate} = 1999-5-27'); ?>
示例5
<?php $str = 'foo o'; $str = preg_replace('/\s\s+/', ' ', $str); // 将会改变为'foo o'echo $str; ?>
示例6
<?php $count = 0; echo preg_replace(array('/\d/', '/\s/'), '*', 'xp 4 to', -1 , $count); echo $count; //3?>
- PCRE 函数 preg_last_error_msg Returns the error message of the last PCRE regex execution
-
发表日期:2021-07-01 08:56:56 | 来源: | 分类:PCRE 函数
-
示例1
<?php preg_match('/(?:\D+|<\d+>)*[!?]/', 'foobar foobar foobar'); if (preg_last_error() !== PREG_NO_ERROR) { echo preg_last_error_msg(); } ?>
- PCRE 函数 preg_replace_callback_array Perform a regular expression search and replace using callbacks
-
发表日期:2021-07-01 08:56:56 | 来源: | 分类:PCRE 函数
-
示例1
<?php $subject = 'Aaaaaa Bbb'; preg_replace_callback_array( [ '~[a]+~i' => function ($match) { echo strlen($match[0]), ' matches for "a" found', PHP_EOL; } , '~[b]+~i' => function ($match) { echo strlen($match[0]), ' matches for "b" found', PHP_EOL; } ], $subject); ?>
- PCRE 函数 preg_replace_callback 执行一个正则表达式搜索并且使用一个回调进行替换
-
发表日期:2021-07-01 08:56:56 | 来源: | 分类:PCRE 函数
-
示例1
<?php /* 一个unix样式的命令行过滤器,用于将段落开始部分的大写字母转换为小写。 */ $fp = fopen("php://stdin", "r") or die("can't read stdin"); while (!feof($fp)) { $line = fgets($fp); $line = preg_replace_callback( '|<p>\s*\w|', function ($matches) { return strtolower($matches[0]); } , $line ); echo $line; } fclose($fp); ?>
示例2
<?php // 将文本中的年份增加一年.$text = "April fools day is 04/01/2002\n"; $text.= "Last christmas was 12/24/2001\n"; // 回调函数function next_year($matches){ // 通常: $matches[0]是完成的匹配 // $matches[1]是第一个捕获子组的匹配 // 以此类推 return $matches[1].($matches[2]+1); } echo preg_replace_callback( "|(\d{ 2} /\d{ 2} /)(\d{ 4} )|", "next_year", $text); ?>
示例3
<?php $input = "plain [indent] deep [indent] deeper [/indent] deep [/indent] plain"; function parseTagsRecursive($input){ /* 译注: 对此正则表达式分段分析 * 首尾两个#是正则分隔符 * \[indent] 匹配一个原文的[indent] * ((?:[^[]|\[(?!/?indent])|(?R))+)分析: * (?:[^[]|\[(?!/?indent])分析: * 首先它是一个非捕获子组 * 两个可选路径, 一个是非[字符, 另一个是[字符但后面紧跟着不是/indent或indent. * (?R) 正则表达式递归 * \[/indent] 匹配结束的[/indent] * / $regex = '#\[indent]((?:[^[]|\[(?!/?indent])|(?R))+)\[/indent]#'; if (is_array($input)) { $input = '<div style="margin-left: 10px">'.$input[1].'</div>'; } return preg_replace_callback($regex, 'parseTagsRecursive', $input); } $output = parseTagsRecursive($input); echo $output; ?>
- PCRE 函数 preg_split 通过一个正则表达式分隔字符串
-
发表日期:2021-07-01 08:56:56 | 来源: | 分类:PCRE 函数
-
示例1
<?php //使用逗号或空格(包含" ", \r, \t, \n, \f)分隔短语$keywords = preg_split("/[\s,]+/", "hypertext language, programming"); print_r($keywords); ?>
示例2
<?php $str = 'string'; $chars = preg_split('//', $str, -1, PREG_SPLIT_NO_EMPTY); print_r($chars); ?>
示例3
<?php $str = 'hypertext language programming'; $chars = preg_split('/ /', $str, -1, PREG_SPLIT_OFFSET_CAPTURE); print_r($chars); ?>
- PCRE 函数 preg_filter 执行一个正则表达式搜索和替换
-
发表日期:2021-07-01 08:56:55 | 来源: | 分类:PCRE 函数
-
示例1
<?php $subject = array('1', 'a', '2', 'b', '3', 'A', 'B', '4'); $pattern = array('/\d/', '/[a-z]/', '/[1a]/'); $replace = array('A:$0', 'B:$0', 'C:$0'); echo "preg_filter returns\n"; print_r(preg_filter($pattern, $replace, $subject)); echo "preg_replace returns\n"; print_r(preg_replace($pattern, $replace, $subject)); ?>
- PCRE 函数 preg_match 执行匹配正则表达式
-
发表日期:2021-07-01 08:56:55 | 来源: | 分类:PCRE 函数
-
示例1
<?php preg_match('/(foo)(bar)(baz)/', 'foobarbaz', $matches, PREG_OFFSET_CAPTURE); print_r($matches); ?>
示例2
<?php preg_match('/(a)(b)*(c)/', 'ac', $matches); var_dump($matches); preg_match('/(a)(b)*(c)/', 'ac', $matches, PREG_UNMATCHED_AS_NULL); var_dump($matches); ?>
示例3
<?php $subject = "abcdef"; $pattern = '/^def/'; preg_match($pattern, $subject, $matches, PREG_OFFSET_CAPTURE, 3); print_r($matches); ?>
示例4
<?php $subject = "abcdef"; $pattern = '/^def/'; preg_match($pattern, substr($subject,3), $matches, PREG_OFFSET_CAPTURE); print_r($matches); ?>
示例5
<?php //模式分隔符后的"i"标记这是一个大小写不敏感的搜索if (preg_match("/php/i", "PHP is the web scripting language of choice.")) { echo "A match was found."; } else { echo "A match was not found."; } ?>
示例6
<?php /* 模式中的\b标记一个单词边界,所以只有独立的单词"web"会被匹配,而不会匹配 * 单词的部分内容比如"webbing" 或 "cobweb" */ if (preg_match("/\bweb\b/i", "PHP is the web scripting language of choice.")) { echo "A match was found."; } else { echo "A match was not found."; } if (preg_match("/\bweb\b/i", "PHP is the website scripting language of choice.")) { echo "A match was found."; } else { echo "A match was not found."; } ?>
示例7
<?php //从URL中获取主机名称preg_match('@^(?:http://)?([^/]+)@i', "http://www.php.net/index.html", $matches); $host = $matches[1]; //获取主机名称的后面两部分preg_match('/[^.]+\.[^.]+$/', $host, $matches); echo "domain name is: { $matches[0]} \n"; ?>
示例8
<?php $str = 'foobar: 2008'; preg_match('/(?P<name>\w+): (?P<digit>\d+)/', $str, $matches); /* 可选的方式 */ // preg_match('/(?<name>\w+): (?<digit>\d+)/', $str, $matches); print_r($matches); ?>
- PCRE 函数 preg_last_error 返回最后一个PCRE正则执行产生的错误代码
-
发表日期:2021-07-01 08:56:55 | 来源: | 分类:PCRE 函数
-
示例1
<?php preg_match('/(?:\D+|<\d+>)*[!?]/', 'foobar foobar foobar'); if (preg_last_error() == PREG_BACKTRACK_LIMIT_ERROR) { print 'Backtrack limit was exhausted!'; } ?>
- PCRE 函数 preg_quote 转义正则表达式字符
-
发表日期:2021-07-01 08:56:55 | 来源: | 分类:PCRE 函数
-
示例1
<?php $keywords = '$40 for a g3/400'; $keywords = preg_quote($keywords, '/'); echo $keywords; // 返回 \$40 for a g3\/400?>
示例2
<?php //在这个例子中,preg_quote($word) 用于保持星号原文涵义,使其不使用正则表达式中的特殊语义。$textbody = "This book is *very* difficult to find."; $word = "*very*"; $textbody = preg_replace ("/" . preg_quote($word, '/') . "/", "<i>" . $word . "</i>", $textbody); ?>
- Session 函数 session_start 启动新会话或者重用现有会话
-
发表日期:2021-07-01 08:56:52 | 来源: | 分类:Session 函数
-
示例1
<?php // page1.phpsession_start(); echo 'Welcome to page #1'; $_SESSION['favcolor'] = 'green'; $_SESSION['animal'] = 'cat'; $_SESSION['time'] = time(); // 如果使用 cookie 方式传送会话 IDecho '<br /><a href="page2.php">page 2</a>'; // 如果不是使用 cookie 方式传送会话 ID,则使用 URL 改写的方式传送会话 IDecho '<br /><a href="page2.php?' . SID . '">page 2</a>'; ?>
示例2
<?php // page2.phpsession_start(); echo 'Welcome to page #2<br />'; echo $_SESSION['favcolor']; // greenecho $_SESSION['animal']; // catecho date('Y m d H:i:s', $_SESSION['time']); // 类似 page1.php 中的代码,你可能需要在这里处理使用 SID 的场景echo '<br /><a href="page1.php">page 1</a>'; ?>
示例3
<?php // 设置 cookie 的有效时间为 1 天session_start([ 'cookie_lifetime' => 86400,]); ?>
示例4
<?php // 如果确定不修改会话中的数据,// 我们可以在会话文件读取完毕之后立即关闭它// 来避免由于给会话文件加锁导致其他页面阻塞session_start([ 'cookie_lifetime' => 86400, 'read_and_close' => true,]);
- Session 函数 session_write_close Write session data and end session
-
发表日期:2021-07-01 08:56:52 | 来源: | 分类:Session 函数
-
session_write_close
(PHP 4 >= 4.0.4, PHP 5, PHP 7, PHP 8)
session_write_close — Write session data and end session
说明
session_write_close(): boolEnd the current session and store session data.
Session data is usually stored after your script terminated without the need to call session_write_close(), but as session data is locked to prevent concurrent writes only one script may operate on a session at any time. When using framesets together with sessions you will experience the frames loading one by one due to this locking. You can reduce the time needed to load all the frames by ending the session as soon as all changes to session variables are done.
参数
此函数没有参数。
返回值
成功时返回
true
, 或者在失败时返回false
。更新日志
版本 说明 7.2.0 The return type of this function is bool now. Formerly, it has been void.
- 前端开发(1)
- 数据库(0)
- PHP(0)
- PHP杂项(34)
- PHP基础-李炎恢系列课程(20)
- 中文函数手册(0)
- 错误处理 函数(13)
- OPcache 函数(6)
- PHP 选项/信息 函数(54)
- Zip 函数(10)
- Hash 函数(15)
- OpenSSL 函数(63)
- Date/Time 函数(51)
- 目录函数(9)
- Fileinfo 函数(6)
- iconv 函数(11)
- 文件系统函数(81)
- 多字节字符串 函数(57)
- GD 和图像处理 函数(114)
- 可交换图像信息(5)
- Math 函数(50)
- 程序执行函数(11)
- PCNTL 函数(23)
- JSON 函数(4)
- SPL 函数(15)
- URL 函数(10)
- cURL 函数(32)
- 网络 函数(33)
- FTP 函数(36)
- Session 函数(23)
- PCRE 函数(11)
- PCRE 正则语法(19)
- 数组 函数(81)
- 类/对象 函数(18)
- 函数处理 函数(13)
- 变量处理 函数(37)
- SimpleXML 函数(3)
- 杂项 函数(31)
- 字符串 函数(101)
- JAVA(0)
- Android(0)
- Linux(0)
- 其他(0)