Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Regex to parse function and parameters

I have the following string:

function(param1, param2, param3, param4, ..., paramN)

I need a Regex code to parse it as an array of strings:

function
param1
param2
param3
param4
.
.
.
paramN

I've tried several examples in the net but none of them seems to work for me.

[EDIT]

Not woking with the suggestion. Check the above code:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Text.RegularExpressions;

namespace TestRegex
{
    class Program
    {
        static void Main(string[] args)
        {
            string Expression = String.Empty;

            while (Expression.Trim() != "EXIT")
            {
                Expression = Console.ReadLine();

                ///
                /// Get function name
                /// 
                var funcTags = Regex.Matches(Expression, @"b[^()]+\((.*)\)$");

                Console.WriteLine("Matches: " + funcTags.Count);
                foreach (var item in funcTags)
                    Console.WriteLine("FuncTag: " + item);

                ///
                /// Get parameters
                /// 
                var paramTags = Regex.Matches(Expression, @"\b[^()]+\((.*)\)$");

                Console.WriteLine("Matches: " + paramTags.Count);
                foreach (var item in paramTags)
                    Console.WriteLine("ParamTag: " + item);
            }
        }
    }
}

Output:

function("a", "b", "c");
Matches: 0
Matches: 0

Something is wrong here... Appreciate help.

like image 778
Mendes Avatar asked Jan 06 '14 23:01

Mendes


1 Answers

Depending on how complex your functions can get, this can actually be quite tricky. See my similar answer over here. The gist is to break up the regex into two problems. First get the function name, then the parameters.

In summary, this will extract the function name:

\b[^()]+\((.*)\)$

For parameters, this handles parameters as well as functions in the parameters:

([^,]+\(.+?\))|([^,]+)

This will handle nested functions:

(?:[^,()]+((?:\((?>[^()]+|\((?<open>)|\)(?<-open>))*(?(open)(?!))\)))*)+

But, if you need to support full C# syntax, this gets tricky fast, e.g. comments in the parameters, etc. See here for a discussion.

Update based on comments

Apologies, some errors in copying that I missed (now corrected). You were missing the first \ in the function regex. You were also using the same pattern for extracting the parameters, whereas you need the second regex as described above. Also, since there is only one function per line, you can just do the single match. This code will work:

    static void Main( string[] args )
    {
        string Expression = "function(param1, param2)";            
        ///
        /// Get function name
        /// 
        var func = Regex.Match( Expression, @"\b[^()]+\((.*)\)$" );

        Console.WriteLine( "FuncTag: " + func.Value );
        string innerArgs = func.Groups[1].Value;
        ///
        /// Get parameters
        /// 
        var paramTags = Regex.Matches( innerArgs, @"([^,]+\(.+?\))|([^,]+)" );

        Console.WriteLine( "Matches: " + paramTags.Count );
        foreach( var item in paramTags )
            Console.WriteLine( "ParamTag: " + item );

    }

Output:

FuncTag: function(param1, param2)
Matches: 2
ParamTag: param1
ParamTag:  param2
like image 70
acarlon Avatar answered Sep 30 '22 16:09

acarlon