Cubic Equations And The Complex Field

One thing I wish to see in languages such as PHP is to find them supporting the complex type. Complex numbers are more than vectors in 2D, and I wish to see expression containing them parsed just like the ones with real numbers. Python supports them, and you have to import ‘cmath’ to use functions of a complex variable. To import cmath type

import cmath

For example, complex numbers are useful in solving cubic equations even if all its roots are real. And cubic equations can be used for Bézier curve manipulations.

Following is the Cardan formula for solving a cubic equation

Be x^3 + ax^2 + bx + c=0 a cubic equation.

Step 1

Convert the equation to the form latex y^3 + py + q = 0
Use the Taylor series formula, to find a k, such that y=x-k:
Be P(x) = x^3 + ax^2 + bx + c
Then, P(x) = P(k) + P'(k)x + {P''(k)x^2 \over 2} + {P'''(k)x^3 \over 6}
P(k) = k^3 + ak^2 + bk + c
P'(k) = 3k^2 + 2ak + b
P''(k) = 6k + 2a
P'''(k) = 6

Because P”(k)=0, 6k + 2a=0, thus:
k= - {a \over 3} .
p=P'(k) = b - {a^2 \over 3}
q=P(k) = {2a^3 \over 27}  - {ba \over 3} + c

For example,
x^3 - 7x^2 +14x - 8 = 0
will become
y^3 -2{1 \over 3}y - {20 \over 27} = 0
In Python:

a = -7
b = 14
c = -8
p = b - a**2 / 3.
q = 2*a**3 / 27. - b*a/3. - 8

Step 2

Find 2 numbers u and v that will help us solve the equation. If y=u+v , then the new equation will be:
u^3 + v^3 + (p + 3uv)(u + v) + q = 0
We can find u,v such that (p + 3uv) = 0,
Thus,

and latex u^3 + v^3 = -q
Since p+3uv=0, u^3{v^3} = {-p^3 \over 27}
From both equations, we get that latex u^3 and latex v^3 are the roots of the quadratic equations
t^2 +qt - {q^3 \over 27} = 0
The roots of the quadratic equations are:
(1) u^3 = - {q \over 2} + \sqrt{{q^2 \over 4} + {p^3 \over 27}}
(2) v^3 = - {q \over 2} - \sqrt{{q^2 \over 4} + {p^3 \over 27}}
In Python, the inner root can be computed using:

innerRoot = cmath.sqrt(q**2 / 4. + p**3/27.)

Now, u and v are cubic roots of (1) and (2) respectively. They must satisfy 3uv=-p.
In Python, you get your initial u using:

u=(-q / 2. + innerRoot) ** (1/3.)

If the pair u,v does not satisfy 3uv = -p, you can multiply your v by
$latex-1 + i \sqrt 3 \over 2 $
until the pair satisfies the condition.
Now, having a solution, get the next by multiplying u by $latex-1 + i \sqrt 3 \over 2 and v by latex-1 – i \sqrt 3 \over 2

In our example:
u^3 = {20 \over 54} + \sqrt{{-263 \over 729}}
v^3 = {20 \over 54} - \sqrt{{-263 \over 729}}

Let’s find our three solutions:
u_1= (0.8333333333333335+0.28867513459481187j), v_1=(0.8333333333333335-0.28867513459481187j)
Thus, latex $y_1 = (1.666666666666667+0j)$
u_2 = (-0.6666666666666659+0.5773502691896264j), v_2=(-0.6666666666666657-0.5773502691896264j)
Thus, y_2 = (-1.3333333333333317+0j)
u_3 = (-0.1666666666666676-0.8660254037844383j), v_3=(-0.1666666666666677+0.866025403784438j)
Thus, y_3 = (-0.3333333333333353-2.220446049250313e-16j)

(The above values are output from Python script. The real results look much better.)
Now, to get the roots of the original equation, add k={-a \over 3} to each y.
In our example,
k = 2{1 \over 3}
Thus,
x_1 = 4, x_2=1, x_3=2

Writing expressions is much easier and more readable when the language supports the complex type.

Advertisements

PHP New Major Version

When you see a change in the major version (the number before the first point of the version id), expect a great leap. New features have been added to PHP in version 7, that make programming more convenient. I’m going to discuss some of them.

Null Coalescing

Suppose you’re trying to get a value from a request, and set it to zero if not sent. So instead of typing

$val = $_GET['foo'];
if ($val == null)
  $val=0;

Simply use ?? as follows:

$val = $_GET['foo'] ?? 0;

The Spaceship Comparison Operator

When making a decision based on comparisons between to values, would you like to use a switch command instead of if ... else? Use the operator ‘<=>’ to compare numbers or strings.
$a<=>$b will return one of the following values:
* -1 if $a is smaller than $b
* 0 if $a equals $b
* 1 if $a is greater than $b

Generator Functions

Generator functions have been introduced in PHP 5.5. They allow you to elegantly use generated values in a foreachloop without calling the function time and time again.
For example, the following code:

<?php
function factUpTo($n){
  $genValue=1;
  for ($i=1; $i<=$n;$i++){
    $genValue *= $i;
    yield $genValue;
  }
}

foreach (factUpTo(8) as $j){
  print $j . "\n";
}
?>

produces the following output:

1
2
6
24
120
720
5040
40320

Following are features introduced in PHP 7:

Returned Values

In addition to generating values, a generator can return a value using the return command. This value will be retrieved by the caller using the method getReturn().

For example, the code:


<?php

$gen = (function() {
    yield 1;
    yield 2;

    return 3;
})();

foreach ($gen as $val) {
    echo $val, PHP_EOL;
}

echo $gen->getReturn(), PHP_EOL;

will produce the output:

1
2
3

Delegation

A generator function can generate values using another generator function. This can be done by adding the keyword from after the command yield.
For example, the following code:


<?php
function gen()
{
    yield 1;
    yield 2;
    yield 4;
    yield from gen2();
}

function gen2()
{
    yield 8;
    yield 16;
}

foreach (gen() as $val)
{
    echo $val, PHP_EOL;
}
?>

will produce the following output

1
2
4
8
16

Return Type Declaration

A return type can be declare by adding it at the end of the function declaration after colons.
For example:

function myFunc(): int
{
.
.
.
return $retValue;
}

returns an integer.

Why Write The Return Type At The End?

Two possible reasons to write the type at the end of the declaration and not at the beginning like in Java, C, and other c-like languages:
* In PHP, the function declaration begins with the keyword funcction. The return type is optional.
* This syntax already exists in AcrionScript.

Find more about PHP 7 in the chapter Migrating from PHP 5.6.x to PHP 7.0.x of the php.net site documentation.

Written with StackEdit.