ℹ️ Select 'Choose Exercise', or randomize 'Next Random Exercise' in selected language.

Choose Exercise:
Timer 00:00
WPM --
Score --
Acc --
Correct chars --

Nim Binary Serialization: Simple Struct

Nim

Goal -- WPM

Ready
Exercise Algorithm Area
1import streams
2import strutils
3import os
4
5type
6Person = object
7name: string
8age: int
9isStudent: bool
10
11proc serializePerson(p: Person, stream: Stream) =
12# Serialize name (length-prefixed string)
13let nameBytes = p.name.toOpenArray(0, p.name.len - 1)
14stream.write(int32(nameBytes.len))
15stream.write(nameBytes)
16
17# Serialize age (int, assume 32-bit, little-endian)
18stream.write(int32(p.age))
19
20# Serialize isStudent (bool, 1 byte)
21stream.write(bool(p.isStudent))
22
23proc deserializePerson(stream: Stream): Person =
24# Deserialize name
25var nameLen: int32
26stream.read(nameLen)
27if nameLen < 0 or nameLen > 1024: # Basic sanity check for string length
28raise newException(ValueError, "Invalid name length during deserialization.")
29var nameBytes = newSeq[byte](int(nameLen))
30stream.read(nameBytes)
31result.name = cast[string](nameBytes)
32
33# Deserialize age
34var age: int32
35stream.read(age)
36result.age = int(age)
37
38# Deserialize isStudent
39var isStudent: bool
40stream.read(isStudent)
41result.isStudent = isStudent
42
43proc main() =
44let originalPerson = Person(name: "Alice", age: 30, isStudent: false)
45echo "Original Person: ", originalPerson.name, ", ", originalPerson.age, ", ", originalPerson.isStudent
46
47# Use a memory stream for demonstration
48var memStream = newStringStream("")
49
50# Serialize
51serializePerson(originalPerson, memStream)
52echo "Serialized data length: ", memStream.len, " bytes"
53
54# Reset stream position for deserialization
55memStream.setPosition(0)
56
57# Deserialize
58let deserializedPerson = deserializePerson(memStream)
59echo "Deserialized Person: ", deserializedPerson.name, ", ", deserializedPerson.age, ", ", deserializedPerson.isStudent
60
61# Test with another person and edge cases
62let anotherPerson = Person(name: "Bob", age: 22, isStudent: true)
63memStream.reset() # Clear and reset
64serializePerson(anotherPerson, memStream)
65memStream.setPosition(0)
66let deserializedAnother = deserializePerson(memStream)
67echo "Deserialized Another: ", deserializedAnother.name, ", ", deserializedAnother.age, ", ", deserializedAnother.isStudent
68
69# Test empty string name
70let emptyNamePerson = Person(name: "", age: 5, isStudent: true)
71memStream.reset()
72serializePerson(emptyNamePerson, memStream)
73memStream.setPosition(0)
74let deserializedEmptyName = deserializePerson(memStream)
75echo "Deserialized Empty Name: ", deserializedEmptyName.name, ", ", deserializedEmptyName.age, ", ", deserializedEmptyName.isStudent
76
77main()
Algorithm description viewbox

Nim Binary Serialization: Simple Struct

Algorithm description:

This Nim code demonstrates binary serialization and deserialization for a custom `Person` object. It defines procedures to write the object's fields (string, int, bool) into a byte stream and read them back. This is crucial for saving/loading data, network communication, and inter-process communication where data needs to be represented in a compact, machine-readable format.

Algorithm explanation:

The `serializePerson` procedure writes the `Person` object's fields to a `Stream`. For the `name` string, it first writes its length as a 32-bit integer, followed by the raw bytes of the string. The `age` (an `int`) is written as a 32-bit integer, assuming little-endian byte order. The `isStudent` boolean is written as a single byte. The `deserializePerson` procedure reverses this process: it reads the name length, then the name bytes, then the age, and finally the boolean. Basic validation is included for string length during deserialization. The time complexity for both serialization and deserialization is O(L), where L is the length of the string field, as string operations dominate. Space complexity is O(L) for creating byte sequences during string handling. Edge cases like empty strings and different boolean values are handled.

Pseudocode:

Type Person:
  name: string
  age: integer
  isStudent: boolean

Procedure serializePerson(person, stream):
  Convert person.name to bytes
  Write length of name bytes to stream (as int32)
  Write name bytes to stream
  Write person.age to stream (as int32)
  Write person.isStudent to stream (as boolean)

Procedure deserializePerson(stream):
  Read name length (int32) from stream
  If name length is invalid, raise error
  Read name bytes from stream based on length
  Convert name bytes to string
  Read age (int32) from stream
  Read isStudent (boolean) from stream
  Return Person object with read values