Generators are responsible for generating test data in ScalaCheck, and are represented by the `org.scalacheck.Gen`

class. ou need to know how to use this class if you want ScalaCheck to generate data of types that are not supported
by default, or if you want to use the `forAll`

method mentioned above, to state properties about a specific subset of
a type. In the `Gen`

object, there are several methods for creating new and modifying existing generators.
We will show how to use some of them in this section. For a more complete reference of what is available,
please see the API scaladoc.

A generator can be seen simply as a function that takes some generation parameters, and (maybe) returns a
generated value. That is, the type `Gen[T]`

may be thought of as a function of type `Gen.Params => Option[T]`

.
However, the `Gen`

class contains additional methods to make it possible to map generators, use them in
for-comprehensions and so on. Conceptually, though, you should think of generators simply as functions, and the
combinators in the `Gen`

object can be used to create or modify the behaviour of such generator functions.

Let's see how to create a new generator. The best way to do it is to use the generator combinators that exist
in the `org.scalacheck.Gen`

module. These can be combined using a for-comprehension. Suppose you need a generator
which generates a tuple that contains two random integer values, one of them being at least twice as big as the
other. The following definition does this:

```
import org.scalacheck.Gen
import org.scalacheck.Prop.forAll
val myGen = for {
n <- Gen.choose(10, 20)
m <- Gen.choose(2 * n, 500)
} yield (n, m)
check {
forAll(myGen) {
case (n, m) => (m >= 2 * n) == res0
}
}
```

You can create generators that pick one value out of a selection of values.
The `oneOf`

method creates a generator that randomly picks one of its parameters each time it generates a value.
Notice that plain values are implicitly converted to generators (which always generate that value) if needed.

The following generator generates a vowel:

```
import org.scalacheck.Gen
import org.scalacheck.Prop.forAll
val vowel = Gen.oneOf('A', 'E', 'I', 'O', 'U')
val validChars: Seq[Char] = res0
check {
forAll(vowel)(v => validChars.contains(v))
}
```

The distribution is uniform, but if you want to control it you can use the frequency combinator:

```
val vowel = Gen.frequency(
(3, 'A'),
(4, 'E'),
(2, 'I'),
(3, 'O'),
(1, 'U'))
```

Now, the vowel generator will generate *E:s* more often than *U:s*. Roughly, 4/14 of the values generated
will be *E:s*, and 1/14 of them will be *U:s*.

Other methods in the `Gen`

API:

```
def alphaChar: Gen[Char]
def alphaStr: Gen[String]
def posNum[T](implicit n: Numeric[T]): Gen[T]
def listOf[T](g: Gen[T]): Gen[List[T]]
def listOfN[T](n: Int, g: Gen[T]): Gen[List[T]]
```

```
import org.scalacheck.Gen.{ alphaChar, listOfN, posNum }
import org.scalacheck.Prop.forAll
check {
forAll(alphaChar)(_.isDigit == res0)
}
check {
forAll(posNum[Int])(n => (n > 0) == res1)
}
check {
forAll(listOfN(10, posNum[Int]))(list => !list.exists(_ < 0) && list.length == res2)
}
```

Conditional generators can be defined using `Gen.suchThat`

.

Conditional generators works just like conditional properties, in the sense that if the condition is too hard,
ScalaCheck might not be able to generate enough values, and it might report a property test as undecided.
The `smallEvenInteger`

definition is probably OK, since it will only throw away half of the generated numbers,
but one has to be careful when using the `suchThat`

operator.

```
import org.scalacheck.Gen
import org.scalacheck.Prop.forAll
val smallEvenInteger = Gen.choose(0, 200) suchThat (_ % 2 == 0)
check {
forAll(smallEvenInteger)(_ % 2 == res0)
}
```

On the basis of the above we can create a generator for the following case class:

`case class Foo(intValue: Int, charValue: Char)`

```
import org.scalacheck.Gen
import org.scalacheck.Prop.forAll
val fooGen = for {
intValue <- Gen.posNum[Int]
charValue <- Gen.alphaChar
} yield Foo(intValue, charValue)
check {
forAll(fooGen)(foo => foo.intValue > 0 && foo.charValue.isDigit == res0)
}
```

When ScalaCheck uses a generator to generate a value, it feeds it with some parameters. One of the parameters the generator is given is a size value, which some generators use to generate their values.

If you want to use the size parameter in your own generator, you can use the `Gen.sized`

method:

`def sized[T](f: Int => Gen[T])`

In this example we're creating a generator that produces two lists of numbers where 1/3 are positive and 2/3 are
negative. *Note: we're also returning the original size to verify the behaviour.*

```
import org.scalacheck.Gen
import org.scalacheck.Prop.forAll
val myGen = Gen.sized { size =>
val positiveNumbers = size / 3
val negativeNumbers = size * 2 / 3
for {
posNumList <- Gen.listOfN(positiveNumbers, Gen.posNum[Int])
negNumList <- Gen.listOfN(negativeNumbers, Gen.posNum[Int] map (n => -n))
} yield (size, posNumList, negNumList)
}
check {
forAll(myGen) {
case (genSize, posN, negN) =>
posN.length == genSize / res0 && negN.length == genSize * res1 / 3
}
}
```

There is a special generator, `Gen.containerOf`

, that generates containers such as lists and arrays.
It takes another generator as argument which is responsible for generating the individual items.
You can use it in the following way:

```
val genIntList = Gen.containerOf[List, Int](Gen.oneOf(1, 3, 5))
val genStringStream = Gen.containerOf[LazyList, String](Gen.alphaStr)
val genBoolArray = Gen.containerOf[Array, Boolean](true)
```

By default, ScalaCheck supports generation of `List`

, `Stream`

(Scala 2.10 -
2.12, deprecated in 2.13), `LazyList`

(Scala 2.13), `Set`

, `Array`

, and
`ArrayList`

(from `java.util`

). You can add support for additional containers
by adding implicit `Buildable`

instances. See `Buildable.scala`

for examples.

There is also `Gen.nonEmptyContainerOf`

for generating non-empty containers, and `Gen.containerOfN`

for
generating containers of a given size.

```
import org.scalacheck.Gen
import org.scalacheck.Prop.forAll
val genIntList = Gen.containerOf[List, Int](Gen.oneOf(2, 4, 6))
val validNumbers: List[Int] = res0
check {
forAll(genIntList)(_ forall (elem => validNumbers.contains(elem)))
}
```