Re(2): Re: Rationalizing the denominator (better solution!)
- To: mathgroup at smc.vnet.net
- Subject: [mg18809] Re(2): [mg18697] Re: [mg18633] Rationalizing the denominator (better solution!)
- From: Andrzej Kozlowski <andrzej at tuins.ac.jp>
- Date: Thu, 22 Jul 1999 08:19:27 -0400
- Sender: owner-wri-mathgroup at wolfram.com
This is still somwhat imperfect. For example:
In[2]:=
RationalizeDenominator[4/(3*(Sqrt[2] - 5^(1/4)))]
Out[2]=
2 4 6
Root[65536 - 294912 #1 + 290304 #1 - 1772928 #1 +
8
6561 #1 & , 1]
In[7]:=
ToRadicals[%]
Out[7]=
608 272 Sqrt[5] 1 327680 1318912 Sqrt[5]
-Sqrt[--- + ----------- + - Sqrt[------ + ---------------]]
9 9 2 9 81
which is not quite what one would like to get. One can do a little better
by modifying the complexity function to penalize the presence of Root:
In[3]:=
RationalizeDenominator1[expr_] :=
FullSimplify[expr, ComplexityFunction ->
(
Count[#, _?
(MatchQ[Denominator[#], Power[_, _Rational] _. + _.] &),
{0, Infinity}
] + If[FreeQ[#, Root], 0, 1] &
)
]
In[4]:=
RationalizeDenominator1[4/(3*(Sqrt[2] - 5^(1/4)))]
Out[4]=
4
-(-) Sqrt[38 + 17 Sqrt[5] + 2 Sqrt[2 (360 + 161 Sqrt[5])]]
3
All these functions will fail however if roots of order higher than 4 are
involved:
In[5]:=
RationalizeDenominator1[f = (2 + 5^(1/6))/(1 - 5^(1/6))]
Out[5]=
1
-1 + --------
1/6
1 5
- - ----
3 3
In such cases one needs to use some mathematics. First we load in the package
In[6]:=
<< Algebra`PolynomialExtendedGCD`
we set
In[7]:=
p = Denominator[f] /. {5^(1/6) -> t}
Out[7]=
1 - t
In[8]:=
q = RootReduce[5^(1/6)][[1]][t]
Out[8]=
6
-5 + t
The answer then is given by:
In[9]:=
Numerator[f]*PolynomialExtendedGCD[p, q][[2, 1]] /. t -> 5^(1/6) // Expand
Out[9]=
1/6 1/3 2/3 5/6
7 3 5 3 5 3 Sqrt[5] 3 5 3 5
-(-) - ------ - ------ - --------- - ------ - ------
4 4 4 4 4 4
We can try to see if Mathematica can verify this by itself. Not
surprisingly it is forced to use numerical methods:
In[12]:=
FullSimplify[
f == -(7/4) - (3*5^(1/6))/4 - (3*5^(1/3))/4 - (3*Sqrt[5])/4 - (3*5^(2/3))/
4 - (3*5^(5/6))/4]
\!\($MaxExtraPrecision::"meprec" \(\(:\)\(\ \)\)
"In increasing internal precision while attempting to evaluate
\!\(7\/4 + \
\(3\\ 5\^\(1/6\)\)\/4 + \(3\\ 5\^\(1/3\)\)\/4 + \(3 \(\(\[LeftSkeleton] 1 \
\[RightSkeleton]\)\) \(\(\[LeftSkeleton] 1 \[RightSkeleton]\)\)\)\/4 + \(3\\ \
5\^\(\[LeftSkeleton] 1 \[RightSkeleton]\)\)\/4 + \(3\\ 5\^\(5/6\)\)\/4 + \(2 \
+ 5\^\(1/6\)\)\/\(1 - 5\^\(1/6\)\)\), the limit $MaxExtraPrecision = \!\(50.`\
\) was reached. Increasing the value of $MaxExtraPrecision may help resolve \
the uncertainty."\)
Out[12]=
True
On Mon, Jul 19, 1999, Ersek, Ted R <ErsekTR at navair.navy.mil> wrote:
>Andrzej Kozlowski wrote:
>----------------------------
>
>A short time after sending my reply to this message I noticed that a far
>better way to rationalize the denominator of most expressions is already
>almost built in into Mathematica! What one has to do is to make use of the
>ComplexityFunction option in FullSimplify, which enables you to decide which
>of two altrnative forms of an expression Mathematica considers to be
>simpler. First we defince a complexity function which makes expressions with
>radicals in the denominator more complex than those without:
>
>In[1]:=
>rat[p_] := If[FreeQ[Denominator[p], Power[_, Rational[_, _]]], 0, 1]
>
>
>Now we can use FullSimplify with ComplexityFunction set to rat. We can now
>rationalize denominators in expressions which we could not deal with before:
>
><snip>
>
>In[3]:=
>FullSimplify[1/(5 - 2*Sqrt[3]), ComplexityFunction -> rat]
>Out[3]=
>1
>-- (5 + 2 Sqrt[3])
>13
>
>----------------------------
>
>The solution from Andrzej Kozlowski doesn't rationalize denominators deep
>down inside an expression. I wrote RationalizeDenominator below which does.
>
>
>In[1]:=
>RationalizeDenominator[expr_]:=
> FullSimplify[expr,ComplexityFunction->
> (
> Count[#,_?
> (MatchQ[Denominator[#],Power[_,_Rational] _.+_.]&),
> {0,Infinity}
> ]&
> )
> ]/.x_Root?
> (LeafCount[ToRadicals[#]]<=LeafCount[#]&):>ToRadicals[x]
>
>
>---------------------
>
>In[2]:=
>tst=2*(E^(Sqrt[2] +Sqrt[3])^(-1) + x)^2;
>
>
>In[3]:=
>RationalizeDenominator[tst]
>Out[3]=
>2*(E^Sqrt[5 - 2*Sqrt[6]] + x)^2
>
>
>In the example above a denominator deep inside the expression is
>rationalized.
>This version also converts Root objects to radicals when it makes sense to
>do so.
>
>----------------------------------
>Of course my function doesn't rationalize the denominator in the following
>example. To do that the expression returned would need the head (HoldForm).
>
>
>In[4]:=
>RationalizeDenominator[1/Sqrt[8]]
>
>Out[4]=
>1/(2*Sqrt[2])
>
>----------------------------------
>
>I think WRI could make a built-in function that would do this much faster,
>and I hope they give us one in a future release.
>
>
>Regards,
>Ted Ersek
>
Andrzej Kozlowski
Toyama International University
JAPAN
http://sigma.tuins.ac.jp/
http://eri2.tuins.ac.jp/