Support array types. Updated documentation

This commit is contained in:
Felix Krause 2016-04-03 11:29:49 +02:00
parent a267f73e0a
commit f2c83cc170
3 changed files with 55 additions and 5 deletions

View File

@ -66,11 +66,11 @@ To support new scalar types, you must implement the ``constructObject()`` and
Collection Types Collection Types
---------------- ----------------
NimYAML supports Nim's ``seq`` and ``Table`` types out of the box. Unlike the NimYAML supports Nim's ``array``, ``set``, ``seq``, ``Table`` and
native YAML types ``!!seq`` and ``!!map``, ``seq`` and ``Table`` define the type ``OrderedTable`` types out of the box. Unlike the native YAML types ``!!seq``
of all their items (or keys and values). So YAML objects with heterogeneous and ``!!map``, Nim's collection types define the type of all their contained
types in them cannot be loaded to Nim collection types. For example, this items (or keys and values). So YAML objects with heterogeneous types in them
sequence: cannot be loaded to Nim collection types. For example, this sequence:
.. code-block:: yaml .. code-block:: yaml

View File

@ -259,6 +259,42 @@ proc representObject*[T](value: seq[T]|set[T], ts: TagStyle,
yield event yield event
yield endSeqEvent() yield endSeqEvent()
proc yamlTag*[I, V](T: typedesc[array[I, V]]): TagId {.inline, raises: [].} =
const rangeName = name(I)
let uri = "!nim:system:array(" & rangeName[6..rangeName.high()] & "," &
safeTagUri(yamlTag(V)) & ')'
result = lazyLoadTag(uri)
proc constructObject*[I, T](s: var YamlStream, c: ConstructionContext,
result: var array[I, T])
{.raises: [YamlConstructionError, YamlStreamError].} =
## constructs a Nim array from a YAML sequence
var event = s.next()
if event.kind != yamlStartSeq:
raise newException(YamlConstructionError, "Expected sequence start")
for index in low(I)..high(I):
event = s.peek()
if event.kind == yamlEndSeq:
raise newException(YamlConstructionError, "Too few array values")
constructChild(s, c, result[index])
event = s.next()
if event.kind != yamlEndSeq:
raise newException(YamlConstructionError, "Too much array values")
proc representObject*[I, T](value: array[I, T], ts: TagStyle,
c: SerializationContext, tag: TagId): RawYamlStream {.raises: [].} =
## represents a Nim array as YAML sequence
result = iterator(): YamlStreamEvent =
let childTagStyle = if ts == tsRootOnly: tsNone else: ts
yield startSeqEvent(tag)
for item in value:
var events = representChild(item, childTagStyle, c)
while true:
let event = events()
if finished(events): break
yield event
yield endSeqEvent()
proc yamlTag*[K, V](T: typedesc[Table[K, V]]): TagId {.inline, raises: [].} = proc yamlTag*[K, V](T: typedesc[Table[K, V]]): TagId {.inline, raises: [].} =
try: try:
let uri = "!nim:tables:Table(" & safeTagUri(yamlTag(K)) & "," & let uri = "!nim:tables:Table(" & safeTagUri(yamlTag(K)) & "," &

View File

@ -93,6 +93,20 @@ suite "Serialization":
dump(input, output, tsNone, asTidy, blockOnly) dump(input, output, tsNone, asTidy, blockOnly)
assertStringEqual "%YAML 1.2\n--- \n- a\n- b", output.data assertStringEqual "%YAML 1.2\n--- \n- a\n- b", output.data
test "Serialization: Load array":
let input = newStringStream("- 23\n- 42\n- 47")
var result: array[0..2, int32]
load(input, result)
assert result[0] == 23
assert result[1] == 42
assert result[2] == 47
test "Serialization: Represent array":
let input = [23'i32, 42'i32, 47'i32]
var output = newStringStream()
dump(input, output, tsNone, asTidy, blockOnly)
assertStringEqual "%YAML 1.2\n--- \n- 23\n- 42\n- 47", output.data
test "Serialization: Load Table[int, string]": test "Serialization: Load Table[int, string]":
let input = newStringStream("23: dreiundzwanzig\n42: zweiundvierzig") let input = newStringStream("23: dreiundzwanzig\n42: zweiundvierzig")
var result: Table[int32, string] var result: Table[int32, string]