Merge pull request #1851 from jpoirier/feature/docs
fix a couple of typos, grammar, and removal of whitespace
This commit is contained in:
commit
5ee4806aa3
3 changed files with 103 additions and 103 deletions
|
|
@ -40,7 +40,7 @@ These integer types are pre-defined:
|
||||||
|
|
||||||
``int``
|
``int``
|
||||||
the generic signed integer type; its size is platform dependent and has the
|
the generic signed integer type; its size is platform dependent and has the
|
||||||
same size as a pointer. This type should be used in general. An integer
|
same size as a pointer. This type should be used in general. An integer
|
||||||
literal that has no type suffix is of this type.
|
literal that has no type suffix is of this type.
|
||||||
|
|
||||||
intXX
|
intXX
|
||||||
|
|
@ -51,7 +51,7 @@ intXX
|
||||||
|
|
||||||
``uint``
|
``uint``
|
||||||
the generic `unsigned integer`:idx: type; its size is platform dependent and
|
the generic `unsigned integer`:idx: type; its size is platform dependent and
|
||||||
has the same size as a pointer. An integer literal with the type
|
has the same size as a pointer. An integer literal with the type
|
||||||
suffix ``'u`` is of this type.
|
suffix ``'u`` is of this type.
|
||||||
|
|
||||||
uintXX
|
uintXX
|
||||||
|
|
@ -59,15 +59,15 @@ uintXX
|
||||||
(example: uint16 is a 16 bit wide unsigned integer).
|
(example: uint16 is a 16 bit wide unsigned integer).
|
||||||
The current implementation supports ``uint8``, ``uint16``, ``uint32``,
|
The current implementation supports ``uint8``, ``uint16``, ``uint32``,
|
||||||
``uint64``. Literals of these types have the suffix 'uXX.
|
``uint64``. Literals of these types have the suffix 'uXX.
|
||||||
Unsigned operations all wrap around; they cannot lead to over- or
|
Unsigned operations all wrap around; they cannot lead to over- or
|
||||||
underflow errors.
|
underflow errors.
|
||||||
|
|
||||||
|
|
||||||
In addition to the usual arithmetic operators for signed and unsigned integers
|
In addition to the usual arithmetic operators for signed and unsigned integers
|
||||||
(``+ - *`` etc.) there are also operators that formally work on *signed*
|
(``+ - *`` etc.) there are also operators that formally work on *signed*
|
||||||
integers but treat their arguments as *unsigned*: They are mostly provided
|
integers but treat their arguments as *unsigned*: They are mostly provided
|
||||||
for backwards compatibility with older versions of the language that lacked
|
for backwards compatibility with older versions of the language that lacked
|
||||||
unsigned integer types. These unsigned operations for signed integers use
|
unsigned integer types. These unsigned operations for signed integers use
|
||||||
the ``%`` suffix as convention:
|
the ``%`` suffix as convention:
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -98,7 +98,7 @@ operation meaning
|
||||||
kinds of integer types are used: the smaller type is converted to the larger.
|
kinds of integer types are used: the smaller type is converted to the larger.
|
||||||
|
|
||||||
A `narrowing type conversion`:idx: converts a larger to a smaller type (for
|
A `narrowing type conversion`:idx: converts a larger to a smaller type (for
|
||||||
example ``int32 -> int16``. A `widening type conversion`:idx: converts a
|
example ``int32 -> int16``. A `widening type conversion`:idx: converts a
|
||||||
smaller type to a larger type (for example ``int16 -> int32``). In Nim only
|
smaller type to a larger type (for example ``int16 -> int32``). In Nim only
|
||||||
widening type conversions are *implicit*:
|
widening type conversions are *implicit*:
|
||||||
|
|
||||||
|
|
@ -111,7 +111,7 @@ widening type conversions are *implicit*:
|
||||||
|
|
||||||
However, ``int`` literals are implicitly convertible to a smaller integer type
|
However, ``int`` literals are implicitly convertible to a smaller integer type
|
||||||
if the literal's value fits this smaller type and such a conversion is less
|
if the literal's value fits this smaller type and such a conversion is less
|
||||||
expensive than other implicit conversions, so ``myInt16 + 34`` produces
|
expensive than other implicit conversions, so ``myInt16 + 34`` produces
|
||||||
an ``int16`` result.
|
an ``int16`` result.
|
||||||
|
|
||||||
For further details, see `Convertible relation`_.
|
For further details, see `Convertible relation`_.
|
||||||
|
|
@ -137,12 +137,12 @@ determined). Assignments from the base type to one of its subrange types
|
||||||
A subrange type has the same size as its base type (``int`` in the example).
|
A subrange type has the same size as its base type (``int`` in the example).
|
||||||
|
|
||||||
Nim requires `interval arithmetic`:idx: for subrange types over a set
|
Nim requires `interval arithmetic`:idx: for subrange types over a set
|
||||||
of built-in operators that involve constants: ``x %% 3`` is of
|
of built-in operators that involve constants: ``x %% 3`` is of
|
||||||
type ``range[0..2]``. The following built-in operators for integers are
|
type ``range[0..2]``. The following built-in operators for integers are
|
||||||
affected by this rule: ``-``, ``+``, ``*``, ``min``, ``max``, ``succ``,
|
affected by this rule: ``-``, ``+``, ``*``, ``min``, ``max``, ``succ``,
|
||||||
``pred``, ``mod``, ``div``, ``%%``, ``and`` (bitwise ``and``).
|
``pred``, ``mod``, ``div``, ``%%``, ``and`` (bitwise ``and``).
|
||||||
|
|
||||||
Bitwise ``and`` only produces a ``range`` if one of its operands is a
|
Bitwise ``and`` only produces a ``range`` if one of its operands is a
|
||||||
constant *x* so that (x+1) is a number of two.
|
constant *x* so that (x+1) is a number of two.
|
||||||
(Bitwise ``and`` is then a ``%%`` operation.)
|
(Bitwise ``and`` is then a ``%%`` operation.)
|
||||||
|
|
||||||
|
|
@ -155,7 +155,7 @@ This means that the following code is accepted:
|
||||||
of 9: echo "C"
|
of 9: echo "C"
|
||||||
of 10: echo "D"
|
of 10: echo "D"
|
||||||
# note: no ``else`` required as (x and 3) + 7 has the type: range[7..10]
|
# note: no ``else`` required as (x and 3) + 7 has the type: range[7..10]
|
||||||
|
|
||||||
|
|
||||||
Pre-defined floating point types
|
Pre-defined floating point types
|
||||||
--------------------------------
|
--------------------------------
|
||||||
|
|
@ -186,17 +186,17 @@ The IEEE standard defines five types of floating-point exceptions:
|
||||||
for example 0.0/0.0, sqrt(-1.0), and log(-37.8).
|
for example 0.0/0.0, sqrt(-1.0), and log(-37.8).
|
||||||
* Division by zero: divisor is zero and dividend is a finite nonzero number,
|
* Division by zero: divisor is zero and dividend is a finite nonzero number,
|
||||||
for example 1.0/0.0.
|
for example 1.0/0.0.
|
||||||
* Overflow: operation produces a result that exceeds the range of the exponent,
|
* Overflow: operation produces a result that exceeds the range of the exponent,
|
||||||
for example MAXDOUBLE+0.0000000000001e308.
|
for example MAXDOUBLE+0.0000000000001e308.
|
||||||
* Underflow: operation produces a result that is too small to be represented
|
* Underflow: operation produces a result that is too small to be represented
|
||||||
as a normal number, for example, MINDOUBLE * MINDOUBLE.
|
as a normal number, for example, MINDOUBLE * MINDOUBLE.
|
||||||
* Inexact: operation produces a result that cannot be represented with infinite
|
* Inexact: operation produces a result that cannot be represented with infinite
|
||||||
precision, for example, 2.0 / 3.0, log(1.1) and 0.1 in input.
|
precision, for example, 2.0 / 3.0, log(1.1) and 0.1 in input.
|
||||||
|
|
||||||
The IEEE exceptions are either ignored at runtime or mapped to the
|
The IEEE exceptions are either ignored at runtime or mapped to the
|
||||||
Nim exceptions: `FloatInvalidOpError`:idx:, `FloatDivByZeroError`:idx:,
|
Nim exceptions: `FloatInvalidOpError`:idx:, `FloatDivByZeroError`:idx:,
|
||||||
`FloatOverflowError`:idx:, `FloatUnderflowError`:idx:,
|
`FloatOverflowError`:idx:, `FloatUnderflowError`:idx:,
|
||||||
and `FloatInexactError`:idx:.
|
and `FloatInexactError`:idx:.
|
||||||
These exceptions inherit from the `FloatingPointError`:idx: base class.
|
These exceptions inherit from the `FloatingPointError`:idx: base class.
|
||||||
|
|
||||||
Nim provides the pragmas `NaNChecks`:idx: and `InfChecks`:idx: to control
|
Nim provides the pragmas `NaNChecks`:idx: and `InfChecks`:idx: to control
|
||||||
|
|
@ -212,7 +212,7 @@ whether the IEEE exceptions are ignored or trap a Nim exception:
|
||||||
In the current implementation ``FloatDivByZeroError`` and ``FloatInexactError``
|
In the current implementation ``FloatDivByZeroError`` and ``FloatInexactError``
|
||||||
are never raised. ``FloatOverflowError`` is raised instead of
|
are never raised. ``FloatOverflowError`` is raised instead of
|
||||||
``FloatDivByZeroError``.
|
``FloatDivByZeroError``.
|
||||||
There is also a `floatChecks`:idx: pragma that is a short-cut for the
|
There is also a `floatChecks`:idx: pragma that is a short-cut for the
|
||||||
combination of ``NaNChecks`` and ``InfChecks`` pragmas. ``floatChecks`` are
|
combination of ``NaNChecks`` and ``InfChecks`` pragmas. ``floatChecks`` are
|
||||||
turned off as default.
|
turned off as default.
|
||||||
|
|
||||||
|
|
@ -303,7 +303,7 @@ and ``pred`` are not available for them either.
|
||||||
|
|
||||||
|
|
||||||
The compiler supports the built-in stringify operator ``$`` for enumerations.
|
The compiler supports the built-in stringify operator ``$`` for enumerations.
|
||||||
The stringify's result can be controlled by explicitly giving the string
|
The stringify's result can be controlled by explicitly giving the string
|
||||||
values to use:
|
values to use:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
|
|
@ -315,12 +315,12 @@ values to use:
|
||||||
valueC = 2,
|
valueC = 2,
|
||||||
valueD = (3, "abc")
|
valueD = (3, "abc")
|
||||||
|
|
||||||
As can be seen from the example, it is possible to both specify a field's
|
As can be seen from the example, it is possible to both specify a field's
|
||||||
ordinal value and its string value by using a tuple. It is also
|
ordinal value and its string value by using a tuple. It is also
|
||||||
possible to only specify one of them.
|
possible to only specify one of them.
|
||||||
|
|
||||||
An enum can be marked with the ``pure`` pragma so that it's fields are not
|
An enum can be marked with the ``pure`` pragma so that it's fields are not
|
||||||
added to the current scope, so they always need to be accessed
|
added to the current scope, so they always need to be accessed
|
||||||
via ``MyEnum.value``:
|
via ``MyEnum.value``:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
|
|
@ -328,7 +328,7 @@ via ``MyEnum.value``:
|
||||||
type
|
type
|
||||||
MyEnum {.pure.} = enum
|
MyEnum {.pure.} = enum
|
||||||
valueA, valueB, valueC, valueD
|
valueA, valueB, valueC, valueD
|
||||||
|
|
||||||
echo valueA # error: Unknown identifier
|
echo valueA # error: Unknown identifier
|
||||||
echo MyEnum.valueA # works
|
echo MyEnum.valueA # works
|
||||||
|
|
||||||
|
|
@ -364,22 +364,22 @@ cstring type
|
||||||
------------
|
------------
|
||||||
The ``cstring`` type represents a pointer to a zero-terminated char array
|
The ``cstring`` type represents a pointer to a zero-terminated char array
|
||||||
compatible to the type ``char*`` in Ansi C. Its primary purpose lies in easy
|
compatible to the type ``char*`` in Ansi C. Its primary purpose lies in easy
|
||||||
interfacing with C. The index operation ``s[i]`` means the i-th *char* of
|
interfacing with C. The index operation ``s[i]`` means the i-th *char* of
|
||||||
``s``; however no bounds checking for ``cstring`` is performed making the
|
``s``; however no bounds checking for ``cstring`` is performed making the
|
||||||
index operation unsafe.
|
index operation unsafe.
|
||||||
|
|
||||||
A Nim ``string`` is implicitly convertible
|
A Nim ``string`` is implicitly convertible
|
||||||
to ``cstring`` for convenience. If a Nim string is passed to a C-style
|
to ``cstring`` for convenience. If a Nim string is passed to a C-style
|
||||||
variadic proc, it is implicitly converted to ``cstring`` too:
|
variadic proc, it is implicitly converted to ``cstring`` too:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
proc printf(formatstr: cstring) {.importc: "printf", varargs,
|
proc printf(formatstr: cstring) {.importc: "printf", varargs,
|
||||||
header: "<stdio.h>".}
|
header: "<stdio.h>".}
|
||||||
|
|
||||||
printf("This works %s", "as expected")
|
printf("This works %s", "as expected")
|
||||||
|
|
||||||
Even though the conversion is implicit, it is not *safe*: The garbage collector
|
Even though the conversion is implicit, it is not *safe*: The garbage collector
|
||||||
does not consider a ``cstring`` to be a root and may collect the underlying
|
does not consider a ``cstring`` to be a root and may collect the underlying
|
||||||
memory. However in practice this almost never happens as the GC considers
|
memory. However in practice this almost never happens as the GC considers
|
||||||
stack roots conservatively. One can use the builtin procs ``GC_ref`` and
|
stack roots conservatively. One can use the builtin procs ``GC_ref`` and
|
||||||
``GC_unref`` to keep the string data alive for the rare cases where it does
|
``GC_unref`` to keep the string data alive for the rare cases where it does
|
||||||
|
|
@ -390,7 +390,7 @@ string from a cstring:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
var str: string = "Hello!"
|
var str: string = "Hello!"
|
||||||
var cstr: cstring = s
|
var cstr: cstring = str
|
||||||
var newstr: string = $cstr
|
var newstr: string = $cstr
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -410,9 +410,9 @@ integers from 0 to ``len(A)-1``. An array expression may be constructed by the
|
||||||
array constructor ``[]``.
|
array constructor ``[]``.
|
||||||
|
|
||||||
Sequences are similar to arrays but of dynamic length which may change
|
Sequences are similar to arrays but of dynamic length which may change
|
||||||
during runtime (like strings). Sequences are implemented as growable arrays,
|
during runtime (like strings). Sequences are implemented as growable arrays,
|
||||||
allocating pieces of memory as items are added. A sequence ``S`` is always
|
allocating pieces of memory as items are added. A sequence ``S`` is always
|
||||||
indexed by integers from 0 to ``len(S)-1`` and its bounds are checked.
|
indexed by integers from 0 to ``len(S)-1`` and its bounds are checked.
|
||||||
Sequences can be constructed by the array constructor ``[]`` in conjunction
|
Sequences can be constructed by the array constructor ``[]`` in conjunction
|
||||||
with the array to sequence operator ``@``. Another way to allocate space for a
|
with the array to sequence operator ``@``. Another way to allocate space for a
|
||||||
sequence is to call the built-in ``newSeq`` procedure.
|
sequence is to call the built-in ``newSeq`` procedure.
|
||||||
|
|
@ -452,11 +452,11 @@ Open arrays
|
||||||
|
|
||||||
Often fixed size arrays turn out to be too inflexible; procedures should
|
Often fixed size arrays turn out to be too inflexible; procedures should
|
||||||
be able to deal with arrays of different sizes. The `openarray`:idx: type
|
be able to deal with arrays of different sizes. The `openarray`:idx: type
|
||||||
allows this; it can only be used for parameters. Openarrays are always
|
allows this; it can only be used for parameters. Openarrays are always
|
||||||
indexed with an ``int`` starting at position 0. The ``len``, ``low``
|
indexed with an ``int`` starting at position 0. The ``len``, ``low``
|
||||||
and ``high`` operations are available for open arrays too. Any array with
|
and ``high`` operations are available for open arrays too. Any array with
|
||||||
a compatible base type can be passed to an openarray parameter, the index
|
a compatible base type can be passed to an openarray parameter, the index
|
||||||
type does not matter. In addition to arrays sequences can also be passed
|
type does not matter. In addition to arrays sequences can also be passed
|
||||||
to an open array parameter.
|
to an open array parameter.
|
||||||
|
|
||||||
The openarray type cannot be nested: multidimensional openarrays are not
|
The openarray type cannot be nested: multidimensional openarrays are not
|
||||||
|
|
@ -467,7 +467,7 @@ Varargs
|
||||||
-------
|
-------
|
||||||
|
|
||||||
A ``varargs`` parameter is an openarray parameter that additionally
|
A ``varargs`` parameter is an openarray parameter that additionally
|
||||||
allows to pass a variable number of arguments to a procedure. The compiler
|
allows to pass a variable number of arguments to a procedure. The compiler
|
||||||
converts the list of arguments to an array implicitly:
|
converts the list of arguments to an array implicitly:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
|
|
@ -494,7 +494,7 @@ type conversions in this context:
|
||||||
# is transformed to:
|
# is transformed to:
|
||||||
myWriteln(stdout, [$123, $"def", $4.0])
|
myWriteln(stdout, [$123, $"def", $4.0])
|
||||||
|
|
||||||
In this example ``$`` is applied to any argument that is passed to the
|
In this example ``$`` is applied to any argument that is passed to the
|
||||||
parameter ``a``. (Note that ``$`` applied to strings is a nop.)
|
parameter ``a``. (Note that ``$`` applied to strings is a nop.)
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -531,7 +531,7 @@ in future versions of the compiler.
|
||||||
person = (creditCard: "Peter", id: 20)
|
person = (creditCard: "Peter", id: 20)
|
||||||
|
|
||||||
The implementation aligns the fields for best access performance. The alignment
|
The implementation aligns the fields for best access performance. The alignment
|
||||||
is compatible with the way the C compiler does it.
|
is compatible with the way the C compiler does it.
|
||||||
|
|
||||||
For consistency with ``object`` declarations, tuples in a ``type`` section
|
For consistency with ``object`` declarations, tuples in a ``type`` section
|
||||||
can also be defined with indentation instead of ``[]``:
|
can also be defined with indentation instead of ``[]``:
|
||||||
|
|
@ -571,7 +571,7 @@ Object construction
|
||||||
-------------------
|
-------------------
|
||||||
|
|
||||||
Objects can also be created with an `object construction expression`:idx: that
|
Objects can also be created with an `object construction expression`:idx: that
|
||||||
has the syntax ``T(fieldA: valueA, fieldB: valueB, ...)`` where ``T`` is
|
has the syntax ``T(fieldA: valueA, fieldB: valueB, ...)`` where ``T`` is
|
||||||
an ``object`` type or a ``ref object`` type:
|
an ``object`` type or a ``ref object`` type:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
|
|
@ -617,10 +617,10 @@ An example:
|
||||||
# the following statement raises an `EInvalidField` exception, because
|
# the following statement raises an `EInvalidField` exception, because
|
||||||
# n.kind's value does not fit and the ``nkString`` branch is not active:
|
# n.kind's value does not fit and the ``nkString`` branch is not active:
|
||||||
n.strVal = ""
|
n.strVal = ""
|
||||||
|
|
||||||
# invalid: would change the active object branch:
|
# invalid: would change the active object branch:
|
||||||
n.kind = nkInt
|
n.kind = nkInt
|
||||||
|
|
||||||
var x = PNode(kind: nkAdd, leftOp: PNode(kind: nkInt, intVal: 4),
|
var x = PNode(kind: nkAdd, leftOp: PNode(kind: nkInt, intVal: 4),
|
||||||
rightOp: PNode(kind: nkInt, intVal: 2))
|
rightOp: PNode(kind: nkInt, intVal: 2))
|
||||||
# valid: does not change the active object branch:
|
# valid: does not change the active object branch:
|
||||||
|
|
@ -660,8 +660,8 @@ untraced references are *unsafe*. However for certain low-level operations
|
||||||
Traced references are declared with the **ref** keyword, untraced references
|
Traced references are declared with the **ref** keyword, untraced references
|
||||||
are declared with the **ptr** keyword.
|
are declared with the **ptr** keyword.
|
||||||
|
|
||||||
An empty subscript ``[]`` notation can be used to derefer a reference,
|
An empty subscript ``[]`` notation can be used to derefer a reference,
|
||||||
the ``addr`` procedure returns the address of an item. An address is always
|
the ``addr`` procedure returns the address of an item. An address is always
|
||||||
an untraced reference.
|
an untraced reference.
|
||||||
Thus the usage of ``addr`` is an *unsafe* feature.
|
Thus the usage of ``addr`` is an *unsafe* feature.
|
||||||
|
|
||||||
|
|
@ -680,7 +680,7 @@ dereferencing operations for reference types:
|
||||||
var
|
var
|
||||||
n: PNode
|
n: PNode
|
||||||
new(n)
|
new(n)
|
||||||
n.data = 9
|
n.data = 9
|
||||||
# no need to write n[].data; in fact n[].data is highly discouraged!
|
# no need to write n[].data; in fact n[].data is highly discouraged!
|
||||||
|
|
||||||
In order to simplify structural type checking, recursive tuples are not valid:
|
In order to simplify structural type checking, recursive tuples are not valid:
|
||||||
|
|
@ -751,20 +751,20 @@ details like this when mixing garbage collected data with unmanaged memory.
|
||||||
Not nil annotation
|
Not nil annotation
|
||||||
------------------
|
------------------
|
||||||
|
|
||||||
All types for that ``nil`` is a valid value can be annotated to
|
All types for that ``nil`` is a valid value can be annotated to
|
||||||
exclude ``nil`` as a valid value with the ``not nil`` annotation:
|
exclude ``nil`` as a valid value with the ``not nil`` annotation:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
type
|
type
|
||||||
PObject = ref TObj not nil
|
PObject = ref TObj not nil
|
||||||
TProc = (proc (x, y: int)) not nil
|
TProc = (proc (x, y: int)) not nil
|
||||||
|
|
||||||
proc p(x: PObject) =
|
proc p(x: PObject) =
|
||||||
echo "not nil"
|
echo "not nil"
|
||||||
|
|
||||||
# compiler catches this:
|
# compiler catches this:
|
||||||
p(nil)
|
p(nil)
|
||||||
|
|
||||||
# and also this:
|
# and also this:
|
||||||
var x: PObject
|
var x: PObject
|
||||||
p(x)
|
p(x)
|
||||||
|
|
@ -851,22 +851,22 @@ Examples:
|
||||||
|
|
||||||
forEach(printItem) # this will NOT compile because calling conventions differ
|
forEach(printItem) # this will NOT compile because calling conventions differ
|
||||||
|
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
|
|
||||||
type
|
type
|
||||||
TOnMouseMove = proc (x, y: int) {.closure.}
|
TOnMouseMove = proc (x, y: int) {.closure.}
|
||||||
|
|
||||||
proc onMouseMove(mouseX, mouseY: int) =
|
proc onMouseMove(mouseX, mouseY: int) =
|
||||||
# has default calling convention
|
# has default calling convention
|
||||||
echo "x: ", mouseX, " y: ", mouseY
|
echo "x: ", mouseX, " y: ", mouseY
|
||||||
|
|
||||||
proc setOnMouseMove(mouseMoveEvent: TOnMouseMove) = discard
|
proc setOnMouseMove(mouseMoveEvent: TOnMouseMove) = discard
|
||||||
|
|
||||||
# ok, 'onMouseMove' has the default calling convention, which is compatible
|
# ok, 'onMouseMove' has the default calling convention, which is compatible
|
||||||
# to 'closure':
|
# to 'closure':
|
||||||
setOnMouseMove(onMouseMove)
|
setOnMouseMove(onMouseMove)
|
||||||
|
|
||||||
|
|
||||||
A subtle issue with procedural types is that the calling convention of the
|
A subtle issue with procedural types is that the calling convention of the
|
||||||
procedure influences the type compatibility: procedural types are only
|
procedure influences the type compatibility: procedural types are only
|
||||||
|
|
@ -932,7 +932,7 @@ of the following conditions hold:
|
||||||
3) The procedure has a calling convention that differs from ``nimcall``.
|
3) The procedure has a calling convention that differs from ``nimcall``.
|
||||||
4) The procedure is anonymous.
|
4) The procedure is anonymous.
|
||||||
|
|
||||||
The rules' purpose is to prevent the case that extending a non-``procvar``
|
The rules' purpose is to prevent the case that extending a non-``procvar``
|
||||||
procedure with default parameters breaks client code.
|
procedure with default parameters breaks client code.
|
||||||
|
|
||||||
The default calling convention is ``nimcall``, unless it is an inner proc (a
|
The default calling convention is ``nimcall``, unless it is an inner proc (a
|
||||||
|
|
@ -964,7 +964,7 @@ types are a perfect tool to model different currencies:
|
||||||
type
|
type
|
||||||
TDollar = distinct int
|
TDollar = distinct int
|
||||||
TEuro = distinct int
|
TEuro = distinct int
|
||||||
|
|
||||||
var
|
var
|
||||||
d: TDollar
|
d: TDollar
|
||||||
e: TEuro
|
e: TEuro
|
||||||
|
|
@ -989,7 +989,7 @@ number without unit; and the same holds for division:
|
||||||
|
|
||||||
proc `*` (x: int, y: TDollar): TDollar =
|
proc `*` (x: int, y: TDollar): TDollar =
|
||||||
result = TDollar(x * int(y))
|
result = TDollar(x * int(y))
|
||||||
|
|
||||||
proc `div` ...
|
proc `div` ...
|
||||||
|
|
||||||
This quickly gets tedious. The implementations are trivial and the compiler
|
This quickly gets tedious. The implementations are trivial and the compiler
|
||||||
|
|
@ -1014,7 +1014,7 @@ currency. This can be solved with templates_.
|
||||||
template additive(typ: typedesc): stmt =
|
template additive(typ: typedesc): stmt =
|
||||||
proc `+` *(x, y: typ): typ {.borrow.}
|
proc `+` *(x, y: typ): typ {.borrow.}
|
||||||
proc `-` *(x, y: typ): typ {.borrow.}
|
proc `-` *(x, y: typ): typ {.borrow.}
|
||||||
|
|
||||||
# unary operators:
|
# unary operators:
|
||||||
proc `+` *(x: typ): typ {.borrow.}
|
proc `+` *(x: typ): typ {.borrow.}
|
||||||
proc `-` *(x: typ): typ {.borrow.}
|
proc `-` *(x: typ): typ {.borrow.}
|
||||||
|
|
@ -1036,7 +1036,7 @@ currency. This can be solved with templates_.
|
||||||
additive(typ)
|
additive(typ)
|
||||||
multiplicative(typ, base)
|
multiplicative(typ, base)
|
||||||
comparable(typ)
|
comparable(typ)
|
||||||
|
|
||||||
defineCurrency(TDollar, int)
|
defineCurrency(TDollar, int)
|
||||||
defineCurrency(TEuro, int)
|
defineCurrency(TEuro, int)
|
||||||
|
|
||||||
|
|
@ -1127,21 +1127,21 @@ modules like `db_sqlite <db_sqlite.html>`_.
|
||||||
Void type
|
Void type
|
||||||
---------
|
---------
|
||||||
|
|
||||||
The ``void`` type denotes the absense of any type. Parameters of
|
The ``void`` type denotes the absense of any type. Parameters of
|
||||||
type ``void`` are treated as non-existent, ``void`` as a return type means that
|
type ``void`` are treated as non-existent, ``void`` as a return type means that
|
||||||
the procedure does not return a value:
|
the procedure does not return a value:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
proc nothing(x, y: void): void =
|
proc nothing(x, y: void): void =
|
||||||
echo "ha"
|
echo "ha"
|
||||||
|
|
||||||
nothing() # writes "ha" to stdout
|
nothing() # writes "ha" to stdout
|
||||||
|
|
||||||
The ``void`` type is particularly useful for generic code:
|
The ``void`` type is particularly useful for generic code:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
proc callProc[T](p: proc (x: T), x: T) =
|
proc callProc[T](p: proc (x: T), x: T) =
|
||||||
when T is void:
|
when T is void:
|
||||||
p()
|
p()
|
||||||
else:
|
else:
|
||||||
p(x)
|
p(x)
|
||||||
|
|
@ -1151,13 +1151,13 @@ The ``void`` type is particularly useful for generic code:
|
||||||
|
|
||||||
callProc[int](intProc, 12)
|
callProc[int](intProc, 12)
|
||||||
callProc[void](emptyProc)
|
callProc[void](emptyProc)
|
||||||
|
|
||||||
However, a ``void`` type cannot be inferred in generic code:
|
However, a ``void`` type cannot be inferred in generic code:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
callProc(emptyProc)
|
callProc(emptyProc)
|
||||||
# Error: type mismatch: got (proc ())
|
# Error: type mismatch: got (proc ())
|
||||||
# but expected one of:
|
# but expected one of:
|
||||||
# callProc(p: proc (T), x: T)
|
# callProc(p: proc (T), x: T)
|
||||||
|
|
||||||
The ``void`` type is only valid for parameters and return types; other symbols
|
The ``void`` type is only valid for parameters and return types; other symbols
|
||||||
|
|
|
||||||
42
doc/tut2.txt
42
doc/tut2.txt
|
|
@ -35,7 +35,7 @@ Object Oriented Programming
|
||||||
===========================
|
===========================
|
||||||
|
|
||||||
While Nim's support for object oriented programming (OOP) is minimalistic,
|
While Nim's support for object oriented programming (OOP) is minimalistic,
|
||||||
powerful OOP technics can be used. OOP is seen as *one* way to design a
|
powerful OOP techniques can be used. OOP is seen as *one* way to design a
|
||||||
program, not *the only* way. Often a procedural approach leads to simpler
|
program, not *the only* way. Often a procedural approach leads to simpler
|
||||||
and more efficient code. In particular, prefering composition over inheritance
|
and more efficient code. In particular, prefering composition over inheritance
|
||||||
is often the better design.
|
is often the better design.
|
||||||
|
|
@ -77,8 +77,8 @@ section.
|
||||||
|
|
||||||
Inheritance is done with the ``object of`` syntax. Multiple inheritance is
|
Inheritance is done with the ``object of`` syntax. Multiple inheritance is
|
||||||
currently not supported. If an object type has no suitable ancestor, ``RootObj``
|
currently not supported. If an object type has no suitable ancestor, ``RootObj``
|
||||||
can be used as its ancestor, but this is only a convention. Objects that have
|
can be used as its ancestor, but this is only a convention. Objects that have
|
||||||
no ancestor are implicitly ``final``. You can use the ``inheritable`` pragma
|
no ancestor are implicitly ``final``. You can use the ``inheritable`` pragma
|
||||||
to introduce new object roots apart from ``system.RootObj``. (This is used
|
to introduce new object roots apart from ``system.RootObj``. (This is used
|
||||||
in the GTK wrapper for instance.)
|
in the GTK wrapper for instance.)
|
||||||
|
|
||||||
|
|
@ -199,7 +199,7 @@ This method call syntax is not restricted to objects, it can be used
|
||||||
for any type:
|
for any type:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
|
|
||||||
echo("abc".len) # is the same as echo(len("abc"))
|
echo("abc".len) # is the same as echo(len("abc"))
|
||||||
echo("abc".toUpper())
|
echo("abc".toUpper())
|
||||||
echo({'a', 'b', 'c'}.card)
|
echo({'a', 'b', 'c'}.card)
|
||||||
|
|
@ -212,7 +212,7 @@ So "pure object oriented" code is easy to write:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
import strutils
|
import strutils
|
||||||
|
|
||||||
stdout.writeln("Give a list of numbers (separated by spaces): ")
|
stdout.writeln("Give a list of numbers (separated by spaces): ")
|
||||||
stdout.write(stdin.readLine.split.map(parseInt).max.`$`)
|
stdout.write(stdin.readLine.split.map(parseInt).max.`$`)
|
||||||
stdout.writeln(" is the maximum!")
|
stdout.writeln(" is the maximum!")
|
||||||
|
|
@ -226,7 +226,7 @@ the same. But setting a value is different; for this a special setter syntax
|
||||||
is needed:
|
is needed:
|
||||||
|
|
||||||
.. code-block:: nim
|
.. code-block:: nim
|
||||||
|
|
||||||
type
|
type
|
||||||
TSocket* = object of RootObj
|
TSocket* = object of RootObj
|
||||||
FHost: int # cannot be accessed from the outside of the module
|
FHost: int # cannot be accessed from the outside of the module
|
||||||
|
|
@ -236,7 +236,7 @@ is needed:
|
||||||
proc `host=`*(s: var TSocket, value: int) {.inline.} =
|
proc `host=`*(s: var TSocket, value: int) {.inline.} =
|
||||||
## setter of hostAddr
|
## setter of hostAddr
|
||||||
s.FHost = value
|
s.FHost = value
|
||||||
|
|
||||||
proc host*(s: TSocket): int {.inline.} =
|
proc host*(s: TSocket): int {.inline.} =
|
||||||
## getter of hostAddr
|
## getter of hostAddr
|
||||||
s.FHost
|
s.FHost
|
||||||
|
|
@ -294,15 +294,15 @@ Procedures always use static dispatch. For dynamic dispatch replace the
|
||||||
method eval(e: PExpr): int =
|
method eval(e: PExpr): int =
|
||||||
# override this base method
|
# override this base method
|
||||||
quit "to override!"
|
quit "to override!"
|
||||||
|
|
||||||
method eval(e: PLiteral): int = e.x
|
method eval(e: PLiteral): int = e.x
|
||||||
method eval(e: PPlusExpr): int = eval(e.a) + eval(e.b)
|
method eval(e: PPlusExpr): int = eval(e.a) + eval(e.b)
|
||||||
|
|
||||||
proc newLit(x: int): PLiteral = PLiteral(x: x)
|
proc newLit(x: int): PLiteral = PLiteral(x: x)
|
||||||
proc newPlus(a, b: PExpr): PPlusExpr = PPlusExpr(a: a, b: b)
|
proc newPlus(a, b: PExpr): PPlusExpr = PPlusExpr(a: a, b: b)
|
||||||
|
|
||||||
echo eval(newPlus(newPlus(newLit(1), newLit(2)), newLit(4)))
|
echo eval(newPlus(newPlus(newLit(1), newLit(2)), newLit(4)))
|
||||||
|
|
||||||
Note that in the example the constructors ``newLit`` and ``newPlus`` are procs
|
Note that in the example the constructors ``newLit`` and ``newPlus`` are procs
|
||||||
because they should use static binding, but ``eval`` is a method because it
|
because they should use static binding, but ``eval`` is a method because it
|
||||||
requires dynamic binding.
|
requires dynamic binding.
|
||||||
|
|
@ -316,16 +316,16 @@ dispatching:
|
||||||
TThing = object of RootObj
|
TThing = object of RootObj
|
||||||
TUnit = object of TThing
|
TUnit = object of TThing
|
||||||
x: int
|
x: int
|
||||||
|
|
||||||
method collide(a, b: TThing) {.inline.} =
|
method collide(a, b: TThing) {.inline.} =
|
||||||
quit "to override!"
|
quit "to override!"
|
||||||
|
|
||||||
method collide(a: TThing, b: TUnit) {.inline.} =
|
method collide(a: TThing, b: TUnit) {.inline.} =
|
||||||
echo "1"
|
echo "1"
|
||||||
|
|
||||||
method collide(a: TUnit, b: TThing) {.inline.} =
|
method collide(a: TUnit, b: TThing) {.inline.} =
|
||||||
echo "2"
|
echo "2"
|
||||||
|
|
||||||
var
|
var
|
||||||
a, b: TUnit
|
a, b: TUnit
|
||||||
collide(a, b) # output: 2
|
collide(a, b) # output: 2
|
||||||
|
|
@ -526,7 +526,7 @@ containers:
|
||||||
yield n.data
|
yield n.data
|
||||||
add(stack, n.ri) # push right subtree onto the stack
|
add(stack, n.ri) # push right subtree onto the stack
|
||||||
n = n.le # and follow the left pointer
|
n = n.le # and follow the left pointer
|
||||||
|
|
||||||
var
|
var
|
||||||
root: PBinaryTree[string] # instantiate a PBinaryTree with ``string``
|
root: PBinaryTree[string] # instantiate a PBinaryTree with ``string``
|
||||||
add(root, newNode("hello")) # instantiates ``newNode`` and ``add``
|
add(root, newNode("hello")) # instantiates ``newNode`` and ``add``
|
||||||
|
|
@ -578,7 +578,7 @@ simple proc for logging:
|
||||||
|
|
||||||
proc log(msg: string) {.inline.} =
|
proc log(msg: string) {.inline.} =
|
||||||
if debug: stdout.writeln(msg)
|
if debug: stdout.writeln(msg)
|
||||||
|
|
||||||
var
|
var
|
||||||
x = 4
|
x = 4
|
||||||
log("x has the value: " & $x)
|
log("x has the value: " & $x)
|
||||||
|
|
@ -595,7 +595,7 @@ Turning the ``log`` proc into a template solves this problem:
|
||||||
|
|
||||||
template log(msg: string) =
|
template log(msg: string) =
|
||||||
if debug: stdout.writeln(msg)
|
if debug: stdout.writeln(msg)
|
||||||
|
|
||||||
var
|
var
|
||||||
x = 4
|
x = 4
|
||||||
log("x has the value: " & $x)
|
log("x has the value: " & $x)
|
||||||
|
|
@ -622,11 +622,11 @@ via a special ``:`` syntax:
|
||||||
close(f)
|
close(f)
|
||||||
else:
|
else:
|
||||||
quit("cannot open: " & fn)
|
quit("cannot open: " & fn)
|
||||||
|
|
||||||
withFile(txt, "ttempl3.txt", fmWrite):
|
withFile(txt, "ttempl3.txt", fmWrite):
|
||||||
txt.writeln("line 1")
|
txt.writeln("line 1")
|
||||||
txt.writeln("line 2")
|
txt.writeln("line 2")
|
||||||
|
|
||||||
In the example the two ``writeln`` statements are bound to the ``body``
|
In the example the two ``writeln`` statements are bound to the ``body``
|
||||||
parameter. The ``withFile`` template contains boilerplate code and helps to
|
parameter. The ``withFile`` template contains boilerplate code and helps to
|
||||||
avoid a common bug: to forget to close the file. Note how the
|
avoid a common bug: to forget to close the file. Note how the
|
||||||
|
|
@ -739,7 +739,7 @@ Term rewriting macros
|
||||||
---------------------
|
---------------------
|
||||||
|
|
||||||
Term rewriting macros can be used to enhance the compilation process
|
Term rewriting macros can be used to enhance the compilation process
|
||||||
with user defined optimizations; see this `document <trmacros.html>`_ for
|
with user defined optimizations; see this `document <trmacros.html>`_ for
|
||||||
further information.
|
further information.
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -5,16 +5,16 @@ Home
|
||||||
Welcome to Nim
|
Welcome to Nim
|
||||||
--------------
|
--------------
|
||||||
|
|
||||||
**Nim** (formerly known as "Nimrod") is a statically typed, imperative
|
**Nim** (formerly known as "Nimrod") is a statically typed, imperative
|
||||||
programming language that tries to give the programmer ultimate power without
|
programming language that tries to give the programmer ultimate power without
|
||||||
compromises on runtime efficiency. This means it focuses on compile-time
|
compromises on runtime efficiency. This means it focuses on compile-time
|
||||||
mechanisms in all their various forms.
|
mechanisms in all their various forms.
|
||||||
|
|
||||||
Beneath a nice infix/indentation based syntax with a
|
Beneath a nice infix/indentation based syntax with a
|
||||||
powerful (AST based, hygienic) macro system lies a semantic model that supports
|
powerful (AST based, hygienic) macro system lies a semantic model that supports
|
||||||
a soft realtime GC on thread local heaps. Asynchronous message passing is used
|
a soft realtime GC on thread local heaps. Asynchronous message passing is used
|
||||||
between threads, so no "stop the world" mechanism is necessary. An unsafe
|
between threads, so no "stop the world" mechanism is necessary. An unsafe
|
||||||
shared memory heap is also provided for the increased efficiency that results
|
shared memory heap is also provided for the increased efficiency that results
|
||||||
from that model.
|
from that model.
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -24,7 +24,7 @@ Nim is efficient
|
||||||
* Native code generation (currently via compilation to C), not dependent on a
|
* Native code generation (currently via compilation to C), not dependent on a
|
||||||
virtual machine: **Nim produces small executables without dependencies
|
virtual machine: **Nim produces small executables without dependencies
|
||||||
for easy redistribution.**
|
for easy redistribution.**
|
||||||
* A fast **non-tracing** garbage collector that supports soft
|
* A fast **non-tracing** garbage collector that supports soft
|
||||||
real-time systems (like games).
|
real-time systems (like games).
|
||||||
* System programming features: Ability to manage your own memory and access the
|
* System programming features: Ability to manage your own memory and access the
|
||||||
hardware directly. Pointers to garbage collected memory are distinguished
|
hardware directly. Pointers to garbage collected memory are distinguished
|
||||||
|
|
@ -33,22 +33,22 @@ Nim is efficient
|
||||||
* Cross-module inlining.
|
* Cross-module inlining.
|
||||||
* Dynamic method binding with inlining and without virtual method table.
|
* Dynamic method binding with inlining and without virtual method table.
|
||||||
* Compile time evaluation of user-defined functions.
|
* Compile time evaluation of user-defined functions.
|
||||||
* Whole program dead code elimination: Only *used functions* are included in
|
* Whole program dead code elimination: Only *used functions* are included in
|
||||||
the executable.
|
the executable.
|
||||||
* Value-based datatypes: For instance, objects and arrays can be allocated on
|
* Value-based datatypes: For instance, objects and arrays can be allocated on
|
||||||
the stack.
|
the stack.
|
||||||
|
|
||||||
|
|
||||||
Nim is expressive
|
Nim is expressive
|
||||||
=================
|
=================
|
||||||
|
|
||||||
* **The Nim compiler and all of the standard library are implemented in
|
* **The Nim compiler and all of the standard libraries are implemented in
|
||||||
Nim.**
|
Nim.**
|
||||||
* Built-in high level datatypes: strings, sets, sequences, etc.
|
* Built-in high level datatypes: strings, sets, sequences, etc.
|
||||||
* Modern type system with local type inference, tuples, variants,
|
* Modern type system with local type inference, tuples, variants,
|
||||||
generics, etc.
|
generics, etc.
|
||||||
* User-defineable operators; code with new operators is often easier to read
|
* User-defineable operators; code with new operators is often easier to read
|
||||||
than code which overloads built-in operators. For example, a
|
than code which overloads built-in operators. For example, a
|
||||||
``=~`` operator is defined in the ``re`` module.
|
``=~`` operator is defined in the ``re`` module.
|
||||||
* Macros can modify the abstract syntax tree at compile time.
|
* Macros can modify the abstract syntax tree at compile time.
|
||||||
|
|
||||||
|
|
@ -58,7 +58,7 @@ Nim is elegant
|
||||||
|
|
||||||
* Macros can use the imperative paradigm to construct parse trees. Nim
|
* Macros can use the imperative paradigm to construct parse trees. Nim
|
||||||
does not require a different coding style for meta programming.
|
does not require a different coding style for meta programming.
|
||||||
* Macros cannot change Nim's syntax because there is no need for it.
|
* Macros cannot change Nim's syntax because there is no need for it.
|
||||||
Nim's syntax is flexible enough.
|
Nim's syntax is flexible enough.
|
||||||
* Statements are grouped by indentation but can span multiple lines.
|
* Statements are grouped by indentation but can span multiple lines.
|
||||||
Indentation must not contain tabulators so the compiler always sees
|
Indentation must not contain tabulators so the compiler always sees
|
||||||
|
|
@ -72,12 +72,12 @@ Nim plays nice with others
|
||||||
Porting to other platforms is easy.
|
Porting to other platforms is easy.
|
||||||
* **The Nim Compiler can also generate C++ or Objective C for easier
|
* **The Nim Compiler can also generate C++ or Objective C for easier
|
||||||
interfacing.**
|
interfacing.**
|
||||||
* There are lots of bindings: for example, bindings to GTK2, the Windows API,
|
* There are lots of bindings: for example, bindings to GTK2, the Windows API,
|
||||||
the POSIX API, OpenGL, SDL, Cairo, Python, Lua, TCL, X11, libzip, PCRE,
|
the POSIX API, OpenGL, SDL, Cairo, Python, Lua, TCL, X11, libzip, PCRE,
|
||||||
libcurl, mySQL and SQLite are included in the standard distribution or
|
libcurl, mySQL and SQLite are included in the standard distribution or
|
||||||
can easily be obtained via the
|
can easily be obtained via the
|
||||||
`Nimble package manager <https://github.com/nim-lang/nimble>`_.
|
`Nimble package manager <https://github.com/nim-lang/nimble>`_.
|
||||||
* A C to Nim conversion utility: New bindings to C libraries are easily
|
* A C to Nim conversion utility: New bindings to C libraries are easily
|
||||||
generated by ``c2nim``.
|
generated by ``c2nim``.
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue