我想用JS来转换嵌套的指数LaTeX表达式,例如
2^{3^{4^5}}
到PHP' pow()
语法
pow(2,pow(3,pow(4,5)))
我知道JS不支持递归RegExp。表达式是等式的一部分,所以我希望解决方案能够像
那样工作\frac{3}{9}+\frac{2^{\sqrt{4^2}}}{6}
应该输出
\frac{3}{9}+\frac{pow(2,\sqrt{pow(4,2)})}{6}
像@ AbcAeffchen的解决方案一样。
我不需要转换非指数部分。
注意:解决方案不得要求使用PHP 5.6,它引入了**
运算符
答案 0 :(得分:4)
一个丑陋的黑客,
> foo
'2,(3^(4^5))'
> var foo = "2^(3^(4^5))".replace(/\^/g, ",");
undefined
> foo
'2,(3,(4,5))'
> var bar = foo.replace(/(\d,)(?=[^\d])/g, "$1pow");
undefined
> var foobar = bar.replace(/^(.*)$/, "pow($1)")
undefined
> foobar
'pow(2,pow(3,pow(4,5)))'
答案 1 :(得分:2)
尝试我写的这个功能。它只使用普通的字符串函数,所以它稍长一点 基本上它的工作原理如下
^
^
之前的部分^
之后的部分所以它在JavaScript中看起来:
function convertLatexPow(str)
{
// contains no pow
var posOfPow = str.indexOf('^');
if(posOfPow == -1)
return str;
var head = str.substr(0,posOfPow);
var tail = str.substr(posOfPow+1);
// find the beginning of pow
var headLen = posOfPow;
var beginning = 0;
var counter;
if(head[headLen-1] == '}') // find the opening brace
{
counter = 1;
for(i = headLen-2; i >= 0; i--)
{
if(head[i] == '}')
counter++;
else if(head[i] == '{')
counter--;
if(counter == 0)
{
beginning = i;
break;
}
}
}
else if(head[headLen-1].match('[0-9]{1}')) // find the beginning of the number
{
for(i = headLen-2; i >= 0; i--)
{
if(!head[i].match('[0-9]{1}'))
{
beginning = i+1;
break;
}
}
}
else // the string looks like ...abc^{..}.. so the basis is only one character ('c' in this case)
beginning = headLen-1;
var untouchedHead = head.substr(0,beginning);
var firstArg = head.substr(beginning);
// find the end of pow
var secondArg, untouchedTail;
if(tail[0] != '{')
{
secondArg = tail[0];
untouchedTail = tail.substr(1);
}
else
{
counter = 1;
var len = tail.length;
var end = len+1;
for(i = 1; i < len; i++)
{
if(tail[i] == '{')
counter++;
else if(tail[i] == '}')
counter--;
if(counter == 0)
{
end = i;
break;
}
}
secondArg = tail.substr(1,end-1);
if(end < len-1)
untouchedTail = tail.substr(end+1);
else
untouchedTail = '';
}
return untouchedHead
+ 'pow(' + firstArg + ',' + convertLatexPow(secondArg) + ')'
+ convertLatexPow(untouchedTail);
}
alert(convertLatexPow('2^{3^{4^5}}'));
alert(convertLatexPow('\\frac{3}{9}+\\frac{2^{\\sqrt{4^2}}}{6}'));
alert(convertLatexPow('{a + 2 \\cdot (b + c)}^2'));
&#13;
输入:'2^{3^{4^5}}'
输出:pow(2,pow(3,pow(4,5)))
输入:'\\frac{3}{9}+\\frac{2^{\\sqrt{4^2}}}{6}'
输出:\frac{3}{9}+\frac{pow(2,\sqrt{pow(4,2)})}{6}
输入:'{a + 2 \\cdot (b + c)}^2'
输出:pow({a + 2 \cdot (b + c)},2)
注意:它不解析\sqrt
。你必须多做这件事。
随意改进它:)
注意:LaTeX中的^
并不意味着 power 。它只是意味着上标。所以2^3
变为2 3 (看起来像&#34; 2到3&#34的力量;),但\sum_{i=1}^n
只是变得更好格式化。但您可以在^
之后直接扩展上述函数以忽略}
。
注意:正如Lucas Trzesniewski在评论中提到的,2^3^4
未被转换&#34;正确&#34;,但它也不是有效的LaTeX表达式。
修改:改进了将'{a + 2 \\cdot (b + c)}^2'
转换为正确的功能。
注意:在LaTeX中存在多种编写大括号的方法(例如(
,\left(
,[
,\lbrace
,..) 。
为了确保此功能适用于所有这些大括号,您应该首先将所有大括号转换为{
和}
。或者使用普通大括号(
,但必须编辑该函数以查找(
而不是{
。
注意:此函数的复杂性为O(n⋅k)
,其中n
是输入的长度,k
是^
的数量在输入中。最坏的情况输入将是第一个测试用例2^{3^{4^{...}}}
。但在大多数情况下,功能会快得多。关于O(n)
的事情。
答案 2 :(得分:0)
您可以迭代地执行此操作:
var foo = "2^(3^(4^5))";
while (/\([^^]+\^[^^]+\)/.test(foo)) {
foo = foo.replace(/\(([^^]+)\^([^^]+)\)/, "pow($1,$2)");
}
if (/(.+)\^(.+)/.test(foo)) {
foo = "pow(" + RegExp.$1 + "," + RegExp.$2 + ")";
}
# foo == "pow(2,pow(3,pow(4,5)))"