I'm a bit confused about the best way to deal with this error. My code looks 
something like the following:
    
    
    type
      Kind = enum
        kindA
        kindB
        kindC
      MyObject = object
        case kind: Kind
        of kindA:
          dataA: int
        of kindB:
          dataB: int
        of kindC:
          dataC1: int
          dataC2: int
        dataAll1: int
        dataAll2: int
        dataAll3: int
    
    
    proc foo(): MyObject =
      let kind = kindA
      
      if kind == kindA:
        result = MyObject(
          kind: kind,
          dataA: 1,
          dataAll1: 10,
          dataAll2: 20,
          dataAll3: 30
        )
      elif kind == kindB:
        result = MyObject(
          kind: kind,
          dataB: 2,
          dataAll1: 10,
          dataAll2: 20,
          dataAll3: 30
        )
      else:
        result = MyObject(
          kind: kind,
          dataC1: 3,
          dataC2: 4,
          dataAll1: 10,
          dataAll2: 20,
          dataAll3: 30
        )
    
    
    Run

which fails with: `you must provide a compile-time value for the discriminator 
'kind' in order to prove that it's safe to initialize 'dataA'`.

Interestingly, if I replace the if-else with a case statement, the code does 
compile; that's fine, I can use case if necessary. However this brings me to my 
next issue, which is that it does not feel very ergonomic to have to repeat the 
initialization of dataAll1-3 in each case despite having the same values.

One possible solution would be to extract dataAll1-3 into its own type (say a 
tuple) and initialize that separately, passing the same value in each case. 
Something like:
    
    
    type
      Kind = enum
        kindA
        kindB
        kindC
      MyObject = object
        case kind: Kind
        of kindA:
          dataA: int
        of kindB:
          dataB: int
        of kindC:
          dataC1: int
          dataC2: int
        dataAll: tuple[data1, data2, data3: int]
    
    proc foo(): MyObject =
      let kind = kindA
      
      let all = (10, 20, 30)
      
      case kind
      of kindA:
        result = MyObject(
          kind: kind,
          dataA: 1,
          dataAll: all
        )
      of kindB:
        result = MyObject(
          kind: kind,
          dataB: 2,
          dataAll: all
        )
      of kindC:
        result = MyObject(
          kind: kind,
          dataC1: 3,
          dataC2: 4,
          dataAll: all
        )
    
    
    Run

This works well enough in a simple case, but still doesn't feel very "good". 
The situation would be even worse if the three fields were not related (in 
which case it doesn't really make sense to group them together).

Does anyone have a more ergonomic way to solve this issue? Thanks!

Reply via email to