too long

Is it possible to write a regex which would take input like 'sqrt(2 * (2+2)) + sin(pi/6)' and transform it into '\sqrt{2 \cdot (2+2)} + \sin(\pi/6)'?

The problem is the 'sqrt' and parentheses in it. It is obvious I can't simply use something like this:

/sqrt\((.?)\)/ -> \\sqrt{$1}

because this code would create something like this '\sqrt{2 \cdot (2+2)) + \sin(\pi/6}'.

My solution: it simply go throw the string converted to char array and tests if a current substring starts with $latex, if it does second for-cycle go from this point in different direction and by parentheses decides where the function starts and ends. (startsWith function)

Code:

public static function formatFunction($function, $latex, $input) {
    $input = preg_replace("/" . $function . "\(/", $latex . "{", $input);
    $arr = str_split($input);

    $inGap = false;
    $gap = 0;

    for ($i = count($arr) - 1; $i >= 0; $i--) {
        if (startsWith(substr($input, $i), $latex)) {
            for ($x = $i; $x < count($arr); $x++) {
                if ($arr[$x] == "(" || $arr[$x] == "{") { $gap++; $inGap = true; } 
                else if ($arr[$x] == ")" || $arr[$x] == "}") {  $gap--; }

                if ($inGap && $gap == 0) {
                    $arr[$x] = "}";
                    $inGap = false;
                    break;
                }
            }
        }
        $gap = 0;
    }

    return implode($arr);
}

Use:

self::formatFunction("sqrt", "\\sqrt", 
"sqrt(25 + sqrt(16 - sqrt(49)) + (7 + 1)) + sin(pi/2)");

Output:

\sqrt{25+\sqrt{16-\sqrt{49}}+(7+1)}+\sin (\pi/2)

Note: sin and pi aren't formated by this code, it's only str_replace function...

In general, no regular expression can effectively handle nested parentheses. Sorry to be the bearer of bad news! The MathJAX parser library can interpret LaTeX equations and you could probably add a custom output routine to do what you want.

For TeX questions, you can also try http://tex.stackexchange.com .

Some time ago i soved a similar problem in such way. Maybe it will be helpful for you

$str = 'sqrt((2 * (2+2)) + sin(pi/(6+7)))';
$from = [];     // parentheses content
$to = [];       // patterns for replace #<number> 
$brackets = [['(', ')'], ['{', '}'], ['[', ']']]; // new parentheses for every level
$level = 0;
$count = 1;  // count or replace made
while($count) {
  $str = preg_replace_callback('(\(([^()]+)\))', 
           function ($m) use (&$to, &$from, $brackets, $level) {
             array_unshift($to, $brackets[$level][0] . $m[1] . $brackets[$level][1]);
             $i = '#' . (count($to)-1); // pattern for future replace. 
                                        // here it '#1', '#2'. 
                                        // Make it so they will be unique
             array_unshift($from, $i); 
             return $i; }, $str, -1, $count); 
  $level++;
  }

echo str_replace($from, $to, $str); // return content back
// sqrt[{2 * (2+2)} + sin{pi/(6+7)}]

I forgot all details, but it, seems, works