-- Hoogle documentation, generated by Haddock -- See Hoogle, http://www.haskell.org/hoogle/ -- | Generic random generators for QuickCheck -- -- Derive instances of Arbitrary for QuickCheck, with various -- options to customize implementations. -- -- For more information -- -- @package generic-random @version 1.3.0.1 -- | Core implementation. -- --

Warning

-- -- This is an internal module: it is not subject to any versioning -- policy, breaking changes can happen at any time. -- -- If something here seems useful, please report it or create a pull -- request to export it from an external module. module Generic.Random.Internal.Generic -- | Pick a constructor with a given distribution, and fill its fields with -- recursive calls to arbitrary. -- --

Example

-- --
--   genericArbitrary (2 % 3 % 5 % ()) :: Gen a
--   
-- -- Picks the first constructor with probability 2/10, the second -- with probability 3/10, the third with probability -- 5/10. genericArbitrary :: GArbitrary UnsizedOpts a => Weights a -> Gen a -- | Pick every constructor with equal probability. Equivalent to -- genericArbitrary uniform. -- --
--   genericArbitraryU :: Gen a
--   
genericArbitraryU :: (GArbitrary UnsizedOpts a, GUniformWeight a) => Gen a -- | arbitrary for types with one constructor. Equivalent to -- genericArbitraryU, with a stricter type. -- --
--   genericArbitrarySingle :: Gen a
--   
genericArbitrarySingle :: (GArbitrary UnsizedOpts a, Weights_ (Rep a) ~ L c0) => Gen a -- | Decrease size at every recursive call, but don't do anything different -- at size 0. -- --
--   genericArbitraryRec (7 % 11 % 13 % ()) :: Gen a
--   
-- -- N.B.: This replaces the generator for fields of type [t] with -- listOf' arbitrary instead of listOf -- arbitrary (i.e., arbitrary for lists). genericArbitraryRec :: GArbitrary SizedOptsDef a => Weights a -> Gen a -- | genericArbitrary with explicit generators. -- --

Example

-- --
--   genericArbitraryG customGens (17 % 19 % ())
--   
-- -- where, for example to override generators for String and -- Int fields, -- --
--   customGens :: Gen String :+ Gen Int
--   customGens =
--     (filter (/= '\NUL') <$> arbitrary) :+
--     (getNonNegative <$> arbitrary)
--   
-- --

Note on multiple matches

