{-# LANGUAGE ConstraintKinds       #-}
{-# LANGUAGE FlexibleContexts      #-}
{-# LANGUAGE FlexibleInstances     #-}
{-# LANGUAGE GADTs                 #-}
{-# LANGUAGE MagicHash             #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE PatternSynonyms       #-}
{-# LANGUAGE RebindableSyntax      #-}
{-# LANGUAGE ScopedTypeVariables   #-}
{-# LANGUAGE TypeApplications      #-}
{-# LANGUAGE TypeFamilies          #-}
{-# LANGUAGE TypeSynonymInstances  #-}
{-# LANGUAGE UndecidableInstances  #-}
{-# LANGUAGE ViewPatterns          #-}
{-# OPTIONS_GHC -fno-warn-orphans #-}
-- |
-- Module      : Data.Array.Accelerate.Data.Complex
-- Copyright   : [2015..2020] The Accelerate Team
-- License     : BSD3
--
-- Maintainer  : Trevor L. McDonell <trevor.mcdonell@gmail.com>
-- Stability   : experimental
-- Portability : non-portable (GHC extensions)
--
-- Complex numbers, stored in the usual C-style array-of-struct representation,
-- for easy interoperability.
--
module Data.Array.Accelerate.Data.Complex (

  -- * Rectangular from
  Complex(..), pattern (::+),
  real,
  imag,

  -- * Polar form
  mkPolar,
  cis,
  polar,
  magnitude, magnitude',
  phase,

  -- * Conjugate
  conjugate,

) where

import Data.Array.Accelerate.Classes
import Data.Array.Accelerate.Data.Functor
import Data.Array.Accelerate.Pattern
import Data.Array.Accelerate.Prelude
import Data.Array.Accelerate.Representation.Tag
import Data.Array.Accelerate.Representation.Type
import Data.Array.Accelerate.Representation.Vec
import Data.Array.Accelerate.Smart
import Data.Array.Accelerate.Sugar.Elt
import Data.Array.Accelerate.Sugar.Vec
import Data.Array.Accelerate.Type
import Data.Primitive.Vec

import Data.Complex                                                 ( Complex(..) )
import Prelude                                                      ( ($) )
import qualified Data.Complex                                       as C
import qualified Prelude                                            as P


infix 6 ::+
pattern (::+) :: Elt a => Exp a -> Exp a -> Exp (Complex a)
pattern r $b::+ :: Exp a -> Exp a -> Exp (Complex a)
$m::+ :: forall r a.
Elt a =>
Exp (Complex a) -> (Exp a -> Exp a -> r) -> (Void# -> r) -> r
::+ i <- (deconstructComplex -> (r, i))
  where (::+) = Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
constructComplex
{-# COMPLETE (::+) #-}


-- Use an array-of-structs representation for complex numbers if possible.
-- This matches the standard C-style layout, but we can use this representation only at
-- specific types (not for any type 'a') as we can only have vectors of primitive type.
-- For other types, we use a structure-of-arrays representation. This is handled by the
-- ComplexR. We use the GADT ComplexR and function complexR to reconstruct
-- information on how the elements are represented.
--
instance Elt a => Elt (Complex a) where
  type EltR (Complex a) = ComplexR (EltR a)
  eltR :: TypeR (EltR (Complex a))
eltR = let tR :: TypeR (EltR a)
tR = Elt a => TypeR (EltR a)
forall a. Elt a => TypeR (EltR a)
eltR @a
          in case TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a))
forall a. TypeR a -> ComplexType a (ComplexR a)
complexR TypeR (EltR a)
tR of
               ComplexVec SingleType (EltR a)
s -> ScalarType (Vec 2 (EltR a)) -> TupR ScalarType (Vec 2 (EltR a))
forall (s :: * -> *) a. s a -> TupR s a
TupRsingle (ScalarType (Vec 2 (EltR a)) -> TupR ScalarType (Vec 2 (EltR a)))
-> ScalarType (Vec 2 (EltR a)) -> TupR ScalarType (Vec 2 (EltR a))
forall a b. (a -> b) -> a -> b
$ VectorType (Vec 2 (EltR a)) -> ScalarType (Vec 2 (EltR a))
forall (n :: Nat) a. VectorType (Vec n a) -> ScalarType (Vec n a)
VectorScalarType (VectorType (Vec 2 (EltR a)) -> ScalarType (Vec 2 (EltR a)))
-> VectorType (Vec 2 (EltR a)) -> ScalarType (Vec 2 (EltR a))
forall a b. (a -> b) -> a -> b
$ Int -> SingleType (EltR a) -> VectorType (Vec 2 (EltR a))
forall (n :: Nat) a.
KnownNat n =>
Int -> SingleType a -> VectorType (Vec n a)
VectorType Int
2 SingleType (EltR a)
s
               ComplexType (EltR a) (ComplexR (EltR a))
ComplexTup   -> TupR ScalarType ()
forall (s :: * -> *). TupR s ()
TupRunit TupR ScalarType ()
-> TypeR (EltR a) -> TupR ScalarType ((), EltR a)
forall (s :: * -> *) a b. TupR s a -> TupR s b -> TupR s (a, b)
`TupRpair` TypeR (EltR a)
tR TupR ScalarType ((), EltR a)
-> TypeR (EltR a) -> TupR ScalarType (((), EltR a), EltR a)
forall (s :: * -> *) a b. TupR s a -> TupR s b -> TupR s (a, b)
`TupRpair` TypeR (EltR a)
tR

  tagsR :: [TagR (EltR (Complex a))]
tagsR = let tR :: TypeR (EltR a)
tR = Elt a => TypeR (EltR a)
forall a. Elt a => TypeR (EltR a)
eltR @a
           in case TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a))
forall a. TypeR a -> ComplexType a (ComplexR a)
complexR TypeR (EltR a)
tR of
               ComplexVec SingleType (EltR a)
s -> [ ScalarType (Vec 2 (EltR a)) -> TagR (Vec 2 (EltR a))
forall a. ScalarType a -> TagR a
TagRsingle (VectorType (Vec 2 (EltR a)) -> ScalarType (Vec 2 (EltR a))
forall (n :: Nat) a. VectorType (Vec n a) -> ScalarType (Vec n a)
VectorScalarType (Int -> SingleType (EltR a) -> VectorType (Vec 2 (EltR a))
forall (n :: Nat) a.
KnownNat n =>
Int -> SingleType a -> VectorType (Vec n a)
VectorType Int
2 SingleType (EltR a)
s)) ]
               ComplexType (EltR a) (ComplexR (EltR a))
ComplexTup   -> let go :: TypeR t -> [TagR t]
                                   go :: TypeR t -> [TagR t]
go TypeR t
TupRunit         = [TagR t
TagR ()
TagRunit]
                                   go (TupRsingle ScalarType t
s)   = [ScalarType t -> TagR t
forall a. ScalarType a -> TagR a
TagRsingle ScalarType t
s]
                                   go (TupRpair TupR ScalarType a
ta TupR ScalarType b
tb) = [TagR a -> TagR b -> TagR (a, b)
forall a b. TagR a -> TagR b -> TagR (a, b)
TagRpair TagR a
a TagR b
b | TagR a
a <- TupR ScalarType a -> [TagR a]
forall t. TypeR t -> [TagR t]
go TupR ScalarType a
ta, TagR b
b <- TupR ScalarType b -> [TagR b]
forall t. TypeR t -> [TagR t]
go TupR ScalarType b
tb]
                                in
                                [ TagR ()
TagRunit TagR () -> TagR (EltR a) -> TagR ((), EltR a)
forall a b. TagR a -> TagR b -> TagR (a, b)
`TagRpair` TagR (EltR a)
ta TagR ((), EltR a) -> TagR (EltR a) -> TagR (((), EltR a), EltR a)
forall a b. TagR a -> TagR b -> TagR (a, b)
`TagRpair` TagR (EltR a)
tb | TagR (EltR a)
ta <- TypeR (EltR a) -> [TagR (EltR a)]
forall t. TypeR t -> [TagR t]
go TypeR (EltR a)
tR, TagR (EltR a)
tb <- TypeR (EltR a) -> [TagR (EltR a)]
forall t. TypeR t -> [TagR t]
go TypeR (EltR a)
tR ]

  toElt :: EltR (Complex a) -> Complex a
toElt = case TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a))
forall a. TypeR a -> ComplexType a (ComplexR a)
complexR (TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a)))
-> TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a))
forall a b. (a -> b) -> a -> b
$ Elt a => TypeR (EltR a)
forall a. Elt a => TypeR (EltR a)
eltR @a of
    ComplexVec SingleType (EltR a)
_ -> \(Vec2 r i)   -> EltR a -> a
forall a. Elt a => EltR a -> a
toElt EltR a
r a -> a -> Complex a
forall a. a -> a -> Complex a
:+ EltR a -> a
forall a. Elt a => EltR a -> a
toElt EltR a
i
    ComplexType (EltR a) (ComplexR (EltR a))
ComplexTup   -> \(((), r), i) -> EltR a -> a
forall a. Elt a => EltR a -> a
toElt EltR a
r a -> a -> Complex a
forall a. a -> a -> Complex a
:+ EltR a -> a
forall a. Elt a => EltR a -> a
toElt EltR a
i

  fromElt :: Complex a -> EltR (Complex a)
fromElt (a
r :+ a
i) = case TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a))
forall a. TypeR a -> ComplexType a (ComplexR a)
complexR (TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a)))
-> TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a))
forall a b. (a -> b) -> a -> b
$ Elt a => TypeR (EltR a)
forall a. Elt a => TypeR (EltR a)
eltR @a of
    ComplexVec SingleType (EltR a)
