Skip to content

Commit 13a262d

Browse files
committed
Update test to heck for inverse by identity
1 parent a783a18 commit 13a262d

File tree

1 file changed

+24
-20
lines changed

1 file changed

+24
-20
lines changed

control/tests/statesp_test.py

Lines changed: 24 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -9,20 +9,21 @@
99

1010
import operator
1111

12-
import control as ct
1312
import numpy as np
1413
import pytest
14+
from numpy.linalg import solve
15+
from numpy.testing import assert_array_almost_equal
16+
from scipy.linalg import block_diag, eigvals
17+
18+
import control as ct
1519
from control.config import defaults
1620
from control.dtime import sample_system
1721
from control.lti import evalfr
1822
from control.statesp import (StateSpace, _convert_to_statespace, _rss_generate,
1923
_statesp_defaults, drss, linfnorm, rss, ss, tf2ss)
24+
from control.tests.conftest import (assert_tf_close_coeff, editsdefaults,
25+
slycotonly)
2026
from control.xferfcn import TransferFunction, ss2tf
21-
from numpy.linalg import solve
22-
from numpy.testing import assert_array_almost_equal
23-
from scipy.linalg import block_diag, eigvals
24-
25-
from .conftest import assert_tf_close_coeff, editsdefaults, slycotonly
2627

2728

2829
class TestStateSpace:
@@ -582,25 +583,28 @@ def test_pow(self, request, sysname, power):
582583
np.testing.assert_allclose(expected.D, result.D)
583584

584585
@slycotonly
585-
@pytest.mark.parametrize("order", ["inv*sys", "sys*inv"])
586-
@pytest.mark.parametrize("sysname", ["sys222", "sys322"])
586+
@pytest.mark.parametrize("order", ["left", "right"])
587+
@pytest.mark.parametrize("sysname", ["sys121", "sys222", "sys322"])
587588
def test_pow_inv(self, request, sysname, order):
588-
"""Power of -1 (inverse of biproper system).
589+
"""Check for identity when multiplying by inverse.
589590
590-
Testing transfer function representations to avoid the
591-
non-uniqueness of the state-space representation. Once MIMO
592-
canonical forms are supported, can check canonical state-space
593-
matrices instead.
591+
This holds approximately true for a few steps but is very
592+
unstable due to numerical precision. Don't assume this in
593+
real life. For testing purposes only!
594594
"""
595595
sys = request.getfixturevalue(sysname)
596-
if order == "inv*sys":
597-
result = (sys**-1 * sys).minreal()
596+
if order == "left":
597+
combined = sys**-1 * sys
598598
else:
599-
result = (sys * sys**-1).minreal()
600-
expected = StateSpace([], [], [], np.eye(sys.ninputs), dt=0)
601-
assert_tf_close_coeff(
602-
ss2tf(expected).minreal(),
603-
ss2tf(result).minreal())
599+
combined = sys * sys**-1
600+
combined = combined.minreal()
601+
np.testing.assert_allclose(combined.dcgain(), np.eye(sys.ninputs),
602+
atol=1e-7)
603+
T = np.linspace(0., 0.3, 100)
604+
U = np.random.rand(sys.ninputs, len(T))
605+
R = combined.forced_response(T=T, U=U, squeeze=False)
606+
# Check that the output is the same as the input
607+
np.testing.assert_allclose(R.outputs, U)
604608

605609
@slycotonly
606610
def test_truediv(self, sys222, sys322):

0 commit comments

Comments
 (0)