-- -- If the list contains multiple matching types for a field x of -- type a (i.e., either Gen a or FieldGen -- "x" a), the generator for the first match will be picked. genericArbitraryG :: GArbitrary (SetGens genList UnsizedOpts) a => genList -> Weights a -> Gen a -- | genericArbitraryU with explicit generators. See also -- genericArbitraryG. genericArbitraryUG :: (GArbitrary (SetGens genList UnsizedOpts) a, GUniformWeight a) => genList -> Gen a -- | genericArbitrarySingle with explicit generators. See also -- genericArbitraryG. genericArbitrarySingleG :: (GArbitrary (SetGens genList UnsizedOpts) a, Weights_ (Rep a) ~ L c0) => genList -> Gen a -- | genericArbitraryRec with explicit generators. See also -- genericArbitraryG. genericArbitraryRecG :: GArbitrary (SetGens genList SizedOpts) a => genList -> Weights a -> Gen a -- | General generic generator with custom options. genericArbitraryWith :: GArbitrary opts a => opts -> Weights a -> Gen a type family Weights_ (f :: Type -> Type) :: Type data a :| b N :: a -> Int -> b -> (:|) a b data L (c :: Symbol) L :: L -- | Trees of weights assigned to constructors of type a, rescaled -- to obtain a probability distribution. -- -- Two ways of constructing them. -- --
--   (x1 % x2 % ... % xn % ()) :: Weights a
--   uniform :: Weights a
--   
-- -- Using (%), there must be exactly as many weights as -- there are constructors. -- -- uniform is equivalent to (1 % ... % 1 -- % ()) (automatically fills out the right number of 1s). data Weights a Weights :: Weights_ (Rep a) -> Int -> Weights a -- | Type of a single weight, tagged with the name of the associated -- constructor for additional compile-time checking. -- --
--   ((9 :: W "Leaf") % (8 :: W "Node") % ())
--   
-- -- Note: these annotations are only checked on GHC 8.0 or newer. They are -- ignored on older GHCs. newtype W (c :: Symbol) W :: Int -> W -- | A smart constructor to specify a custom distribution. It can be -- omitted for the % operator is overloaded to insert it. weights :: (Weights_ (Rep a), Int, ()) -> Weights a -- | Uniform distribution. uniform :: UniformWeight_ (Rep a) => Weights a type family First a :: Symbol type family First' w type family Prec' w -- | A synonym for (~), except on GHC 7.10 and older, where it's -- the trivial constraint. See note on W. class (a ~ b) => a ~. b class WeightBuilder' w -- | A binary constructor for building up trees of weights. (%) :: (WeightBuilder' w, c ~. First' w) => W c -> Prec' w -> w infixr 1 % class WeightBuilder a where { type family Prec a r; } (%.) :: (WeightBuilder a, c ~. First a) => W c -> Prec a r -> (a, Int, r) class UniformWeight a uniformWeight :: UniformWeight a => (a, Int) class UniformWeight (Weights_ f) => UniformWeight_ f -- | Derived uniform distribution of constructors for a. class UniformWeight_ (Rep a) => GUniformWeight a -- | Type-level options for GArbitrary. newtype Options (s :: Sizing) (genList :: Type) Options :: genList -> Options [_generators] :: Options -> genList -- | Default options for unsized generators. unsizedOpts :: UnsizedOpts -- | Default options for sized generators. sizedOpts :: SizedOpts -- | Default options overriding the list generator using listOf'. sizedOptsDef :: SizedOptsDef -- | Whether to decrease the size parameter before generating fields. data Sizing Sized :: Sizing Unsized :: Sizing type UnsizedOpts = Options 'Unsized () type SizedOpts = Options 'Sized () type SizedOptsDef = Options 'Sized (Gen1 [] :+ ()) type family SizingOf opts :: Sizing setSized :: Options s g -> Options 'Sized g setUnsized :: Options s g -> Options 'Unsized g -- | Heterogeneous list of generators. data a :+ b (:+) :: a -> b -> (:+) a b infixr 1 :+ infixr 1 :+ type family GeneratorsOf opts :: Type class HasGenerators opts generators :: HasGenerators opts => opts -> GeneratorsOf opts setGenerators :: genList -> Options s g0 -> Options s genList type family SetGens (g :: Type) opts -- | Custom generator for record fields named s. -- -- Available only for base >= 4.9 (GHC >= -- 8.0.1). newtype FieldGen (s :: Symbol) a FieldGen :: Gen a -> FieldGen a [unFieldGen] :: FieldGen a -> Gen a -- | FieldGen constructor with the field name given via a proxy. fieldGen :: proxy s -> Gen a -> FieldGen s a -- | Custom generator for the i-th field of the constructor named -- c. -- -- Available only for base >= 4.9 (GHC >= -- 8.0.1). newtype ConstrGen (c :: Symbol) (i :: Nat) a ConstrGen :: Gen a -> ConstrGen a [unConstrGen] :: ConstrGen a -> Gen a -- | ConstrGen constructor with the constructor name given via a -- proxy. constrGen :: proxy '(c, i) -> Gen a -> ConstrGen c i a -- | Custom generators for "containers" of kind Type -> Type, -- parameterized by the generator for "contained elements". -- -- A custom generator Gen1 f will be used for any field -- whose type has the form f x, requiring a generator of -- x. newtype Gen1 f Gen1 :: (forall a. Gen a -> Gen (f a)) -> Gen1 f [unGen1] :: Gen1 f -> forall a. Gen a -> Gen (f a) -- | Custom generators for unary type constructors that are not -- "containers", i.e., which don't require a generator of a to -- generate an f a. -- -- A custom generator Gen1_ f will be used for any field -- whose type has the form f x. newtype Gen1_ f Gen1_ :: (forall a. Gen (f a)) -> Gen1_ f [unGen1_] :: Gen1_ f -> forall a. Gen (f a) -- | An alternative to vectorOf that divides the size parameter by -- the length of the list. vectorOf' :: Int -> Gen a -> Gen [a] -- | An alternative to listOf that divides the size parameter by the -- length of the list. The length follows a geometric distribution of -- parameter 1/(sqrt size + 1). listOf' :: Gen a -> Gen [a] -- | An alternative to listOf1 (nonempty lists) that divides the -- size parameter by the length of the list. The length (minus one) -- follows a geometric distribution of parameter 1/(sqrt size + -- 1). listOf1' :: Gen a -> Gen [a] -- | Geometric distribution of parameter 1/(sqrt n + 1) (n -- >= 0). geom :: Int -> Gen Int -- | Generic Arbitrary class GA opts f ga :: GA opts f => opts -> Weights_ f -> Int -> Gen (f p) -- | Generic Arbitrary class (Generic a, GA opts (Rep a)) => GArbitrary opts a gaSum' :: GASum opts f => opts -> Weights_ f -> Int -> Gen (f p) class GASum opts f gaSum :: GASum opts f => opts -> Int -> Weights_ f -> Gen (f p) class GAProduct (s :: Sizing) (c :: Maybe Symbol) opts f gaProduct :: GAProduct s c opts f => proxys '(s, c) -> opts -> Gen (f p) class GAProduct' (c :: Maybe Symbol) (i :: Nat) opts f gaProduct' :: GAProduct' c i opts f => proxy '(c, i) -> opts -> Gen (f p) type family Arity f :: Nat -- | Given a list of custom generators gs, find one that applies, -- or use Arbitrary a by default. -- -- g and gs follow this little state machine: -- --
--             g,      gs | result
--   ---------------------+-----------------------------
--            (),      () | END
--            (), g :+ gs | g, gs
--            (),      g  | g, () when g is not (_ :+ _)
--        g :+ h,      gs | g, h :+ gs
--         Gen a,      gs | END if matching, else (), gs
--    FieldGen a,      gs | idem
--   ConstrGen a,      gs | idem
--        Gen1 a,      gs | idem
--       Gen1_ a,      gs | idem
--   
class ArbitraryOr (fullGenList :: Type) (g :: Type) (gs :: Type) (sel :: (Maybe Symbol, Nat, Maybe Symbol)) a arbitraryOr :: ArbitraryOr fullGenList g gs sel a => proxy sel -> fullGenList -> g -> gs -> Gen a -- | Get the name contained in a Meta tag. type family Name (d :: Meta) :: Maybe Symbol newtype Weighted a Weighted :: Maybe (Int -> Gen a, Int) -> Weighted a liftGen :: Gen a -> Weighted a instance GHC.Base.Functor Generic.Random.Internal.Generic.Weighted instance GHC.Num.Num (Generic.Random.Internal.Generic.W c) instance GHC.Base.Applicative Generic.Random.Internal.Generic.Weighted instance GHC.Base.Alternative Generic.Random.Internal.Generic.Weighted instance Generic.Random.Internal.Generic.GAProduct (Generic.Random.Internal.Generic.SizingOf opts) (Generic.Random.Internal.Generic.Name c) opts f => Generic.Random.Internal.Generic.GA opts (GHC.Generics.M1 GHC.Generics.C c f) instance Generic.Random.Internal.Generic.GAProduct (Generic.Random.Internal.Generic.SizingOf opts) (Generic.Random.Internal.Generic.Name c) opts f => Generic.Random.Internal.Generic.GASum opts (GHC.Generics.M1 GHC.Generics.C c f) instance (Generic.Random.Internal.Generic.HasGenerators opts, Generic.Random.Internal.Generic.ArbitraryOr gs () gs '(c, i, Generic.Random.Internal.Generic.Name d) a, gs Data.Type.Equality.~ Generic.Random.Internal.Generic.GeneratorsOf opts) => Generic.Random.Internal.Generic.GAProduct' c i opts (GHC.Generics.S1 d (GHC.Generics.K1 _k a)) instance Test.QuickCheck.Arbitrary.Arbitrary a => Generic.Random.Internal.Generic.ArbitraryOr fg () () sel a instance Generic.Random.Internal.Generic.ArbitraryOr fg b g sel a => Generic.Random.Internal.Generic.ArbitraryOr fg () (b Generic.Random.Internal.Generic.:+ g) sel a instance Generic.Random.Internal.Generic.ArbitraryOr fg g () sel a => Generic.Random.Internal.Generic.ArbitraryOr fg () g sel a instance Generic.Random.Internal.Generic.ArbitraryOr fg g (h Generic.Random.Internal.Generic.:+ gs) sel a => Generic.Random.Internal.Generic.ArbitraryOr fg (g Generic.Random.Internal.Generic.:+ h) gs sel a instance Generic.Random.Internal.Generic.ArbitraryOr fg () gs sel a => Generic.Random.Internal.Generic.ArbitraryOr fg g gs sel a instance Generic.Random.Internal.Generic.ArbitraryOr fg (Test.QuickCheck.Gen.Gen a) g sel a instance (a Data.Type.Equality.~ a') => Generic.Random.Internal.Generic.ArbitraryOr fg (Generic.Random.Internal.Generic.FieldGen s a) g '(con, i, 'GHC.Maybe.Just s) a' instance (a Data.Type.Equality.~ a') => Generic.Random.Internal.Generic.ArbitraryOr fg (Generic.Random.Internal.Generic.ConstrGen c i a) g '( 'GHC.Maybe.Just c, i, s) a' instance forall k fg (f :: k -> *) g (sel :: (GHC.Maybe.Maybe GHC.Types.Symbol, GHC.Types.Nat, GHC.Maybe.Maybe GHC.Types.Symbol)) (a :: k). Generic.Random.Internal.Generic.ArbitraryOr fg (Generic.Random.Internal.Generic.Gen1_ f) g sel (f a) instance Generic.Random.Internal.Generic.ArbitraryOr fg () fg '( 'GHC.Maybe.Nothing, 0, 'GHC.Maybe.Nothing) a => Generic.Random.Internal.Generic.ArbitraryOr fg (Generic.Random.Internal.Generic.Gen1 f) g sel (f a) instance forall k (c :: GHC.Maybe.Maybe GHC.Types.Symbol) opts (f :: k -> *). (Generic.Random.Internal.Generic.GAProduct' c 0 opts f, GHC.TypeNats.KnownNat (Generic.Random.Internal.Generic.Arity f)) => Generic.Random.Internal.Generic.GAProduct 'Generic.Random.Internal.Generic.Sized c opts f instance forall k (c :: GHC.Maybe.Maybe GHC.Types.Symbol) (i :: GHC.Types.Nat) opts (f :: k -> *) (g :: k -> *). (Generic.Random.Internal.Generic.GAProduct' c i opts f, Generic.Random.Internal.Generic.GAProduct' c (i GHC.TypeNats.+ Generic.Random.Internal.Generic.Arity f) opts g) => Generic.Random.Internal.Generic.GAProduct' c i opts (f GHC.Generics.:*: g) instance forall k (c :: GHC.Maybe.Maybe GHC.Types.Symbol) opts (f :: k -> *). Generic.Random.Internal.Generic.GAProduct' c 0 opts f => Generic.Random.Internal.Generic.GAProduct 'Generic.Random.Internal.Generic.Unsized c opts f instance forall k (c :: GHC.Maybe.Maybe GHC.Types.Symbol) opts (d :: GHC.Generics.Meta) (f :: k -> *). Generic.Random.Internal.Generic.GAProduct' c 0 opts (GHC.Generics.S1 d f) => Generic.Random.Internal.Generic.GAProduct 'Generic.Random.Internal.Generic.Sized c opts (GHC.Generics.S1 d f) instance Generic.Random.Internal.Generic.GAProduct' c i opts GHC.Generics.U1 instance Generic.Random.Internal.Generic.GAProduct 'Generic.Random.Internal.Generic.Sized c opts GHC.Generics.U1 instance (Generic.Random.Internal.Generic.GASum opts f, Generic.Random.Internal.Generic.GASum opts g) => Generic.Random.Internal.Generic.GA opts (f GHC.Generics.:+: g) instance (Generic.Random.Internal.Generic.GASum opts f, Generic.Random.Internal.Generic.GASum opts g) => Generic.Random.Internal.Generic.GASum opts (f GHC.Generics.:+: g) instance (GHC.Generics.Generic a, Generic.Random.Internal.Generic.GA opts (GHC.Generics.Rep a)) => Generic.Random.Internal.Generic.GArbitrary opts a instance Generic.Random.Internal.Generic.GA opts f => Generic.Random.Internal.Generic.GA opts (GHC.Generics.M1 GHC.Generics.D c f) instance Generic.Random.Internal.Generic.HasGenerators (Generic.Random.Internal.Generic.Options s g) instance Generic.Random.Internal.Generic.UniformWeight_ (GHC.Generics.Rep a) => Generic.Random.Internal.Generic.GUniformWeight a instance Generic.Random.Internal.Generic.UniformWeight (Generic.Random.Internal.Generic.Weights_ f) => Generic.Random.Internal.Generic.UniformWeight_ f instance (Generic.Random.Internal.Generic.UniformWeight a, Generic.Random.Internal.Generic.UniformWeight b) => Generic.Random.Internal.Generic.UniformWeight (a Generic.Random.Internal.Generic.:| b) instance Generic.Random.Internal.Generic.UniformWeight (Generic.Random.Internal.Generic.L c) instance Generic.Random.Internal.Generic.UniformWeight () instance Generic.Random.Internal.Generic.WeightBuilder (Generic.Random.Internal.Generic.Weights_ (GHC.Generics.Rep a)) => Generic.Random.Internal.Generic.WeightBuilder' (Generic.Random.Internal.Generic.Weights a) instance Generic.Random.Internal.Generic.WeightBuilder a => Generic.Random.Internal.Generic.WeightBuilder' (a, GHC.Types.Int, r) instance Generic.Random.Internal.Generic.WeightBuilder a => Generic.Random.Internal.Generic.WeightBuilder (a Generic.Random.Internal.Generic.:| b) instance Generic.Random.Internal.Generic.WeightBuilder (Generic.Random.Internal.Generic.L c) instance Generic.Random.Internal.Generic.WeightBuilder () instance forall k (a :: k) (b :: k). (a Data.Type.Equality.~ b) => a Generic.Random.Internal.Generic.~. b -- | Base case discovery. -- --

Warning

-- -- This is an internal module: it is not subject to any versioning -- policy, breaking changes can happen at any time. -- -- If something here seems useful, please report it or create a pull -- request to export it from an external module. module Generic.Random.Internal.BaseCase -- | Decrease size to ensure termination for recursive types, looking for -- base cases once the size reaches 0. -- --
--   genericArbitrary' (17 % 19 % 23 % ()) :: Gen a
--   
-- -- N.B.: This replaces the generator for fields of type [t] with -- listOf' arbitrary instead of listOf -- arbitrary (i.e., arbitrary for lists). genericArbitrary' :: (GArbitrary SizedOptsDef a, BaseCase a) => Weights a -> Gen a -- | Equivalent to genericArbitrary' uniform. -- --
--   genericArbitraryU' :: Gen a
--   
-- -- N.B.: This replaces the generator for fields of type [t] with -- listOf' arbitrary instead of listOf -- arbitrary (i.e., arbitrary for lists). genericArbitraryU' :: (GArbitrary SizedOptsDef a, BaseCase a, GUniformWeight a) => Gen a -- | Run the first generator if the size is positive. Run the second if the -- size is zero. -- --
--   defaultGen `withBaseCase` baseCaseGen
--   
withBaseCase :: Gen a -> Gen a -> Gen a -- | Find a base case of type a with maximum depth z, -- recursively using BaseCaseSearch instances to search deeper -- levels. -- -- y is the depth of a base case, if found. -- -- e is the original type the search started with, that -- a appears in. It is used for error reporting. class BaseCaseSearch (a :: *) (z :: Nat) (y :: Maybe Nat) (e :: *) baseCaseSearch :: BaseCaseSearch a z y e => prox y -> proxy '(z, e) -> IfM y Gen Proxy a class BaseCaseSearching_ a z y baseCaseSearching_ :: BaseCaseSearching_ a z y => proxy y -> proxy2 '(z, a) -> IfM y Gen Proxy a -> Gen a -- | Progressively increase the depth bound for BaseCaseSearch. class BaseCaseSearching a z baseCaseSearching :: BaseCaseSearching a z => proxy '(z, a) -> Gen a -- | Custom instances can override the default behavior. class BaseCase a -- | Generator of base cases. baseCase :: BaseCase a => Gen a type family IfM (b :: Maybe t) (c :: k) (d :: k) :: k type (==) m n = IsEQ (CmpNat m n) type family IsEQ (e :: Ordering) :: Bool type family (||?) (b :: Maybe Nat) (c :: Maybe Nat) :: Maybe Nat type family (&&?) (b :: Maybe Nat) (c :: Maybe Nat) :: Maybe Nat type Max m n = MaxOf (CmpNat m n) m n type family MaxOf (e :: Ordering) (m :: k) (n :: k) :: k type Min m n = MinOf (CmpNat m n) m n type family MinOf (e :: Ordering) (m :: k) (n :: k) :: k class Alternative (IfM y Weighted Proxy) => GBCS (f :: k -> *) (z :: Nat) (y :: Maybe Nat) (e :: *) gbcs :: GBCS f z y e => prox y -> proxy '(z, e) -> IfM y Weighted Proxy (f p) class Alternative (IfM (yf ||? yg) Weighted Proxy) => GBCSSum f g z e yf yg gbcsSum :: GBCSSum f g z e yf yg => prox '(yf, yg) -> proxy '(z, e) -> IfM yf Weighted Proxy (f p) -> IfM yg Weighted Proxy (g p) -> IfM (yf ||? yg) Weighted Proxy ((f :+: g) p) class GBCSSumCompare f g z e o gbcsSumCompare :: GBCSSumCompare f g z e o => proxy0 o -> proxy '(z, e) -> Weighted (f p) -> Weighted (g p) -> Weighted ((f :+: g) p) class Alternative (IfM (yf &&? yg) Weighted Proxy) => GBCSProduct f g z e yf yg gbcsProduct :: GBCSProduct f g z e yf yg => prox '(yf, yg) -> proxy '(z, e) -> IfM yf Weighted Proxy (f p) -> IfM yg Weighted Proxy (g p) -> IfM (yf &&? yg) Weighted Proxy ((f :*: g) p) class IsMaybe b ifMmap :: IsMaybe b => proxy b -> (c a -> c' a') -> (d a -> d' a') -> IfM b c d a -> IfM b c' d' a' ifM :: IsMaybe b => proxy b -> c a -> d a -> IfM b c d a class GBaseCaseSearch a z y e gBaseCaseSearch :: GBaseCaseSearch a z y e => prox y -> proxy '(z, e) -> IfM y Gen Proxy a instance Generic.Random.Internal.BaseCase.GBaseCaseSearch a z y e => Generic.Random.Internal.BaseCase.BaseCaseSearch a z y e instance (GHC.Generics.Generic a, Generic.Random.Internal.BaseCase.GBCS (GHC.Generics.Rep a) z y e, Generic.Random.Internal.BaseCase.IsMaybe y) => Generic.Random.Internal.BaseCase.GBaseCaseSearch a z y e instance forall t1 (t2 :: t1). Generic.Random.Internal.BaseCase.IsMaybe ('GHC.Maybe.Just t2) instance Generic.Random.Internal.BaseCase.IsMaybe 'GHC.Maybe.Nothing instance (Generic.Random.Internal.BaseCase.BaseCaseSearch c (z GHC.TypeNats.- 1) y e, (z Generic.Random.Internal.BaseCase.== 0) Data.Type.Equality.~ 'GHC.Types.False, GHC.Base.Alternative (Generic.Random.Internal.BaseCase.IfM y Generic.Random.Internal.Generic.Weighted Data.Proxy.Proxy), Generic.Random.Internal.BaseCase.IsMaybe y) => Generic.Random.Internal.BaseCase.GBCS (GHC.Generics.K1 i c) z y e instance forall k (f :: k -> *) (g :: k -> *) (z :: GHC.Types.Nat) e (yf :: GHC.Maybe.Maybe GHC.Types.Nat) (yg :: GHC.Maybe.Maybe GHC.Types.Nat) (y :: GHC.Maybe.Maybe GHC.Types.Nat). (Generic.Random.Internal.BaseCase.GBCSProduct f g z e yf yg, Generic.Random.Internal.BaseCase.GBCS f z yf e, Generic.Random.Internal.BaseCase.GBCS g z yg e, y Data.Type.Equality.~ (yf Generic.Random.Internal.BaseCase.&&? yg)) => Generic.Random.Internal.BaseCase.GBCS (f GHC.Generics.:*: g) z y e instance forall k1 k2 k3 (yf :: GHC.Maybe.Maybe GHC.Types.Nat) (yg :: GHC.Maybe.Maybe GHC.Types.Nat) (f :: k3 -> *) (g :: k3 -> *) (z :: k2) (e :: k1). ((yf Generic.Random.Internal.BaseCase.&&? yg) Data.Type.Equality.~ 'GHC.Maybe.Nothing) => Generic.Random.Internal.BaseCase.GBCSProduct f g z e yf yg instance forall k1 k2 k3 (f :: k3 -> *) (g :: k3 -> *) (z :: k2) (e :: k1) (m :: GHC.Types.Nat) (n :: GHC.Types.Nat). Generic.Random.Internal.BaseCase.GBCSProduct f g z e ('GHC.Maybe.Just m) ('GHC.Maybe.Just n) instance forall k1 k2 k3 (f :: k3 -> *) (g :: k3 -> *) (z :: k2) (e :: k1) (m :: GHC.Types.Nat) (n :: GHC.Types.Nat). Generic.Random.Internal.BaseCase.GBCSSumCompare f g z e (GHC.TypeNats.CmpNat m n) => Generic.Random.Internal.BaseCase.GBCSSum f g z e ('GHC.Maybe.Just m) ('GHC.Maybe.Just n) instance forall k1 k2 k3 (f :: k3 -> *) (g :: k3 -> *) (z :: k2) (e :: k1). Generic.Random.Internal.BaseCase.GBCSSumCompare f g z e 'GHC.Types.EQ instance forall k1 k2 k3 (f :: k3 -> *) (g :: k3 -> *) (z :: k2) (e :: k1). Generic.Random.Internal.BaseCase.GBCSSumCompare f g z e 'GHC.Types.LT instance forall k1 k2 k3 (f :: k3 -> *) (g :: k3 -> *) (z :: k2) (e :: k1). Generic.Random.Internal.BaseCase.GBCSSumCompare f g z e 'GHC.Types.GT instance forall k (f :: k -> *) (g :: k -> *) (z :: GHC.Types.Nat) e (yf :: GHC.Maybe.Maybe GHC.Types.Nat) (yg :: GHC.Maybe.Maybe GHC.Types.Nat) (y :: GHC.Maybe.Maybe GHC.Types.Nat). (Generic.Random.Internal.BaseCase.GBCSSum f g z e yf yg, Generic.Random.Internal.BaseCase.GBCS f z yf e, Generic.Random.Internal.BaseCase.GBCS g z yg e, y Data.Type.Equality.~ (yf Generic.Random.Internal.BaseCase.||? yg)) => Generic.Random.Internal.BaseCase.GBCS (f GHC.Generics.:+: g) z y e instance forall k1 k2 k3 (f :: k3 -> *) (g :: k3 -> *) (z :: k2) (e :: k1). Generic.Random.Internal.BaseCase.GBCSSum f g z e 'GHC.Maybe.Nothing 'GHC.Maybe.Nothing instance forall k1 k2 k3 (f :: k3 -> *) (g :: k3 -> *) (z :: k2) (e :: k1) (m :: GHC.Types.Nat). Generic.Random.Internal.BaseCase.GBCSSum f g z e ('GHC.Maybe.Just m) 'GHC.Maybe.Nothing instance forall k1 k2 k3 (f :: k3 -> *) (g :: k3 -> *) (z :: k2) (e :: k1) (n :: GHC.Types.Nat). Generic.Random.Internal.BaseCase.GBCSSum f g z e 'GHC.Maybe.Nothing ('GHC.Maybe.Just n) instance forall k (f :: k -> *) (z :: GHC.Types.Nat) (y :: GHC.Maybe.Maybe GHC.Types.Nat) e i (c :: GHC.Generics.Meta). Generic.Random.Internal.BaseCase.GBCS f z y e => Generic.Random.Internal.BaseCase.GBCS (GHC.Generics.M1 i c f) z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Nothing) => Generic.Random.Internal.BaseCase.GBCS (GHC.Generics.K1 i c) 0 y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.GBCS GHC.Generics.U1 z y e instance forall k (f :: k -> *) e (y :: GHC.Maybe.Maybe GHC.Types.Nat) (z :: GHC.Types.Nat). ((TypeError ...), GHC.Base.Alternative (Generic.Random.Internal.BaseCase.IfM y Generic.Random.Internal.Generic.Weighted Data.Proxy.Proxy)) => Generic.Random.Internal.BaseCase.GBCS f z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch GHC.Types.Char z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch GHC.Types.Int z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch GHC.Integer.Type.Integer z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch GHC.Types.Float z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch GHC.Types.Double z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch GHC.Types.Word z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch () z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch GHC.Types.Bool z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch [a] z y e instance (y Data.Type.Equality.~ 'GHC.Maybe.Just 0) => Generic.Random.Internal.BaseCase.BaseCaseSearch GHC.Types.Ordering z y e instance (Generic.Random.Internal.BaseCase.BaseCaseSearch a z y a, Generic.Random.Internal.BaseCase.BaseCaseSearching_ a z y) => Generic.Random.Internal.BaseCase.BaseCaseSearching a z instance forall t k a (z :: k) (m :: t). Generic.Random.Internal.BaseCase.BaseCaseSearching_ a z ('GHC.Maybe.Just m) instance Generic.Random.Internal.BaseCase.BaseCaseSearching a (z GHC.TypeNats.+ 1) => Generic.Random.Internal.BaseCase.BaseCaseSearching_ a z 'GHC.Maybe.Nothing instance Generic.Random.Internal.BaseCase.BaseCaseSearching a 0 => Generic.Random.Internal.BaseCase.BaseCase a -- | GHC.Generics-based arbitrary generators. -- --

Basic usage

-- --
--   data Foo = A | B | C  -- some generic data type
--     deriving Generic
--   
-- -- Derive instances of Arbitrary. -- --
--   instance Arbitrary Foo where
--     arbitrary = genericArbitrary uniform  -- give a distribution of constructors
--   
-- -- Or derive standalone generators (the fields must still be instances of -- Arbitrary, or use custom generators). -- --
--   genFoo :: Gen Foo
--   genFoo = genericArbitrary uniform
--   
-- -- For more information: -- -- module Generic.Random -- | Pick a constructor with a given distribution, and fill its fields with -- recursive calls to arbitrary. -- --

Example

-- --
--   genericArbitrary (2 % 3 % 5 % ()) :: Gen a
--   
-- -- Picks the first constructor with probability 2/10, the second -- with probability 3/10, the third with probability -- 5/10. genericArbitrary :: GArbitrary UnsizedOpts a => Weights a -> Gen a -- | Pick every constructor with equal probability. Equivalent to -- genericArbitrary uniform. -- --
--   genericArbitraryU :: Gen a
--   
genericArbitraryU :: (GArbitrary UnsizedOpts a, GUniformWeight a) => Gen a -- | arbitrary for types with one constructor. Equivalent to -- genericArbitraryU, with a stricter type. -- --
--   genericArbitrarySingle :: Gen a
--   
genericArbitrarySingle :: (GArbitrary UnsizedOpts a, Weights_ (Rep a) ~ L c0) => Gen a -- | Decrease size at every recursive call, but don't do anything different -- at size 0. -- --
--   genericArbitraryRec (7 % 11 % 13 % ()) :: Gen a
--   
-- -- N.B.: This replaces the generator for fields of type [t] with -- listOf' arbitrary instead of listOf -- arbitrary (i.e., arbitrary for lists). genericArbitraryRec :: GArbitrary SizedOptsDef a => Weights a -> Gen a -- | Decrease size to ensure termination for recursive types, looking for -- base cases once the size reaches 0. -- --
--   genericArbitrary' (17 % 19 % 23 % ()) :: Gen a
--   
-- -- N.B.: This replaces the generator for fields of type [t] with -- listOf' arbitrary instead of listOf -- arbitrary (i.e., arbitrary for lists). genericArbitrary' :: (GArbitrary SizedOptsDef a, BaseCase a) => Weights a -> Gen a -- | Equivalent to genericArbitrary' uniform. -- --
--   genericArbitraryU' :: Gen a
--   
-- -- N.B.: This replaces the generator for fields of type [t] with -- listOf' arbitrary instead of listOf -- arbitrary (i.e., arbitrary for lists). genericArbitraryU' :: (GArbitrary SizedOptsDef a, BaseCase a, GUniformWeight a) => Gen a -- | genericArbitrary with explicit generators. -- --

Example

-- --
--   genericArbitraryG customGens (17 % 19 % ())
--   
-- -- where, for example to override generators for String and -- Int fields, -- --
--   customGens :: Gen String :+ Gen Int
--   customGens =
--     (filter (/= '\NUL') <$> arbitrary) :+
--     (getNonNegative <$> arbitrary)
--   
-- --

Note on multiple matches

-- -- If the list contains multiple matching types for a field x of -- type a (i.e., either Gen a or FieldGen -- "x" a), the generator for the first match will be picked. genericArbitraryG :: GArbitrary (SetGens genList UnsizedOpts) a => genList -> Weights a -> Gen a -- | genericArbitraryU with explicit generators. See also -- genericArbitraryG. genericArbitraryUG :: (GArbitrary (SetGens genList UnsizedOpts) a, GUniformWeight a) => genList -> Gen a -- | genericArbitrarySingle with explicit generators. See also -- genericArbitraryG. genericArbitrarySingleG :: (GArbitrary (SetGens genList UnsizedOpts) a, Weights_ (Rep a) ~ L c0) => genList -> Gen a -- | genericArbitraryRec with explicit generators. See also -- genericArbitraryG. genericArbitraryRecG :: GArbitrary (SetGens genList SizedOpts) a => genList -> Weights a -> Gen a -- | Trees of weights assigned to constructors of type a, rescaled -- to obtain a probability distribution. -- -- Two ways of constructing them. -- --
--   (x1 % x2 % ... % xn % ()) :: Weights a
--   uniform :: Weights a
--   
-- -- Using (%), there must be exactly as many weights as -- there are constructors. -- -- uniform is equivalent to (1 % ... % 1 -- % ()) (automatically fills out the right number of 1s). data Weights a -- | Type of a single weight, tagged with the name of the associated -- constructor for additional compile-time checking. -- --
--   ((9 :: W "Leaf") % (8 :: W "Node") % ())
--   
-- -- Note: these annotations are only checked on GHC 8.0 or newer. They are -- ignored on older GHCs. data W (c :: Symbol) -- | A binary constructor for building up trees of weights. (%) :: (WeightBuilder' w, c ~. First' w) => W c -> Prec' w -> w infixr 1 % -- | Uniform distribution. uniform :: UniformWeight_ (Rep a) => Weights a -- | Heterogeneous list of generators. data a :+ b (:+) :: a -> b -> (:+) a b infixr 1 :+ infixr 1 :+ -- | Custom generator for record fields named s. -- -- Available only for base >= 4.9 (GHC >= -- 8.0.1). newtype FieldGen (s :: Symbol) a FieldGen :: Gen a -> FieldGen a [unFieldGen] :: FieldGen a -> Gen a -- | FieldGen constructor with the field name given via a proxy. fieldGen :: proxy s -> Gen a -> FieldGen s a -- | Custom generator for the i-th field of the constructor named -- c. -- -- Available only for base >= 4.9 (GHC >= -- 8.0.1). newtype ConstrGen (c :: Symbol) (i :: Nat) a ConstrGen :: Gen a -> ConstrGen a [unConstrGen] :: ConstrGen a -> Gen a -- | ConstrGen constructor with the constructor name given via a -- proxy. constrGen :: proxy '(c, i) -> Gen a -> ConstrGen c i a -- | Custom generators for "containers" of kind Type -> Type, -- parameterized by the generator for "contained elements". -- -- A custom generator Gen1 f will be used for any field -- whose type has the form f x, requiring a generator of -- x. newtype Gen1 f Gen1 :: (forall a. Gen a -> Gen (f a)) -> Gen1 f [unGen1] :: Gen1 f -> forall a. Gen a -> Gen (f a) -- | Custom generators for unary type constructors that are not -- "containers", i.e., which don't require a generator of a to -- generate an f a. -- -- A custom generator Gen1_ f will be used for any field -- whose type has the form f x. newtype Gen1_ f Gen1_ :: (forall a. Gen (f a)) -> Gen1_ f [unGen1_] :: Gen1_ f -> forall a. Gen (f a) -- | An alternative to listOf that divides the size parameter by the -- length of the list. The length follows a geometric distribution of -- parameter 1/(sqrt size + 1). listOf' :: Gen a -> Gen [a] -- | An alternative to listOf1 (nonempty lists) that divides the -- size parameter by the length of the list. The length (minus one) -- follows a geometric distribution of parameter 1/(sqrt size + -- 1). listOf1' :: Gen a -> Gen [a] -- | An alternative to vectorOf that divides the size parameter by -- the length of the list. vectorOf' :: Int -> Gen a -> Gen [a] -- | Run the first generator if the size is positive. Run the second if the -- size is zero. -- --
--   defaultGen `withBaseCase` baseCaseGen
--   
withBaseCase :: Gen a -> Gen a -> Gen a -- | Custom instances can override the default behavior. class BaseCase a -- | Generator of base cases. baseCase :: BaseCase a => Gen a -- | Type-level options for GArbitrary. data Options (s :: Sizing) (genList :: Type) -- | General generic generator with custom options. genericArbitraryWith :: GArbitrary opts a => opts -> Weights a -> Gen a -- | Whether to decrease the size parameter before generating fields. data Sizing Sized :: Sizing Unsized :: Sizing setSized :: Options s g -> Options 'Sized g setUnsized :: Options s g -> Options 'Unsized g type family SetGens (g :: Type) opts setGenerators :: genList -> Options s g0 -> Options s genList type SizedOpts = Options 'Sized () -- | Default options for sized generators. sizedOpts :: SizedOpts type SizedOptsDef = Options 'Sized (Gen1 [] :+ ()) -- | Default options overriding the list generator using listOf'. sizedOptsDef :: SizedOptsDef type UnsizedOpts = Options 'Unsized () -- | Default options for unsized generators. unsizedOpts :: UnsizedOpts -- | Generic Arbitrary class (Generic a, GA opts (Rep a)) => GArbitrary opts a -- | Derived uniform distribution of constructors for a. class UniformWeight_ (Rep a) => GUniformWeight a -- | Generic implementations of QuickCheck's arbitrary. -- --

Example

-- -- Define your type. -- --
--   data Tree a = Leaf a | Node (Tree a) (Tree a)
--     deriving Generic
--   
-- -- Pick an arbitrary implementation, specifying the required -- distribution of data constructors. -- --
--   instance Arbitrary a => Arbitrary (Tree a) where
--     arbitrary = genericArbitrary (9 % 8 % ())
--   
-- -- That random generator arbitrary :: Gen (Tree a) picks -- a Leaf with probability 9/17, or a Node with -- probability 8/17, and recursively fills their fields with -- arbitrary. -- -- For Tree, the generic implementation genericArbitrary -- is equivalent to the following: -- --
--   genericArbitrary :: Arbitrary a => Weights (Tree a) -> Gen (Tree a)
--   genericArbitrary (x % y % ()) =
--     frequency
--       [ (x, Leaf <$> arbitrary)
--       , (y, Node <$> arbitrary <*> arbitrary)
--       ]
--   
-- --

Distribution of constructors

-- -- The distribution of constructors can be specified as a special list of -- weights in the same order as the data type definition. This -- assigns to each constructor a probability proportional to its weight; -- in other words, p_C = weight_C / sumOfWeights. -- -- The list of weights is built up with the (%) operator -- as a cons, and using the unit () as the empty list, in the -- order corresponding to the data type definition. -- --

Uniform distribution

-- -- You can specify the uniform distribution (all weights equal) with -- uniform. (genericArbitraryU is available as a shorthand -- for genericArbitrary uniform.) -- -- Note that for many recursive types, a uniform distribution tends to -- produce big or even infinite values. -- --

Typed weights

-- -- GHC 8.0.1 and above only (base ≥ 4.9). For compatibility, the -- annotations are still allowed on older GHC versions, but ignored. -- -- The weights actually have type W "ConstructorName" -- (just a newtype around Int), so that you can annotate a weight -- with its corresponding constructor. The constructors must appear in -- the same order as in the original type definition. -- -- This will type-check. -- --
--   ((x :: W "Leaf") % (y :: W "Node") % ()) :: Weights (Tree a)
--   ( x              % (y :: W "Node") % ()) :: Weights (Tree a)
--   
-- -- This will not. -- --
--   ((x :: W "Node") % y % ()) :: Weights (Tree a)
--   -- Requires an order of constructors different from the definition of the Tree type.
--   
--   ( x              % y % z % ()) :: Weights (Tree a)
--   -- Doesn't have the right number of weights.
--   
-- --

Ensuring termination

-- -- As mentioned earlier, one must be careful with recursive types to -- avoid producing extremely large values. The alternative generator -- genericArbitraryRec decreases the size parameter at every call -- to keep values at reasonable sizes, to be used together with -- withBaseCase. -- -- For example, we may provide a base case consisting of only -- Leaf: -- --
--   instance Arbitrary a => Arbitrary (Tree a) where
--     arbitrary = genericArbitraryRec (1 % 2 % ())
--       `withBaseCase` (Leaf <$> arbitrary)
--   
-- -- That is equivalent to the following definition. Note the resize -- modifier. -- --
--   arbitrary :: Arbitrary a => Gen (Tree a)
--   arbitrary = sized $ \n ->
--     -- "if" condition from withBaseCase
--     if n == 0 then
--       Leaf <$> arbitrary
--     else
--       -- genericArbitraryRec
--       frequency
--         [ (1, resize (max 0 (n - 1)) (Leaf <$> arbitrary))
--         , (2, resize (n `div` 2)     (Node <$> arbitrary <*> arbitrary))
--         ]
--   
-- -- The resizing strategy is as follows: the size parameter of Gen -- is divided among the fields of the chosen constructor, or decreases by -- one if the constructor is unary. withBaseCase defG -- baseG is equal to defG as long as the size parameter is -- nonzero, and it becomes baseG once the size reaches zero. -- This combination generally ensures that the number of constructors -- remains bounded by the initial size parameter passed to Gen. -- --

Automatic base case discovery

-- -- In some situations, generic-random can also construct base cases -- automatically. This works best with fully concrete types (no type -- parameters). -- --
--   {-# LANGUAGE FlexibleInstances #-}
--   
--   instance Arbitrary (Tree ()) where
--     arbitrary = genericArbitrary' (1 % 2 % ())
--   
-- -- The above instance will infer the value Leaf () as a base -- case. -- -- To discover values of type Tree a, we must inspect the type -- argument a, thus we incur some extra constraints if we want -- polymorphism. It is preferrable to apply the type class -- BaseCase to the instance head (Tree a) as follows, as -- it doesn't reduce to something worth seeing. -- --
--   {-# LANGUAGE FlexibleContexts, UndecidableInstances #-}
--   
--   instance (Arbitrary a, BaseCase (Tree a))
--     => Arbitrary (Tree a) where
--     arbitrary = genericArbitrary' (1 % 2 % ())
--   
-- -- The BaseCase type class finds values of minimal depth, where -- the depth of a constructor is defined as 1 + max(0, depths of -- fields), e.g., Leaf () has depth 2. -- --

Note about lists

-- -- The Arbitrary instance for lists can be problematic for this -- way of implementing recursive sized generators, because they make a -- lot of recursive calls to arbitrary without decreasing the size -- parameter. Hence, as a default, genericArbitraryRec also -- detects fields which are lists to replace arbitrary with a -- different generator that divides the size parameter by the length of -- the list before generating each element. This uses the customizable -- mechanism shown in the next section. -- -- If you really want to use arbitrary for lists in the derived -- instances, substitute genericArbitraryRec with -- genericArbitraryRecG (). -- --
--   arbitrary = genericArbitraryRecG ()
--     `withBaseCase` baseGen
--   
-- -- Some combinators are available for further tweaking: listOf', -- listOf1', vectorOf'. -- --

Custom generators for some fields

-- --

Example 1 (Gen, FieldGen)

-- -- Sometimes, a few fields may need custom generators instead of -- arbitrary. For example, imagine here that String is -- meant to represent alphanumerical strings only, and that IDs are meant -- to be nonnegative, whereas balances can have any sign. -- --
--   data User = User {
--     userName :: String,
--     userId :: Int,
--     userBalance :: Int
--     } deriving Generic
--   
-- -- A naive approach has the following problems: -- -- -- -- Using generic-random, we can declare a (heterogeneous) list of -- generators to be used instead of arbitrary when generating -- certain fields. -- --
--   customGens :: FieldGen "userId" Int :+ Gen String
--   customGens =
--     FieldGen (getNonNegative <$> arbitrary) :+
--     listOf (elements (filter isAlphaNum [minBound .. maxBound]))
--   
-- -- Now we use the genericArbitraryG combinator and other -- G-suffixed variants that accept those explicit generators. -- -- -- --
--   instance Arbitrary User where
--     arbitrary = genericArbitrarySingleG customGens
--   
-- --

Example 2 (ConstrGen)

-- -- Here's the Tree type from the beginning again. -- --
--   data Tree a = Leaf a | Node (Tree a) (Tree a)
--     deriving Generic
--   
-- -- We will generate "right-leaning linear trees", which look like this: -- --
--   Node (Leaf 1)
--        (Node (Leaf 2)
--              (Node (Leaf 3)
--                    (Node (Leaf 4)
--                          (Leaf 5))))
--   
-- -- To do so, we force every left child of a Node to be a -- Leaf: -- --
--   {-# LANGUAGE ScopedTypeVariables #-}
--   
--   instance Arbitrary a => Arbitrary (Tree a) where
--     arbitrary = genericArbitraryUG customGens
--       where
--         -- Generator for the left field (i.e., at index 0) of constructor Node,
--         -- which must have type (Tree a).
--         customGens :: ConstrGen "Node" 0 (Tree a)
--         customGens =  ConstrGen (Leaf <$> arbitrary)
--   
-- -- That instance is equivalent to the following: -- --
--   instance Arbitrary a => Arbitrary (Tree a) where
--     arbitrary = oneof
--       [ Leaf <$> arbitrary
--       , Node <$> (Leaf <$> arbitrary) <*> arbitrary
--       --                                  ^ recursive call
--       ]
--   
-- --

Custom generators reference

-- -- The custom generator modifiers that can occur in the list are: -- -- -- -- Suggestions to add more modifiers or otherwise improve this tutorial -- are welcome! The issue tracker is this way. module Generic.Random.Tutorial