_ -> EltR a -> EltR a -> Vec 2 (EltR a)
forall a. Prim a => a -> a -> Vec2 a
Vec2 (a -> EltR a
forall a. Elt a => a -> EltR a
fromElt a
r) (a -> EltR a
forall a. Elt a => a -> EltR a
fromElt a
i)
    ComplexType (EltR a) (ComplexR (EltR a))
ComplexTup   -> (((), a -> EltR a
forall a. Elt a => a -> EltR a
fromElt a
r), a -> EltR a
forall a. Elt a => a -> EltR a
fromElt a
i)

type family ComplexR a where
  ComplexR Half   = Vec2 Half
  ComplexR Float  = Vec2 Float
  ComplexR Double = Vec2 Double
  ComplexR Int    = Vec2 Int
  ComplexR Int8   = Vec2 Int8
  ComplexR Int16  = Vec2 Int16
  ComplexR Int32  = Vec2 Int32
  ComplexR Int64  = Vec2 Int64
  ComplexR Word   = Vec2 Word
  ComplexR Word8  = Vec2 Word8
  ComplexR Word16 = Vec2 Word16
  ComplexR Word32 = Vec2 Word32
  ComplexR Word64 = Vec2 Word64
  ComplexR a      = (((), a), a)

-- This isn't ideal because we gather the evidence based on the
-- representation type, so we really get the evidence (VecElt (EltR a)),
-- which is not very useful...
--    - TLM 2020-07-16
data ComplexType a c where
  ComplexVec :: VecElt a => SingleType a -> ComplexType a (Vec2 a)
  ComplexTup ::                             ComplexType a (((), a), a)

