2
$\begingroup$

Is it possible to calculate $\log_{10} x$ without using $\log_{10}$? I'm interested because I'm working with a framework that has some simple functions, but log is not one of them.

The specific platform is capable of doing addition, subtraction, multiplication and division. I can write a formula of a finite, predefined length; e.g. while loops or for loops that continue indefinitely are not available. It's a black-box project with an interface capable of creating formulas, so basically, I need to write the expression to calculate $\log_{10} x$ in one line, and I can't write my own method or something to do more dynamic calculations.

An approximation of $\log_{10} x$ is perfectly acceptable.

$\endgroup$
  • $\begingroup$ Could you flesh out your question to give the context, what functions you dispose of, what base the logarithm has, what $x$ is? $\endgroup$ – Raskolnikov Sep 7 '15 at 7:48
  • 1
    $\begingroup$ You could use a taylor series for the logarithm to get an approximation. In that case you would only need addition, multiplication and division. $\endgroup$ – Marc Sep 7 '15 at 7:50
  • $\begingroup$ It depends on the accuracy you need and of the space you have. A very rough solution could be to register some values of the logarithm and use recursion to fall back to one of them, by successive multiplications or divisions by $2$. $\endgroup$ – Tom-Tom Sep 7 '15 at 7:55
  • $\begingroup$ @Raskolnikov the base is 10. x is something I can calculate with addition/multiplication. $\endgroup$ – Adam Jensen Sep 7 '15 at 7:58
  • 1
    $\begingroup$ maybe use a Taylor series? $\endgroup$ – Mastrem Sep 7 '15 at 8:00
2
$\begingroup$

You can use a Taylor polynomial to first roughly compute $\ln n$. $$\ln n\approx0+\dfrac{1}{1!}(n-1)+\dfrac{(\frac{-1}{n^2})}{2!}(n-1)^2+\dfrac{(\frac{2}{n^3})}{3!}(n-1)^3+\dfrac{(\frac{-6}{n^4})}{4!}(n-1)^4+\dfrac{(\frac{24}{n^5})}{5!}(n-1)^5$$ Then use the fact that $\ln 10 \approx2.302585092994046$, so divide $\ln n$ by that to get $\log_{10} n$

$\endgroup$
  • $\begingroup$ Why does the dividend (over the factorial part of the series) go from using n to using x? $\endgroup$ – Adam Jensen Sep 8 '15 at 0:15
  • $\begingroup$ oops.. I'll correct my mistake $\endgroup$ – Mastrem Sep 8 '15 at 14:58
  • $\begingroup$ Thanks. I feel like this is the easiest to understand, and useful answer in my case, as I need to write a simple equation in the form $\log_{10} x = $... and not introduce new variables. $\endgroup$ – Adam Jensen Sep 9 '15 at 0:48
  • $\begingroup$ I think this taylor series only converges if $n \leq 2$. $\endgroup$ – flawr Dec 17 '16 at 18:15
  • $\begingroup$ @flawr, tho argument reduction ($\log(ab)=\log a+\log b$) will actually allow you to squeeze out answers from it if needed. $\endgroup$ – J. M. is a poor mathematician Dec 17 '16 at 20:04
6
$\begingroup$

Write $x=a\times 10^b$ with $0<a<1$. So, $$\log_{10}x=b+\log_{10}(a)=b+\frac{\log (a)}{\log (10)}$$ Now, use the very fast convergent series expansion $$\log\Big(\frac{1+x}{1-x}\Big)=2\Big(\frac{x}{1}+\frac{x^3}{3}++\frac{x^5}{5}+\cdots\Big)$$ using $a=\frac{1+x}{1-x}$ that is to say $x=\frac{a-1}{a+1}$ and you know that $\log(10)\approx 2.30259$.

$\endgroup$
  • $\begingroup$ Can you please explain a little more verbosely what it is you are doing? What is the first premise (x = a * 10^b ...)? $\endgroup$ – Adam Jensen Sep 8 '15 at 0:25
  • $\begingroup$ Since we speak about $\log_{10}(x)$, we know that $\log_{10}(10^b)=b$. So, we isolate this term first and just focus on $a$ that is to say the mantissa. $\endgroup$ – Claude Leibovici Sep 8 '15 at 6:38
  • $\begingroup$ So, if I have understood this correctly, this requires me to first refactor x into the product of a which is a number between 0 and 1, and 10^b, where b is unknown. Am I correct, and how am I supposed to do that? $\endgroup$ – Adam Jensen Sep 8 '15 at 8:19
  • 1
    $\begingroup$ Suppose that $x>1$, then count the number of times you need to divide it by $10$ until the result of the division is $<1$; this gives $b$. If $x<1$, count the number of times you need tomultiply it by $10$ until the result of the multiplication is $>1$; this gives $b+1$. $\endgroup$ – Claude Leibovici Sep 8 '15 at 8:36
  • $\begingroup$ Thank you for the clarification. So I take it it is not possible to rewrite your answer in the form $\log_{10} x = $... at least not without introducing the new variable b. Correct? $\endgroup$ – Adam Jensen Sep 8 '15 at 12:52
