【发布时间】:2017-11-14 00:36:32
【问题描述】:
我想在 PHP 中实现我非常基本的日历功能。但客户希望能够从其他来源导入他自己的日历。我有一个通用的 ics 文件。 我发现有时大行,例如 Long Descriptions 或一些苹果 iCal 行会分解为以空格作为第一个字符的新行。
我想通过 preg_match_all 使用正则表达式获取每个属性。
这是一个示例,其中包含来自 google 和 apple 属性的示例行以及我从客户那里得到的类似描述。
BEGIN:VEVENT
DTSTART:20150123T060000Z
DTEND:20150123T070000Z
DTSTAMP:20171027T205827Z
UID:1234567894567890ß6543
CREATED:20150131T171526Z
ORGANIZER;CN=someemail@mail.com:mailto:email@server.com
UID:1234567890
ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;CN=So
me NameX-NUM-GUESTS=0:mailto:name@server.com
ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=ACCEPTED;CN=Anoth
er Name;X-NUM-GUESTS=0:mailto:name@server.com
DESCRIPTION: this is a very long d\nescription. It brea
ks down if the l\nine is too long. It seems to be quit
e normal. But it \n also contains \n's.
X-APPLE-STRUCTURED-LOCATION;VALUE=URI;X-APPLE-MAPKIT-HANDLE=CAESmQIaEgnfNH1
2wAtJQBFuMT83NE0hQCKcAQoLRGV1dHNjaGxhbmQSAkRFGgZIZXNzZW4qEUZyYW5rZnVydCBhbS
BNYWluMhFGcmFua2Z1cnQgYW0gTWFpbjoFNjA1MjhCBFPDvGRSGUhlaW5yaWNoLUhvZmZtYW5uL
VN0cmHDn2VaAjEwYhxIZWlucmljaC1Ib2ZmbWFubi1TdHJhw59lIDEwigEJTmllZGVycmFkigEE
U8O8ZCocSGVpbnJpY2gtSG9mZm1hbm4tU3RyYcOfZSAxMDIcSGVpbnJpY2gtSG9mZm1hbm4tU3R
yYcOfZSAxMDIXNjA1MjggRnJhbmtmdXJ0IGFtIE1haW4yC0RldXRzY2hsYW5kODlAAA==;X-APP
LE-RADIUS=49.91306619367188;X-APPLE-REFERENCEFRAME=1;X-TITLE="A location , Frankfurt am Main, Germany":geo:12.345678,9.123456
LAST-MODIFIED:20150131T171526Z
LOCATION:
SEQUENCE:0
STATUS:CONFIRMED
SUMMARY: The Title
TRANSP:OPAQUE
END:VEVENT
我得到的正则表达式似乎适用于不在下一行继续的行:
/(((.*?:)(.*?)).*)/
为
BEGIN:VEVENT
DTSTART:20150123T060000Z
DTEND:20150123T070000Z
DTSTAMP:20171027T205827Z
UID:1234567894567890ß6543
CREATED:20150131T171526Z
UID:1234567890
DESCRIPTION: some description
LAST-MODIFIED:20150131T171526Z
LOCATION:
SEQUENCE:0
STATUS:CONFIRMED
SUMMARY: The Title
TRANSP:OPAQUE
END:VEVENT
给出这个:
array(5
0 => array(15
0 => BEGIN:VEVENT
1 => DTSTART:20150123T060000Z
2 => DTEND:20150123T070000Z
3 => DTSTAMP:20171027T205827Z
4 => UID:1234567894567890ß6543
5 => CREATED:20150131T171526Z
6 => UID:1234567890
7 => DESCRIPTION: some description
8 => LAST-MODIFIED:20150131T171526Z
9 => LOCATION:
10 => SEQUENCE:0
11 => STATUS:CONFIRMED
12 => SUMMARY: The Title
13 => TRANSP:OPAQUE
14 => END:VEVENT
)
http://www.phpliveregex.com/p/lXX (preg_match_all)
我当然可以使用它,但我不知道如何检测可以有任意数量的换行符的属性中的换行符。 http://www.phpliveregex.com/p/lXY (preg_match_all)
就像,对于我提供的确切示例,以下正则表达式似乎有效:
(DESCRIPTION:(.*))|(X-APPLE(.*?)geo:(.*))|(((.*?:)(.*?)).*)|((.*)\n(.*):mailto:.*)|((.*):mailto:.*)
http://www.phpliveregex.com/p/lXW (preg_match_all)
但我无法涵盖任何单个案例,因为运行时可能会爆炸。
已解决
我没有从正确的角度看待这一点。 我只需要 preg_replace 换行即可:
preg_replace("/\n /", "", $input_lines);
在 \n 之后有一个空格很重要。 之后,我可以继续正确地获取任何线路。
【问题讨论】:
-
你必须使用 preg_match_all 吗?为什么不用preg_replace,匹配
\n并替换为空白phpliveregex.com/p/lY0 -
仅供参考:这称为“线折叠”。可能会帮助您找到解决方案。
-
啊,没想到。删除线折叠实际上是一个好主意,并且可以按我的意愿工作。我希望我能支持你的 cmets。谢谢。也许其他人会偶然发现这个问题,所以我会更新它。