complexR :: TypeR a -> ComplexType a (ComplexR a)
complexR :: TypeR a -> ComplexType a (ComplexR a)
complexR = TypeR a -> ComplexType a (ComplexR a)
forall a. TypeR a -> ComplexType a (ComplexR a)
tuple
  where
    tuple :: TypeR a -> ComplexType a (ComplexR a)
    tuple :: TypeR a -> ComplexType a (ComplexR a)
tuple TypeR a
TupRunit       = ComplexType a (ComplexR a)
forall a. ComplexType a (((), a), a)
ComplexTup
    tuple TupRpair{}     = ComplexType a (ComplexR a)
forall a. ComplexType a (((), a), a)
ComplexTup
    tuple (TupRsingle ScalarType a
s) = ScalarType a -> ComplexType a (ComplexR a)
forall a. ScalarType a -> ComplexType a (ComplexR a)
scalar ScalarType a
s

    scalar :: ScalarType a -> ComplexType a (ComplexR a)
    scalar :: ScalarType a -> ComplexType a (ComplexR a)
scalar (SingleScalarType SingleType a
t) = SingleType a -> ComplexType a (ComplexR a)
forall a. SingleType a -> ComplexType a (ComplexR a)
single SingleType a
t
    scalar VectorScalarType{}   = ComplexType a (ComplexR a)
forall a. ComplexType a (((), a), a)
ComplexTup

    single :: SingleType a -> ComplexType a (ComplexR a)
    single :: SingleType a -> ComplexType a (ComplexR a)
single (NumSingleType NumType a
t) = NumType a -> ComplexType a (ComplexR a)
forall a. NumType a -> ComplexType a (ComplexR a)
num NumType a
t

    num :: NumType a -> ComplexType a (ComplexR a)
    num :: NumType a -> ComplexType a (ComplexR a)
num (IntegralNumType IntegralType a
t) = IntegralType a -> ComplexType a (ComplexR a)
forall a. IntegralType a -> ComplexType a (ComplexR a)
integral IntegralType a
t
    num (FloatingNumType FloatingType a
t) = FloatingType a -> ComplexType a (ComplexR a)
forall a. FloatingType a -> ComplexType a (ComplexR a)
floating FloatingType a
t

    integral :: IntegralType a -> ComplexType a (ComplexR a)
    integral :: IntegralType a -> ComplexType a (ComplexR a)
integral IntegralType a
TypeInt    = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    integral IntegralType a
TypeInt8   = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    integral IntegralType a
TypeInt16  = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    integral IntegralType a
TypeInt32  = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    integral IntegralType a
TypeInt64  = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    integral IntegralType a
TypeWord   = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    integral IntegralType a
TypeWord8  = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    integral IntegralType a
TypeWord16 = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    integral IntegralType a
TypeWord32 = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    integral IntegralType a
TypeWord64 = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType

    floating :: FloatingType a -> ComplexType a (ComplexR a)
    floating :: FloatingType a -> ComplexType a (ComplexR a)
floating FloatingType a
TypeHalf   = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    floating FloatingType a
TypeFloat  = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType
    floating FloatingType a
TypeDouble = SingleType a -> ComplexType a (Vec2 a)
forall a. VecElt a => SingleType a -> ComplexType a (Vec2 a)
ComplexVec SingleType a
forall a. IsSingle a => SingleType a
singleType


constructComplex :: forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
constructComplex :: Exp a -> Exp a -> Exp (Complex a)
constructComplex Exp a
r Exp a
i =
  case TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a))
forall a. TypeR a -> ComplexType a (ComplexR a)
complexR (Elt a => TypeR (EltR a)
forall a. Elt a => TypeR (EltR a)
eltR @a) of
    ComplexType (EltR a) (ComplexR (EltR a))
ComplexTup   -> Exp (a, a) -> Exp (Complex a)
forall a b. (EltR a ~ EltR b) => Exp a -> Exp b
coerce (Exp (a, a) -> Exp (Complex a)) -> Exp (a, a) -> Exp (Complex a)
forall a b. (a -> b) -> a -> b
$ Exp a -> Exp a -> Exp (a, a)
forall (con :: * -> *) x0 x1.
IsPattern con (x0, x1) (con x0, con x1) =>
con x0 -> con x1 -> con (x0, x1)
T2 Exp a
r Exp a
i
    ComplexVec SingleType (EltR a)
_ -> Exp (EltR a) -> Exp (EltR a) -> Exp (Complex a)
forall (con :: * -> *) vec x0 x1.
IsVector con vec (con x0, con x1) =>
con x0 -> con x1 -> con vec
V2 (Exp a -> Exp (EltR a)
forall a b. (EltR a ~ EltR b) => Exp a -> Exp b
coerce @a @(EltR a) Exp a
r) (Exp a -> Exp (EltR a)
forall a b. (EltR a ~ EltR b) => Exp a -> Exp b
coerce @a @(EltR a) Exp a
i)