6
$\begingroup$

The CORDIC algorithms may help here (used by most calculators working in BCD in the old days because requiring only additions and shifts).

It uses an array $\rm{L}$ of precalculated logarithms in base $10$ ($\log$ means $\log_{10}$ here) and
$x$ will be supposed written using digits (with a decimal point) :

L= [log(2), log(1.1), log(1.01), ... , log(1.000001)];

The relation $\;\displaystyle \log(x) = \log\left(x\,10^{−n}\right) + n\;\;$ is used to get all positive real values $x$ in the range $(1,10]\;$ ($n$ is the number of shifts of the decimal points required for this purpose, $10^{−n}$ really means "right-shift of $n$" for $n>0$).

The algorithm may then be applied to $\;x\mapsto x\,10^{−n}$ :

k= 0; y= 0; p= 1;  //p is the partial product
while (k <= 6)
{
   while (x >= p+p*10^(-k))
   {
      y= y+L[k];       // L[k] = log(1+10^{-k})
      p= p+p*10^(-k);
   }
   k= k+1;
}
return y;

The idea is that for $$x=(1+1)^{n_0}\,(1+10^{-1})^{n_1}\,(1+10^{-2})^{n_2}\cdots (1+10^{-6})^{n_6}(1+\epsilon)$$ we will get $$\log(x)=n_0\log(1+1)+n_1\log(1+10^{-1})+\cdots+n_6\log(1+10^{-6})$$ and the precision should be near $7$ digits with the upperbound $6$ (more terms means more precision).

$\endgroup$
  • $\begingroup$ NB. replacing the return value $y$ by $\;y+\log(e)\,(x/p-1)\;$ would give nearly $13$ digits precision (If division and multiplication are allowed...) $\endgroup$ – Raymond Manzoni Sep 7 '15 at 12:30
4
$\begingroup$

Many platforms will at least have a function for the natural logarithm ($\ln$).

Note that $\log_{10}(x) = \ln(x)/\ln(10)$.

$\endgroup$
  • $\begingroup$ This is unfortunately not the case with the platform I'm working with. But I guess I can get an approximation of ln x using Mastrem's answer and use what you proposed. $\endgroup$ – Adam Jensen Sep 8 '15 at 0:24
3
$\begingroup$

There also exists an approximation of the logarithm from the arithmetric-geometric mean:

$$\ln x\approx\frac{\pi}{2M_{AG}(1,\frac{4}{s})}-m\ln(2)$$ where $s=2^m.x>2^\frac{p}{2}$ and error is about $\frac{\ln x}{2^p}$

This is interesting because this mean converges quickly, so you can get a better approximation than with by using Taylor series at least for general numbers. All you need to have is a definition of constants $\pi$ and $ln(2)$ with good precision.

You do not need to know $p$ in practice, this is just to show the order of precision obtained. $2^m$ is also easy to compute because it is a simple integer shift, the bigger the $m$ you choose, the bigger precision you get. I tested with $m=31$ just to stay within 32 bits types, and I got more than 10 exact decimals for $\ln x$.

And $M_{AG}$ can be calculated easily in a simple for loop, in general for usual floats double precision, it converges in less than 10 steps.

To get $\log_{10}(x)$ just divide the result by another constant $\ln(10)$.

$\endgroup$
2
$\begingroup$

You can use the formula posted above by Mastrem, but it works good enough only when n is close to 1. When n is not close to 1, then that formula gives a result with big error, and when n is a big number that formula is not applicable at all.

What to do? When n is a big number you can use the property of log, which states that $$log_a(b)^c = c \; log_a (b) $$

If you have to find ln n, and n is a big number, then you must first take 10 times (just 10 is enough for any big number) the square root of n. Let us name this new number $\alpha$:

$$\alpha = \sqrt(\sqrt(\sqrt(\sqrt(\sqrt(\sqrt(\sqrt(\sqrt(\sqrt(\sqrt(n))))))))))$$ (using the standard denomination for square root function in many programs)

so,

$$n = ((((((((((\alpha)^2)^2)^2)^2)^2)^2)^2)^2)^2)^2$$

and we can write: $$ln \,n = ln((((((((((\alpha)^2)^2)^2)^2)^2)^2)^2)^2)^2)^2$$

an using the log property explained above: $$ln \,n = 2\cdot2\cdot2\cdot2\cdot2\cdot2\cdot2\cdot2\, ln (\alpha) = 1024\, ln \,(\alpha) $$

where $\alpha$ will be always very close to 1, and the formula of Mastrem above can be used.

$\endgroup$
  • $\begingroup$ Nice to note! Welcome to Math SE by the way! +1! $\endgroup$ – Brevan Ellefsen Dec 17 '16 at 19:19

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.