如何使用正则表达式按前缀字符进行分割?

5

我想要将下面的字符串:

~Peter~Lois~Chris~Meg~Stewie

按照字符~进行分割,并得到以下结果:

Peter
Lois
Chris
Meg
Stewie

使用Javascript或C#中的标准字符串分割函数,第一个结果肯定是空字符串。我想避免忽略第一个结果,因为第一个结果实际上可能是空字符串。

我一直在试验使用正则表达式,但是却无法解决问题。我相信有人已经找到了优雅的解决方案。


嗯,你到底想要什么呢?你似乎不想抛弃第一个元素,但又希望它可以是一个空字符串...能否重新表达一下这部分内容? - Rob
同意,你说你想允许第一个元素为空字符串,那么这将与你想要结果以非空字符串开头的情况有何不同? - Adam Bellaire
3个回答

4

针对您的需求,我看到有两个选项:

(1) 如果存在前缀字符,则删除该字符。

(2) 使用完整的正则表达式来分离字符串。

这两种方法都在以下代码中进行了说明:

using System;
using System.Linq;
using System.Text.RegularExpressions;

class APP { static void Main() {

string s = "~Peter~Lois~Chris~Meg~Stewie";

// #1 - Trim+Split
Console.WriteLine ("[#1 - Trim+Split]");
string[] result = s.TrimStart('~').Split('~');
foreach (string t in result) { Console.WriteLine("'"+t+"'"); }

// #2 - Regex
Console.WriteLine ("[#2 - Regex]");
Regex RE = new Regex("~([^~]*)");
MatchCollection theMatches = RE.Matches(s);
foreach (Match match in theMatches) { Console.WriteLine("'"+match.Groups[1].Value+"'"); }

// #3 - Regex with LINQ [ modified from @ccook's code ]
Console.WriteLine ("[#3 - Regex with LINQ]");
Regex.Matches(s, "~([^~]*)")
    .OfType<Match>()
    .ToList()
    .ForEach(m => Console.WriteLine("'"+m.Groups[1].Value+"'"))
    ;
}}

在#2中的正则表达式匹配分隔符后跟一个包含零个或多个非分隔符字符的匹配组。结果匹配是被分隔的字符串(包括任何空字符串)。对于每个匹配,"match.Value"是整个字符串,包括前导分隔符,"match.Groups1.Value"是第一个不包含分隔符的字符串的匹配组。
为了完整起见,第三种编码(#3)也包括了相同的正则表达式方法,但采用了LINQ编码风格。
如果你在使用正则表达式方面有困难,我强烈推荐Jeffrey E. F. Friedl所著的《精通正则表达式第三版》。它是迄今为止理解正则表达式的最佳辅助工具,并且以后可作为优秀的参考书或复习资料。

1
在C#中,这似乎可以得到你想要的:
"~Peter~Lois~Chris~Meg~Stewie".Split("~".ToCharArray(), StringSplitOptions.RemoveEmptyEntries);

如果你在波浪符号周围使用单引号''而不是双引号"",则不需要调用.ToCharArray()。 - Eric Schoonover
@spoon16:对于默认重载,那是正确的,但因为我正在使用接受枚举的重载,所以我必须传递一个实际的数组作为第一个字符。如果没有它,我会得到编译错误。 - Jay Bazuzi

1
这里是一个LINQ方法...
请注意,使用RegexOptions.ExplicitCapture选项将不包括匹配项。如果没有它,'~'也将被包括在内。
using System;
using System.Linq;
using System.Text.RegularExpressions;

namespace ConsoleApplication2
{
    class Program
    {
        static void Main(string[] args)
        {
            string s = "~Peter~Lois~Chris~Meg~Stewie";
            Regex.Split(s, "(~)", RegexOptions.ExplicitCapture)
                .Where(i=>!String.IsNullOrEmpty(i))
                .ToList().ForEach(i => Console.WriteLine(i));
            Console.ReadLine();
        }
    }
}

不幸的是,这会移除所有空字符串[类似于“.Split('~',StringSplitOptions.RemoveEmptyEntries)”答案],但是提问者希望保留内部空字符串。虽然这种方法很有启发性,但我已经发布了我的答案修改,包括类似的LINQ编码。 - rivy

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接