C#: finding instances of a string within a string

2019-03-04 10:11发布

问题:

Suppose I had the string "1 AND 2 AND 3 OR 4", and want to create an array of strings that contains all substrings "AND" or "OR", in order, found within the string.

So the above string would return a string array of {"AND", "AND", "OR"}.

What would be a smart way of writing that?

EDIT: Using C# 2.0+,

string rule = "1 AND 2 AND 3 OR 4";
string pattern = "(AND|OR)";
string[] conditions = Regex.Split(rule, pattern);

gives me {"1", "AND", "2", "AND", "3", "OR", "4"}, which isn't quite what I'm after. How can I reduce that to the ANDs and ORs only?

回答1:

This regex (.NET) seems to do what you want. You're looking for the matches (multiple) in the group at index=1:

.*?((AND)|(OR))*.*?

EDIT I've tested the following and it seems to do what you want. It's more lines than i would like but it approaches the task in a purely regex fashion (which IMHO is what you should be doing):

        string text = "1 AND 2 AND 3 OR 4";
        string pattern = @"AND|OR";

        Regex r = new Regex(pattern, RegexOptions.IgnoreCase);

        Match m = r.Match(text);
        ArrayList results = new ArrayList();
        while (m.Success)
        {
            results.Add(m.Groups[0].Value);

            m = m.NextMatch();
        }

        string[] matchesStringArray = (string[])results.ToArray(typeof(string));


回答2:

Your probably looking for a tokeniser or Lexer, have a look at the following article:

C# Regular Expression Recipes—A Better Tokenizer



回答3:

Since you know the exact substring you're looking for... why not just use IndexOf(substr, iOffset) to know the number of occurances (loop till it returns -1) ??

Depending on the complexity of your task, it could be simpler/faster than using regular expressions (since you're not matching patterns).



回答4:

string rule = "1 AND 2 AND 3 OR 4";
string pattern = "(AND|OR)";
MatchCollection conditions = Regex.Matches(rule, pattern);

Use Match.Value to get the string.



回答5:

Here's a goofy way that I came up with:

string rule = "1 AND 2 AND 3 OR 4";
List<string> andsOrs = new List<string>();
string[] split = rule.Split();
for (int i = 0; i < split.Length; i++)
{
   if (split[i] == "AND" || split[i] == "OR")
   {
       andsOrs.Add(split[i]);
   }
}
string[] conditions = andsOrs.ToArray();
return conditions;