# ----------------------------------------------------------------------------# SymForce - Copyright 2022, Skydio, Inc.# This source code is under the Apache 2.0 license found in the LICENSE file.# ----------------------------------------------------------------------------from__future__importannotationsimportnumpyasnpimportsymforce.internal.symbolicassffromsymforceimportopsfromsymforceimporttypingasTfromsymforce.ops.interfacesimportGroup
[docs]classComplex(Group):""" A complex number is a number that can be expressed in the form a + bi, where a and b are real numbers, and i is a solution of the equation x**2 = -1. Because no real number satisfies this equation, i is called an imaginary number. For the complex number a + bi, a is called the real part, and b is called the imaginary part. Despite the historical nomenclature "imaginary", complex numbers are regarded in the mathematical sciences as just as "real" as the real numbers, and are fundamental in many aspects of the scientific description of the natural world. A complex number is also a convenient way to store a two-dimensional rotation. References: https://en.wikipedia.org/wiki/Complex_number """def__init__(self,real:T.Scalar,imag:T.Scalar)->None:""" Construct from a real and imaginary scalar. Args: real (Scalar): imag (Scalar): """self.real=realself.imag=imag# -------------------------------------------------------------------------# Storage concept - see symforce.ops.storage_ops# -------------------------------------------------------------------------def__repr__(self)->str:return"<C real={}, imag={}>".format(repr(self.real),repr(self.imag))
# -------------------------------------------------------------------------# Group concept - see symforce.ops.group_ops# -------------------------------------------------------------------------
[docs]@classmethoddefrandom_uniform(cls,low:T.Scalar,high:T.Scalar)->Complex:""" Generate a random complex number with real and imaginary parts between the given bounds """re=np.random.uniform(low,high)im=np.random.uniform(low,high)returnComplex(re,im)
[docs]@classmethoddefunit_random(cls)->Complex:""" Generate a unit-norm random complex number """u1=np.random.uniform(low=0.0,high=1.0)returncls.unit_random_from_uniform_sample(u1,pi=np.pi)
[docs]@classmethoddefunit_random_from_uniform_sample(cls,u1:T.Scalar,pi:T.Scalar=sf.pi)->Complex:""" Generate a unit-norm random Complex number from a variable sampled uniformly on [0, 1] """theta=2*pi*u1returnComplex(sf.cos(theta),sf.sin(theta))