PowerShell 7.x中用正则从长字符串拆分邮件头的问题
拆分邮件头分段的正则表达式方案
需求场景
处理包含邮件头的长字符串,提取每个以单词字符(\w)开头的行,以及该行后续所有以空格开头的行(直到下一个以单词字符开头的行之前)。
可行正则表达式
基础匹配版本
(?m)^(\w.*(?:\n\s+.*)*)
兼容制表符的严谨版本
如果邮件头续行可能用制表符而非空格,可使用以下正则:
(?m)^(\w.*(?:\n[^\S\n]+.*)*)
PowerShell 7.x 实操示例
假设邮件头字符串存储在$emailHeader变量中,用[regex]::Matches()提取所有匹配段:
$emailHeader = @" X-MS-Exchange-Organization-InternalOrgSender: False Received: from YQBPR0101CA0152.CANPRD01.PROD.OUTLOOK.COM (2603:10b6:c01:e::25) by YQBPR0101MB5927.CANPRD01.PROD.OUTLOOK.COM (2603:10b6:c01:36::19) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.6652.27; Tue, 8 Aug 2023 03:59:56 +0000 Received: from YQBCAN01FT026.eop-CAN01.prod.protection.outlook.com (2603:10b6:c01:e:cafe::70) by YQBPR0101CA0152.outlook.office365.com (2603:10b6:c01:e::25) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.6652.27 via Frontend Transport; Tue, 8 Aug 2023 03:59:56 +0000 "@ $matches = [regex]::Matches($emailHeader, '(?m)^(\w.*(?:\n\s+.*)*)') $matches.Value
正则规则解释
(?m):启用多行模式,让^匹配每行的开头位置^(\w.*:匹配行首的单词字符,以及该行剩余的全部内容(?:\n\s+.*)*:非捕获组,匹配零次或多次的“换行符+空格开头+该行剩余内容”,确保完整捕获所有续行;用非捕获组是为了避免生成多余的分组结果
原失败正则的问题分析
- 第一个正则
'(?sm)(^\w.*(\n\s+.*)+)':- 启用了单行模式
(?s),导致.会匹配换行符,整个字符串被当作单行处理,匹配范围直接覆盖到字符串末尾,无法分段
- 启用了单行模式
- 第二个正则
'(?m)(^\w.*(?=(\n\s+.*)*))':- 正向预查
(?=...)是零宽断言,仅做位置判断,不会实际捕获后续的续行内容,最终只匹配到开头的单行
- 正向预查
内容的提问来源于stack exchange,提问作者94jeepyj
相关产品推荐
相关产品推荐

