{-# LANGUAGE CPP, GeneralizedNewtypeDeriving, ScopedTypeVariables #-} {-# LANGUAGE StandaloneDeriving, TypeFamilies #-} {-# OPTIONS_GHC -Wno-orphans #-} module Algebra.Normed where import AlgebraicPrelude -- | Additional types for /normed/ types. class (Ord (Norm a)) => Normed a where type Norm a norm :: a -> Norm a liftNorm :: Norm a -> a #if defined(__GLASGOW_HASKELL__) && __GLASGOW_HASKELL__ >= 802 deriving instance Normed a => Normed (WrapNum a) deriving instance Normed a => Normed (WrapFractional a) deriving instance Normed a => Normed (WrapAlgebra a) deriving instance Normed a => Normed (WrapIntegral a) deriving instance Normed a => Normed (Add a) deriving instance Normed a => Normed (Mult a) #else instance Normed a => Normed (WrapNum a) where type Norm (WrapNum a) = Norm a norm = norm . unwrapNum liftNorm = WrapNum . liftNorm instance Normed a => Normed (WrapFractional a) where type Norm (WrapFractional a) = Norm a norm = norm . unwrapFractional liftNorm = WrapFractional . liftNorm instance Normed a => Normed (WrapAlgebra a) where type Norm (WrapAlgebra a) = Norm a norm = norm . unwrapAlgebra liftNorm = WrapAlgebra . liftNorm instance Normed a => Normed (WrapIntegral a) where type Norm (WrapIntegral a) = Norm a norm = norm . unwrapIntegral liftNorm = WrapIntegral . liftNorm instance Normed a => Normed (Add a) where type Norm (Add a) = Norm a norm = norm . runAdd liftNorm = Add . liftNorm instance Normed a => Normed (Mult a) where type Norm (Mult a) = Norm a norm = norm . runMult liftNorm = Mult . liftNorm #endif instance Normed Double where type Norm Double = Double norm :: Double -> Norm Double norm = Double -> Norm Double forall a. Num a => a -> a abs liftNorm :: Norm Double -> Double liftNorm = Norm Double -> Double forall a. a -> a id instance Normed Int where type Norm Int = Int norm :: Int -> Norm Int norm = Int -> Norm Int forall a. Num a => a -> a abs liftNorm :: Norm Int -> Int liftNorm = Norm Int -> Int forall a. a -> a id instance Normed Integer where type Norm Integer = Integer norm :: Integer -> Norm Integer norm = Integer -> Norm Integer forall a. Num a => a -> a abs liftNorm :: Norm Integer -> Integer liftNorm = Norm Integer -> Integer forall a. a -> a id instance (Ord (Norm d), Euclidean d, Euclidean (Norm d), Normed d) => Normed (Fraction d) where type Norm (Fraction d) = Fraction (Norm d) norm :: Fraction d -> Norm (Fraction d) norm Fraction d f = d -> Norm d forall a. Normed a => a -> Norm a norm (Fraction d -> d forall t. Fraction t -> t numerator Fraction d f) Norm d -> Norm d -> Fraction (Norm d) forall d. GCDDomain d => d -> d -> Fraction d % d -> Norm d forall a. Normed a => a -> Norm a norm (Fraction d -> d forall t. Fraction t -> t denominator Fraction d f) liftNorm :: Norm (Fraction d) -> Fraction d liftNorm Norm (Fraction d) f = Norm d -> d forall a. Normed a => Norm a -> a liftNorm (Fraction (Norm d) -> Norm d forall t. Fraction t -> t numerator Fraction (Norm d) Norm (Fraction d) f) d -> d -> Fraction d forall d. GCDDomain d => d -> d -> Fraction d % Norm d -> d forall a. Normed a => Norm a -> a liftNorm (Fraction (Norm d) -> Norm d forall t. Fraction t -> t denominator Fraction (Norm d) Norm (Fraction d) f) {-# ANN module "Hlint: ignore Unused LANGUAGE pragma" #-}