Add more runnableExamples (#16864)

Add more links
This commit is contained in:
konsumlamm 2021-01-31 19:53:22 +01:00 • committed by GitHub
commit c05d1aab13
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23

View file

@ -15,18 +15,22 @@
import std/private/since import std/private/since
export system.`$` # for backward compatibility export system.`$` # for backward compatibility
proc name*(t: typedesc): string {.magic: "TypeTrait".} proc name*(t: typedesc): string {.magic: "TypeTrait".} =
## Returns the name of the given type. ## Returns the name of the given type.
## ##
## Alias for system.`$`(t) since Nim v0.20. ## Alias for `system.\`$\`(t) <dollars.html#$,typedesc>`_ since Nim v0.20.
runnableExamples:
doAssert name(int) == "int"
doAssert name(seq[string]) == "seq[string]"
proc arity*(t: typedesc): int {.magic: "TypeTrait".} = proc arity*(t: typedesc): int {.magic: "TypeTrait".} =
## Returns the arity of the given type. This is the number of "type" ## Returns the arity of the given type. This is the number of "type"
## components or the number of generic parameters a given type ``t`` has. ## components or the number of generic parameters a given type `t` has.
runnableExamples: runnableExamples:
assert arity(seq[string]) == 1 doAssert arity(int) == 0
assert arity(array[3, int]) == 2 doAssert arity(seq[string]) == 1
assert arity((int, int, float, string)) == 4 doAssert arity(array[3, int]) == 2
doAssert arity((int, int, float, string)) == 4
proc genericHead*(t: typedesc): typedesc {.magic: "TypeTrait".} = proc genericHead*(t: typedesc): typedesc {.magic: "TypeTrait".} =
## Accepts an instantiated generic type and returns its ## Accepts an instantiated generic type and returns its
@ -34,20 +38,23 @@ proc genericHead*(t: typedesc): typedesc {.magic: "TypeTrait".} =
## A compile-time error will be produced if the supplied type ## A compile-time error will be produced if the supplied type
## is not generic. ## is not generic.
## ##
## See also: ## **See also:**
## * `stripGenericParams <#stripGenericParams,typedesc>`_ ## * `stripGenericParams proc <#stripGenericParams,typedesc>`_
runnableExamples: runnableExamples:
type type
Foo[T] = object Foo[T] = object
FooInst = Foo[int] FooInst = Foo[int]
Foo2 = genericHead(FooInst) Foo2 = genericHead(FooInst)
doAssert Foo2 is Foo and Foo is Foo2 doAssert Foo2 is Foo and Foo is Foo2
doAssert genericHead(Foo[seq[string]]) is Foo doAssert genericHead(Foo[seq[string]]) is Foo
doAssert not compiles(genericHead(int)) doAssert not compiles(genericHead(int))
type Generic = concept f type Generic = concept f
type _ = genericHead(typeof(f)) type _ = genericHead(typeof(f))
proc bar(a: Generic): typeof(a) = a proc bar(a: Generic): typeof(a) = a
doAssert bar(Foo[string].default) == Foo[string]() doAssert bar(Foo[string].default) == Foo[string]()
doAssert not compiles bar(string.default) doAssert not compiles bar(string.default)
@ -55,66 +62,105 @@ proc genericHead*(t: typedesc): typedesc {.magic: "TypeTrait".} =
doAssert genericHead(Foo[int])[float] is Foo[float] doAssert genericHead(Foo[int])[float] is Foo[float]
doAssert seq[int].genericHead is seq doAssert seq[int].genericHead is seq
proc stripGenericParams*(t: typedesc): typedesc {.magic: "TypeTrait".} proc stripGenericParams*(t: typedesc): typedesc {.magic: "TypeTrait".} =
## This trait is similar to `genericHead <#genericHead,typedesc>`_, but ## This trait is similar to `genericHead <#genericHead,typedesc>`_, but
## instead of producing error for non-generic types, it will just return ## instead of producing an error for non-generic types, it will just return
## them unmodified. ## them unmodified.
runnableExamples:
type Foo[T] = object
doAssert stripGenericParams(Foo[string]) is Foo
doAssert stripGenericParams(int) is int
proc supportsCopyMem*(t: typedesc): bool {.magic: "TypeTrait".} proc supportsCopyMem*(t: typedesc): bool {.magic: "TypeTrait".}
## This trait returns true if the type ``t`` is safe to use for ## This trait returns true if the type `t` is safe to use for
## `copyMem`:idx:. ## `copyMem`:idx:.
## ##
## Other languages name a type like these `blob`:idx:. ## Other languages name a type like these `blob`:idx:.
proc isNamedTuple*(T: typedesc): bool {.magic: "TypeTrait".} proc isNamedTuple*(T: typedesc): bool {.magic: "TypeTrait".} =
## Return true for named tuples, false for any other type. ## Returns true for named tuples, false for any other type.
runnableExamples:
doAssert not isNamedTuple(int)
doAssert not isNamedTuple((string, int))
doAssert isNamedTuple(tuple[name: string, age: int])
proc distinctBase*(T: typedesc): typedesc {.magic: "TypeTrait".} proc distinctBase*(T: typedesc): typedesc {.magic: "TypeTrait".} =
## Returns base type for distinct types, works only for distinct types. ## Returns the base type for distinct types. This works only
## compile time error otherwise ## for distinct types and produces a compile time error otherwise.
##
## **See also:**
## * `distinctBase template <#distinctBase.t,T>`_
runnableExamples:
type MyInt = distinct int
doAssert distinctBase(MyInt) is int
doAssert not compiles(distinctBase(int))
since (1, 1): since (1, 1):
template distinctBase*[T](a: T): untyped = template distinctBase*[T](a: T): untyped =
## overload for values ## Overload of `distinctBase <#distinctBase,typedesc>`_ for values.
runnableExamples: runnableExamples:
type MyInt = distinct int type MyInt = distinct int
doAssert 12.MyInt.distinctBase == 12 doAssert 12.MyInt.distinctBase == 12
distinctBase(type(a))(a) distinctBase(type(a))(a)
proc tupleLen*(T: typedesc[tuple]): int {.magic: "TypeTrait".} proc tupleLen*(T: typedesc[tuple]): int {.magic: "TypeTrait".} =
## Return number of elements of `T` ## Returns the number of elements of the tuple type `T`.
##
## **See also:**
## * `tupleLen template <#tupleLen.t>`_
runnableExamples:
doAssert tupleLen((int, int, float, string)) == 4
doAssert tupleLen(tuple[name: string, age: int]) == 2
template tupleLen*(t: tuple): int = template tupleLen*(t: tuple): int =
## Return number of elements of `t` ## Returns the number of elements of the tuple `t`.
##
## **See also:**
## * `tupleLen proc <#tupleLen,typedesc>`_
runnableExamples:
doAssert tupleLen((1, 2)) == 2
tupleLen(type(t)) tupleLen(type(t))
template get*(T: typedesc[tuple], i: static int): untyped = template get*(T: typedesc[tuple], i: static int): untyped =
## Return `i`\th element of `T` ## Returns the `i`-th element of `T`.
# Note: `[]` currently gives: `Error: no generic parameters allowed for ...` # Note: `[]` currently gives: `Error: no generic parameters allowed for ...`
runnableExamples:
doAssert get((int, int, float, string), 2) is float
type(default(T)[i]) type(default(T)[i])
type StaticParam*[value: static type] = object type StaticParam*[value: static type] = object
## used to wrap a static value in `genericParams` ## Used to wrap a static value in `genericParams <#genericParams.t,typedesc>`_.
since (1, 3, 5): since (1, 3, 5):
template elementType*(a: untyped): typedesc = template elementType*(a: untyped): typedesc =
## return element type of `a`, which can be any iterable (over which you ## Returns the element type of `a`, which can be any iterable (over which you
## can iterate) ## can iterate).
runnableExamples: runnableExamples:
iterator myiter(n: int): auto = iterator myiter(n: int): auto =
for i in 0..<n: yield i for i in 0 ..< n:
yield i
doAssert elementType(@[1,2]) is int doAssert elementType(@[1,2]) is int
doAssert elementType("asdf") is char doAssert elementType("asdf") is char
doAssert elementType(myiter(3)) is int doAssert elementType(myiter(3)) is int
typeof(block: (for ai in a: ai)) typeof(block: (for ai in a: ai))
import std/macros import std/macros
macro enumLen*(T: typedesc[enum]): int = macro enumLen*(T: typedesc[enum]): int =
## Returns the number of items in the enum `T`. ## Returns the number of items in the enum `T`.
runnableExamples: runnableExamples:
type Foo = enum fooItem1 fooItem2 type Foo = enum
fooItem1
fooItem2
doAssert Foo.enumLen == 2 doAssert Foo.enumLen == 2
let bracketExpr = getType(T) let bracketExpr = getType(T)
@ -179,19 +225,23 @@ macro genericParamsImpl(T: typedesc): untyped =
since (1, 1): since (1, 1):
template genericParams*(T: typedesc): untyped = template genericParams*(T: typedesc): untyped =
## return tuple of generic params for generic `T` ## Returns the tuple of generic parameters for the generic type `T`.
##
## **Note:** For the builtin array type, the index generic parameter will
## **always** become a range type after it's bound to a variable.
runnableExamples: runnableExamples:
type Foo[T1, T2] = object type Foo[T1, T2] = object
doAssert genericParams(Foo[float, string]) is (float, string) doAssert genericParams(Foo[float, string]) is (float, string)
type Bar[N: static float, T] = object type Bar[N: static float, T] = object
doAssert genericParams(Bar[1.0, string]) is (StaticParam[1.0], string) doAssert genericParams(Bar[1.0, string]) is (StaticParam[1.0], string)
doAssert genericParams(Bar[1.0, string]).get(0).value == 1.0 doAssert genericParams(Bar[1.0, string]).get(0).value == 1.0
doAssert genericParams(seq[Bar[2.0, string]]).get(0) is Bar[2.0, string] doAssert genericParams(seq[Bar[2.0, string]]).get(0) is Bar[2.0, string]
var s: seq[Bar[3.0, string]] var s: seq[Bar[3.0, string]]
doAssert genericParams(typeof(s)) is (Bar[3.0, string],) doAssert genericParams(typeof(s)) is (Bar[3.0, string],)
# NOTE: For the builtin array type, the index generic param will
# **always** become a range type after it's bound to a variable.
doAssert genericParams(array[10, int]) is (StaticParam[10], int) doAssert genericParams(array[10, int]) is (StaticParam[10], int)
var a: array[10, int] var a: array[10, int]
doAssert genericParams(typeof(a)) is (range[0..9], int) doAssert genericParams(typeof(a)) is (range[0..9], int)