Cannonical way to do circular dependency in Nim
Asked Answered
E

1

5

Suppose we have two modules: one defines an Object and one defines an ObjectFactory. The Object needs to have access to the ObjectFactory use some of its functions, and the ObjectFactory needs access the Object to be able to instantiate Objects.

What is the cannonical way to solve this in Nim if the Object is implemented in a module and the ObjectFactory is implemented in another module?

Ecumenical answered 14/5, 2015 at 10:31 Comment(0)
M
8

I am assuming that the issue here is with mutually recursive types, i.e. where the declarations of two or more types refer to one another. Methods or procedures that refer to one another are handled fine by mutually recursive imports, though one has to be careful with module initialization in this case.

As in most other languages that normally require mutually recursive types to be within the same module/compilation unit, there are two principal answers.

One solution is to have the two types within the same module that is imported by both the module that declares the object type and the module that declares the factory type (both types still need to be part of the same type clause). E.g., you create a separate file, called something like factory_types.nim, and put both types in it:

type
  ObjectFactory = ref object
    lastValue: Object
    x: proc(): Object

  Object = ref object
    factory: ObjectFactory

This module would then be imported by both the module implementing the object and the module implementing the factory.

The other solution, where you can keep each type in its module, is parametric polymorphism, where a type parameter is used as a forward declaration. E.g., you do:

type
  ObjectFactory[TargetType] = ref object
    lastValue: TargetType
    generator: proc(): TargetType

and elsewhere:

type
  Object = ref object
    factory: ObjectFactory[Object]
Malachi answered 14/5, 2015 at 10:56 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.