deconstructComplex :: forall a. Elt a => Exp (Complex a) -> (Exp a, Exp a)
deconstructComplex :: Exp (Complex a) -> (Exp a, Exp a)
deconstructComplex c :: Exp (Complex a)
c@(Exp SmartExp (EltR (Complex a))
c') =
  case TypeR (EltR a) -> ComplexType (EltR a) (ComplexR (EltR a))
forall a. TypeR a -> ComplexType a (ComplexR a)
complexR (Elt a => TypeR (EltR a)
forall a. Elt a => TypeR (EltR a)
eltR @a) of
    ComplexType (EltR a) (ComplexR (EltR a))
ComplexTup   -> let T2 Exp a
r Exp a
i = Exp (Complex a) -> Exp (a, a)
forall a b. (EltR a ~ EltR b) => Exp a -> Exp b
coerce Exp (Complex a)
c in (Exp a
r, Exp a
i)
    ComplexVec SingleType (EltR a)
t -> let T2 Exp a
r Exp a
i = SmartExp (EltR (a, a)) -> Exp (a, a)
forall t. SmartExp (EltR t) -> Exp t
Exp (PreSmartExp SmartAcc SmartExp (((), EltR a), EltR a)
-> SmartExp (((), EltR a), EltR a)
forall t. PreSmartExp SmartAcc SmartExp t -> SmartExp t
SmartExp (VecR 2 (EltR a) (((), EltR a), EltR a)
-> SmartExp (Vec 2 (EltR a))
-> PreSmartExp SmartAcc SmartExp (((), EltR a), EltR a)
forall (n :: Nat) s tup (exp :: * -> *) (acc :: * -> *).
KnownNat n =>
VecR n s tup -> exp (Vec n s) -> PreSmartExp acc exp tup
VecUnpack (VecR 1 (EltR a) ((), EltR a)
-> VecR (1 + 1) (EltR a) (((), EltR a), EltR a)
forall (n :: Nat) s t. VecR n s t -> VecR (n + 1) s (t, s)
VecRsucc (VecR 0 (EltR a) () -> VecR (0 + 1) (EltR a) ((), EltR a)
forall (n :: Nat) s t. VecR n s t -> VecR (n + 1) s (t, s)
VecRsucc (SingleType (EltR a) -> VecR 0 (EltR a) ()
forall s. SingleType s -> VecR 0 s ()
VecRnil SingleType (EltR a)
t))) SmartExp (Vec 2 (EltR a))
SmartExp (EltR (Complex a))
c'))
                     in (Exp a
r, Exp a
i)

coerce :: EltR a ~ EltR b => Exp a -> Exp b
coerce :: Exp a -> Exp b
coerce (Exp SmartExp (EltR a)
e) = SmartExp (EltR b) -> Exp b
forall t. SmartExp (EltR t) -> Exp t
Exp SmartExp (EltR a)
SmartExp (EltR b)
e

instance (Lift Exp a, Elt (Plain a)) => Lift Exp (Complex a) where
  type Plain (Complex a) = Complex (Plain a)
  lift :: Complex a -> Exp (Plain (Complex a))
lift (a
r :+ a
i) = a -> Exp (Plain a)
forall (c :: * -> *) e. Lift c e => e -> c (Plain e)
lift a
r Exp (Plain a) -> Exp (Plain a) -> Exp (Complex (Plain a))
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ a -> Exp (Plain a)
forall (c :: * -> *) e. Lift c e => e -> c (Plain e)
lift a
i

instance Elt a => Unlift Exp (Complex (Exp a)) where
  unlift :: Exp (Plain (Complex (Exp a))) -> Complex (Exp a)
unlift (r ::+ i) = Exp a
r Exp a -> Exp a -> Complex (Exp a)
forall a. a -> a -> Complex a
:+ Exp a
i


instance Eq a => Eq (Complex a) where
  Exp a
r1 ::+ Exp a
c1 == :: Exp (Complex a) -> Exp (Complex a) -> Exp Bool
== Exp a
r2 ::+ Exp a
c2 = Exp a
r1 Exp a -> Exp a -> Exp Bool
forall a. Eq a => Exp a -> Exp a -> Exp Bool
== Exp a
r2 Exp Bool -> Exp Bool -> Exp Bool
&& Exp a
c1 Exp a -> Exp a -> Exp Bool
forall a. Eq a => Exp a -> Exp a -> Exp Bool
== Exp a
c2
  Exp a
r1 ::+ Exp a
c1 /= :: Exp (Complex a) -> Exp (Complex a) -> Exp Bool
/= Exp a
r2 ::+ Exp a
c2 = Exp a
r1 Exp a -> Exp a -> Exp Bool
forall a. Eq a => Exp a -> Exp a -> Exp Bool
/= Exp a
r2 Exp Bool -> Exp Bool -> Exp Bool
|| Exp a
c1 Exp a -> Exp a -> Exp Bool
forall a. Eq a => Exp a -> Exp a -> Exp Bool
/= Exp a
c2

instance RealFloat a => P.Num (Exp (Complex a)) where
  + :: Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
(+)    = (Complex (Exp a) -> Complex (Exp a) -> Complex (Exp a))
-> Exp (Plain (Complex (Exp a)))
-> Exp (Plain (Complex (Exp a)))
-> Exp (Plain (Complex (Exp a)))
forall a b c.
(Unlift Exp a, Unlift Exp b, Lift Exp c) =>
(a -> b -> c) -> Exp (Plain a) -> Exp (Plain b) -> Exp (Plain c)
lift2 (Complex (Exp a) -> Complex (Exp a) -> Complex (Exp a)
forall a. Num a => a -> a -> a
(+) :: Complex (Exp a) -> Complex (Exp a) -> Complex (Exp a))
  (-)    = (Complex (Exp a) -> Complex (Exp a) -> Complex (Exp a))
-> Exp (Plain (Complex (Exp a)))
-> Exp (Plain (Complex (Exp a)))
-> Exp (Plain (Complex (Exp a)))
forall a b c.
(Unlift Exp a, Unlift Exp b, Lift Exp c) =>
(a -> b -> c) -> Exp (Plain a) -> Exp (Plain b) -> Exp (Plain c)
lift2 ((-) :: Complex (Exp a) -> Complex (Exp a) -> Complex (Exp a))
  * :: Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
(*)    = (Complex (Exp a) -> Complex (Exp a) -> Complex (Exp a))
-> Exp (Plain (Complex (Exp a)))
-> Exp (Plain (Complex (Exp a)))
-> Exp (Plain (Complex (Exp a)))
forall a b c.
(Unlift Exp a, Unlift Exp b, Lift Exp c) =>
(a -> b -> c) -> Exp (Plain a) -> Exp (Plain b) -> Exp (Plain c)
lift2 (Complex (Exp a) -> Complex (Exp a) -> Complex (Exp a)
forall a. Num a => a -> a -> a
(*) :: Complex (Exp a) -> Complex (Exp a) -> Complex (Exp a))
  negate :: Exp (Complex a) -> Exp (Complex a)
negate = (Complex (Exp a) -> Complex (Exp a))
-> Exp (Plain (Complex (Exp a))) -> Exp (Plain (Complex (Exp a)))
forall a b.
(Unlift Exp a, Lift Exp b) =>
(a -> b) -> Exp (Plain a) -> Exp (Plain b)
lift1 (Complex (Exp a) -> Complex (Exp a)
forall a. Num a => a -> a
negate :: Complex (Exp a) -> Complex (Exp a))
  signum :: Exp (Complex a) -> Exp (Complex a)
signum z :: Exp (Complex a)
z@(Exp a
x ::+ Exp a
y) =
    if Exp (Complex a)
z Exp (Complex a) -> Exp (Complex a) -> Exp Bool
forall a. Eq a => Exp a -> Exp a -> Exp Bool
== Exp (Complex a)
0
       then Exp (Complex a)
z
       else let r :: Exp a
r = Exp (Complex a) -> Exp a
forall a. RealFloat a => Exp (Complex a) -> Exp a
magnitude Exp (Complex a)
z
             in Exp a
xExp a -> Exp a -> Exp a
forall a. Fractional a => a -> a -> a
/Exp a
r Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
yExp a -> Exp a -> Exp a
forall a. Fractional a => a -> a -> a
/Exp a
r
  abs :: Exp (Complex a) -> Exp (Complex a)
abs Exp (Complex a)
z         = Exp (Complex a) -> Exp a
forall a. RealFloat a => Exp (Complex a) -> Exp a
magnitude Exp (Complex a)
z Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
0
  fromInteger :: Integer -> Exp (Complex a)
fromInteger Integer
n = Integer -> Exp a
forall a. Num a => Integer -> a
fromInteger Integer
n Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
0

instance RealFloat a => P.Fractional (Exp (Complex a)) where
  fromRational :: Rational -> Exp (Complex a)
fromRational Rational
x  = Rational -> Exp a
forall a. Fractional a => Rational -> a
fromRational Rational
x Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
0
  Exp (Complex a)
z / :: Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
/ Exp (Complex a)
z'          = (Exp a
xExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
x''Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
+Exp a
yExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
y'') Exp a -> Exp a -> Exp a
forall a. Fractional a => a -> a -> a
/ Exp a
d Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ (Exp a
yExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
x''Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
-Exp a
xExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
y'') Exp a -> Exp a -> Exp a
forall a. Fractional a => a -> a -> a
/ Exp a
d
    where
      Exp a
x  :+ Exp a
y   = Exp (Plain (Complex (Exp a))) -> Complex (Exp a)
forall (c :: * -> *) e. Unlift c e => c (Plain e) -> e
unlift Exp (Complex a)
Exp (Plain (Complex (Exp a)))
z
      Exp a
x' :+ Exp a
y'  = Exp (Plain (Complex (Exp a))) -> Complex (Exp a)
forall (c :: * -> *) e. Unlift c e => c (Plain e) -> e
unlift Exp (Complex a)
Exp (Plain (Complex (Exp a)))
z'
      --
      x'' :: Exp a
x'' = Exp Int -> Exp a -> Exp a
forall a. RealFloat a => Exp Int -> Exp a -> Exp a
scaleFloat Exp Int
k Exp a
x'
      y'' :: Exp a
y'' = Exp Int -> Exp a -> Exp a
forall a. RealFloat a => Exp Int -> Exp a -> Exp a
scaleFloat Exp Int
k Exp a
y'
      k :: Exp Int
k   = - Exp Int -> Exp Int -> Exp Int
forall a. Ord a => Exp a -> Exp a -> Exp a
max (Exp a -> Exp Int
forall a. RealFloat a => Exp a -> Exp Int
exponent Exp a
x') (Exp a -> Exp Int
forall a. RealFloat a => Exp a -> Exp Int
exponent Exp a
y')
      d :: Exp a
d   = Exp a
x'Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
x'' Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
+ Exp a
y'Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
y''

instance RealFloat a => P.Floating (Exp (Complex a)) where
  pi :: Exp (Complex a)
pi                = Exp a
forall a. Floating a => a
pi Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
0
  exp :: Exp (Complex a) -> Exp (Complex a)
exp (Exp a
x ::+ Exp a
y)     = let expx :: Exp a
expx = Exp a -> Exp a
forall a. Floating a => a -> a
exp Exp a
x
                       in Exp a
expx Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
cos Exp a
y Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
expx Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
sin Exp a
y
  log :: Exp (Complex a) -> Exp (Complex a)
log Exp (Complex a)
z             = Exp a -> Exp a
forall a. Floating a => a -> a
log (Exp (Complex a) -> Exp a
forall a. RealFloat a => Exp (Complex a) -> Exp a
magnitude Exp (Complex a)
z) Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp (Complex a) -> Exp a
forall a. RealFloat a => Exp (Complex a) -> Exp a
phase Exp (Complex a)
z
  sqrt :: Exp (Complex a) -> Exp (Complex a)
sqrt z :: Exp (Complex a)
z@(Exp a
x ::+ Exp a
y)  =
    if Exp (Complex a)
z Exp (Complex a) -> Exp (Complex a) -> Exp Bool
forall a. Eq a => Exp a -> Exp a -> Exp Bool
== Exp (Complex a)
0
      then Exp (Complex a)
0
      else Exp a
u Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ (Exp a
y Exp a -> Exp a -> Exp Bool
forall a. Ord a => Exp a -> Exp a -> Exp Bool
< Exp a
0 Exp Bool -> (Exp a, Exp a) -> Exp a
forall t. Elt t => Exp Bool -> (Exp t, Exp t) -> Exp t
? (-Exp a
v, Exp a
v))
    where
      T2 Exp a
u Exp a
v = Exp a
x Exp a -> Exp a -> Exp Bool
forall a. Ord a => Exp a -> Exp a -> Exp Bool
< Exp a
0 Exp Bool -> (Exp (a, a), Exp (a, a)) -> Exp (a, a)
forall t. Elt t => Exp Bool -> (Exp t, Exp t) -> Exp t
? (Exp a -> Exp a -> Exp (a, a)
forall (con :: * -> *) x0 x1.
IsPattern con (x0, x1) (con x0, con x1) =>
con x0 -> con x1 -> con (x0, x1)
T2 Exp a
v' Exp a
u', Exp a -> Exp a -> Exp (a, a)
forall (con :: * -> *) x0 x1.
IsPattern con (x0, x1) (con x0, con x1) =>
con x0 -> con x1 -> con (x0, x1)
T2 Exp a
u' Exp a
v')
      v' :: Exp a
v'     = Exp a -> Exp a
forall a. Num a => a -> a
abs Exp a
y Exp a -> Exp a -> Exp a
forall a. Fractional a => a -> a -> a
/ (Exp a
u'Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
2)
      u' :: Exp a
u'     = Exp a -> Exp a
forall a. Floating a => a -> a
sqrt ((Exp (Complex a) -> Exp a
forall a. RealFloat a => Exp (Complex a) -> Exp a
magnitude Exp (Complex a)
z Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
+ Exp a -> Exp a
forall a. Num a => a -> a
abs Exp a
x) Exp a -> Exp a -> Exp a
forall a. Fractional a => a -> a -> a
/ Exp a
2)

  Exp (Complex a)
x ** :: Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
** Exp (Complex a)
y =
    if Exp (Complex a)
y Exp (Complex a) -> Exp (Complex a) -> Exp Bool
forall a. Eq a => Exp a -> Exp a -> Exp Bool
== Exp (Complex a)
0 then Exp (Complex a)
1 else
    if Exp (Complex a)
x Exp (Complex a) -> Exp (Complex a) -> Exp Bool
forall a. Eq a => Exp a -> Exp a -> Exp Bool
== Exp (Complex a)
0 then if Exp a
exp_r Exp a -> Exp a -> Exp Bool
forall a. Ord a => Exp a -> Exp a -> Exp Bool
> Exp a
0 then Exp (Complex a)
0 else
                   if Exp a
exp_r Exp a -> Exp a -> Exp Bool
forall a. Ord a => Exp a -> Exp a -> Exp Bool
< Exp a
0 then Exp a
inf Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
0
                                else Exp a
nan Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
nan
              else if Exp a -> Exp Bool
forall a. RealFloat a => Exp a -> Exp Bool
isInfinite Exp a
r Exp Bool -> Exp Bool -> Exp Bool
|| Exp a -> Exp Bool
forall a. RealFloat a => Exp a -> Exp Bool
isInfinite Exp a
i
                     then if Exp a
exp_r Exp a -> Exp a -> Exp Bool
forall a. Ord a => Exp a -> Exp a -> Exp Bool
> Exp a
0 then Exp a
inf Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
0 else
                          if Exp a
exp_r Exp a -> Exp a -> Exp Bool
forall a. Ord a => Exp a -> Exp a -> Exp Bool
< Exp a
0 then Exp (Complex a)
0
                                       else Exp a
nan Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
nan
                     else Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
exp (Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
log Exp (Complex a)
x Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
* Exp (Complex a)
y)
    where
      Exp a
r     ::+ Exp a
i  = Exp (Complex a)
x
      Exp a
exp_r ::+ Exp a
_  = Exp (Complex a)
y
      --
      inf :: Exp a
inf = Exp a
1 Exp a -> Exp a -> Exp a
forall a. Fractional a => a -> a -> a
/ Exp a
0
      nan :: Exp a
nan = Exp a
0 Exp a -> Exp a -> Exp a
forall a. Fractional a => a -> a -> a
/ Exp a
0

  sin :: Exp (Complex a) -> Exp (Complex a)
sin (Exp a
x ::+ Exp a
y)  = Exp a -> Exp a
forall a. Floating a => a -> a
sin Exp a
x Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
cosh Exp a
y Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a -> Exp a
forall a. Floating a => a -> a
cos Exp a
x Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
sinh Exp a
y
  cos :: Exp (Complex a) -> Exp (Complex a)
cos (Exp a
x ::+ Exp a
y)  = Exp a -> Exp a
forall a. Floating a => a -> a
cos Exp a
x Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
cosh Exp a
y Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ (- Exp a -> Exp a
forall a. Floating a => a -> a
sin Exp a
x Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
sinh Exp a
y)
  tan :: Exp (Complex a) -> Exp (Complex a)
tan (Exp a
x ::+ Exp a
y)  = (Exp a
sinxExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
coshy Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
cosxExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
sinhy) Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Fractional a => a -> a -> a
/ (Exp a
cosxExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
coshy Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ (-Exp a
sinxExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
sinhy))
    where
      sinx :: Exp a
sinx  = Exp a -> Exp a
forall a. Floating a => a -> a
sin Exp a
x
      cosx :: Exp a
cosx  = Exp a -> Exp a
forall a. Floating a => a -> a
cos Exp a
x
      sinhy :: Exp a
sinhy = Exp a -> Exp a
forall a. Floating a => a -> a
sinh Exp a
y
      coshy :: Exp a
coshy = Exp a -> Exp a
forall a. Floating a => a -> a
cosh Exp a
y

  sinh :: Exp (Complex a) -> Exp (Complex a)
sinh (Exp a
x ::+ Exp a
y) = Exp a -> Exp a
forall a. Floating a => a -> a
cos Exp a
y Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
sinh Exp a
x Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a -> Exp a
forall a. Floating a => a -> a
sin  Exp a
y Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
cosh Exp a
x
  cosh :: Exp (Complex a) -> Exp (Complex a)
cosh (Exp a
x ::+ Exp a
y) = Exp a -> Exp a
forall a. Floating a => a -> a
cos Exp a
y Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
cosh Exp a
x Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a -> Exp a
forall a. Floating a => a -> a
sin Exp a
y Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
* Exp a -> Exp a
forall a. Floating a => a -> a
sinh Exp a
x
  tanh :: Exp (Complex a) -> Exp (Complex a)
tanh (Exp a
x ::+ Exp a
y) = (Exp a
cosyExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
sinhx Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
sinyExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
coshx) Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Fractional a => a -> a -> a
/ (Exp a
cosyExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
coshx Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
sinyExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
sinhx)
    where
      siny :: Exp a
siny  = Exp a -> Exp a
forall a. Floating a => a -> a
sin Exp a
y
      cosy :: Exp a
cosy  = Exp a -> Exp a
forall a. Floating a => a -> a
cos Exp a
y
      sinhx :: Exp a
sinhx = Exp a -> Exp a
forall a. Floating a => a -> a
sinh Exp a
x
      coshx :: Exp a
coshx = Exp a -> Exp a
forall a. Floating a => a -> a
cosh Exp a
x

  asin :: Exp (Complex a) -> Exp (Complex a)
asin z :: Exp (Complex a)
z@(Exp a
x ::+ Exp a
y) = Exp a
y' Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ (-Exp a
x')
    where
      Exp a
x' ::+ Exp a
y' = Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
log (((-Exp a
y) Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
x) Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
+ Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
sqrt (Exp (Complex a)
1 Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
- Exp (Complex a)
zExp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
*Exp (Complex a)
z))

  acos :: Exp (Complex a) -> Exp (Complex a)
acos Exp (Complex a)
z                    = Exp a
y'' Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ (-Exp a
x'')
    where
      Exp a
x'' ::+ Exp a
y''  = Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
log (Exp (Complex a)
z Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
+ ((-Exp a
y') Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
x'))
      Exp a
x'  ::+ Exp a
y'   = Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
sqrt (Exp (Complex a)
1 Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
- Exp (Complex a)
zExp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
*Exp (Complex a)
z)

  atan :: Exp (Complex a) -> Exp (Complex a)
atan z :: Exp (Complex a)
z@(Exp a
x ::+ Exp a
y) = Exp a
y' Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ (-Exp a
x')
    where
      Exp a
x' ::+ Exp a
y' = Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
log (((Exp a
1Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
-Exp a
y) Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a
x) Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Fractional a => a -> a -> a
/ Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
sqrt (Exp (Complex a)
1Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
+Exp (Complex a)
zExp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
*Exp (Complex a)
z))

  asinh :: Exp (Complex a) -> Exp (Complex a)
asinh Exp (Complex a)
z =  Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
log (Exp (Complex a)
z Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
+ Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
sqrt (Exp (Complex a)
1Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
+Exp (Complex a)
zExp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
*Exp (Complex a)
z))
  acosh :: Exp (Complex a) -> Exp (Complex a)
acosh Exp (Complex a)
z =  Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
log (Exp (Complex a)
z Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
+ (Exp (Complex a)
zExp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
+Exp (Complex a)
1) Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
* Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
sqrt ((Exp (Complex a)
zExp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
-Exp (Complex a)
1)Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Fractional a => a -> a -> a
/(Exp (Complex a)
zExp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
+Exp (Complex a)
1)))
  atanh :: Exp (Complex a) -> Exp (Complex a)
atanh Exp (Complex a)
z =  Exp (Complex a)
0.5 Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
* Exp (Complex a) -> Exp (Complex a)
forall a. Floating a => a -> a
log ((Exp (Complex a)
1.0Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
+Exp (Complex a)
z) Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Fractional a => a -> a -> a
/ (Exp (Complex a)
1.0Exp (Complex a) -> Exp (Complex a) -> Exp (Complex a)
forall a. Num a => a -> a -> a
-Exp (Complex a)
z))


instance (FromIntegral a b, Num b, Elt (Complex b)) => FromIntegral a (Complex b) where
  fromIntegral :: Exp a -> Exp (Complex b)
fromIntegral Exp a
x = Exp a -> Exp b
forall a b. (FromIntegral a b, Integral a) => Exp a -> Exp b
fromIntegral Exp a
x Exp b -> Exp b -> Exp (Complex b)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp b
0

-- | @since 1.2.0.0
--
instance Functor Complex where
  fmap :: (Exp a -> Exp b) -> Exp (Complex a) -> Exp (Complex b)
fmap Exp a -> Exp b
f (Exp a
r ::+ Exp a
i) = Exp a -> Exp b
f Exp a
r Exp b -> Exp b -> Exp (Complex b)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ Exp a -> Exp b
f Exp a
i


-- | The non-negative magnitude of a complex number
--
magnitude :: RealFloat a => Exp (Complex a) -> Exp a
magnitude :: Exp (Complex a) -> Exp a
magnitude (Exp a
r ::+ Exp a
i) = Exp Int -> Exp a -> Exp a
forall a. RealFloat a => Exp Int -> Exp a -> Exp a
scaleFloat Exp Int
k (Exp a -> Exp a
forall a. Floating a => a -> a
sqrt (Exp a -> Exp a
forall a. Num a => a -> a
sqr (Exp Int -> Exp a -> Exp a
forall a. RealFloat a => Exp Int -> Exp a -> Exp a
scaleFloat Exp Int
mk Exp a
r) Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
+ Exp a -> Exp a
forall a. Num a => a -> a
sqr (Exp Int -> Exp a -> Exp a
forall a. RealFloat a => Exp Int -> Exp a -> Exp a
scaleFloat Exp Int
mk Exp a
i)))
  where
    k :: Exp Int
k     = Exp Int -> Exp Int -> Exp Int
forall a. Ord a => Exp a -> Exp a -> Exp a
max (Exp a -> Exp Int
forall a. RealFloat a => Exp a -> Exp Int
exponent Exp a
r) (Exp a -> Exp Int
forall a. RealFloat a => Exp a -> Exp Int
exponent Exp a
i)
    mk :: Exp Int
mk    = -Exp Int
k
    sqr :: a -> a
sqr a
z = a
z a -> a -> a
forall a. Num a => a -> a -> a
* a
z

-- | As 'magnitude', but ignore floating point rounding and use the traditional
-- (simpler to evaluate) definition.
--
-- @since 1.3.0.0
--
magnitude' :: RealFloat a => Exp (Complex a) -> Exp a
magnitude' :: Exp (Complex a) -> Exp a
magnitude' (Exp a
r ::+ Exp a
i) = Exp a -> Exp a
forall a. Floating a => a -> a
sqrt (Exp a
rExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
r Exp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
+ Exp a
iExp a -> Exp a -> Exp a
forall a. Num a => a -> a -> a
*Exp a
i)

-- | The phase of a complex number, in the range @(-'pi', 'pi']@. If the
-- magnitude is zero, then so is the phase.
--
phase :: RealFloat a => Exp (Complex a) -> Exp a
phase :: Exp (Complex a) -> Exp a
phase z :: Exp (Complex a)
z@(Exp a
r ::+ Exp a
i) =
  if Exp (Complex a)
z Exp (Complex a) -> Exp (Complex a) -> Exp Bool
forall a. Eq a => Exp a -> Exp a -> Exp Bool
== Exp (Complex a)
0
    then Exp a
0
    else Exp a -> Exp a -> Exp a
forall a. RealFloat a => Exp a -> Exp a -> Exp a
atan2 Exp a
i Exp a
r

-- | The function 'polar' takes a complex number and returns a (magnitude,
-- phase) pair in canonical form: the magnitude is non-negative, and the phase
-- in the range @(-'pi', 'pi']@; if the magnitude is zero, then so is the phase.
--
polar :: RealFloat a => Exp (Complex a) -> Exp (a,a)
polar :: Exp (Complex a) -> Exp (a, a)
polar Exp (Complex a)
z =  Exp a -> Exp a -> Exp (a, a)
forall (con :: * -> *) x0 x1.
IsPattern con (x0, x1) (con x0, con x1) =>
con x0 -> con x1 -> con (x0, x1)
T2 (Exp (Complex a) -> Exp a
forall a. RealFloat a => Exp (Complex a) -> Exp a
magnitude Exp (Complex a)
z) (Exp (Complex a) -> Exp a
forall a. RealFloat a => Exp (Complex a) -> Exp a
phase Exp (Complex a)
z)

-- | Form a complex number from polar components of magnitude and phase.
--
mkPolar :: forall a. Floating a => Exp a -> Exp a -> Exp (Complex a)
mkPolar :: Exp a -> Exp a -> Exp (Complex a)
mkPolar = (Exp a -> Exp a -> Complex (Exp a))
-> Exp (Plain (Exp a))
-> Exp (Plain (Exp a))
-> Exp (Plain (Complex (Exp a)))
forall a b c.
(Unlift Exp a, Unlift Exp b, Lift Exp c) =>
(a -> b -> c) -> Exp (Plain a) -> Exp (Plain b) -> Exp (Plain c)
lift2 (Exp a -> Exp a -> Complex (Exp a)
forall a. Floating a => a -> a -> Complex a
C.mkPolar :: Exp a -> Exp a -> Complex (Exp a))

-- | @'cis' t@ is a complex value with magnitude @1@ and phase @t@ (modulo
-- @2*'pi'@).
--
cis :: forall a. Floating a => Exp a -> Exp (Complex a)
cis :: Exp a -> Exp (Complex a)
cis = (Exp a -> Complex (Exp a))
-> Exp (Plain (Exp a)) -> Exp (Plain (Complex (Exp a)))
forall a b.
(Unlift Exp a, Lift Exp b) =>
(a -> b) -> Exp (Plain a) -> Exp (Plain b)
lift1 (Exp a -> Complex (Exp a)
forall a. Floating a => a -> Complex a
C.cis :: Exp a -> Complex (Exp a))

-- | Return the real part of a complex number
--
real :: Elt a => Exp (Complex a) -> Exp a
real :: Exp (Complex a) -> Exp a
real (Exp a
r ::+ Exp a
_) = Exp a
r

-- | Return the imaginary part of a complex number
--
imag :: Elt a => Exp (Complex a) -> Exp a
imag :: Exp (Complex a) -> Exp a
imag (Exp a
_ ::+ Exp a
i) = Exp a
i

-- | Return the complex conjugate of a complex number, defined as
--
-- > conjugate(Z) = X - iY
--
conjugate :: Num a => Exp (Complex a) -> Exp (Complex a)
conjugate :: Exp (Complex a) -> Exp (Complex a)
conjugate Exp (Complex a)
z = Exp (Complex a) -> Exp a
forall a. Elt a => Exp (Complex a) -> Exp a
real Exp (Complex a)
z Exp a -> Exp a -> Exp (Complex a)
forall a. Elt a => Exp a -> Exp a -> Exp (Complex a)
::+ (- Exp (Complex a) -> Exp a
forall a. Elt a => Exp (Complex a) -> Exp a
imag Exp (Complex a)
z)