tdeepcopy.nim 2.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. discard """
  2. output: "ok"
  3. """
  4. import tables, lists
  5. type
  6. ListTable[K, V] = object
  7. valList: DoublyLinkedList[V]
  8. table: Table[K, DoublyLinkedNode[V]]
  9. ListTableRef*[K, V] = ref ListTable[K, V]
  10. proc initListTable*[K, V](initialSize = 64): ListTable[K, V] =
  11. result.valList = initDoublyLinkedList[V]()
  12. result.table = initTable[K, DoublyLinkedNode[V]]()
  13. proc newListTable*[K, V](initialSize = 64): ListTableRef[K, V] =
  14. new(result)
  15. result[] = initListTable[K, V](initialSize)
  16. proc `[]=`*[K, V](t: var ListTable[K, V], key: K, val: V) =
  17. if key in t.table:
  18. t.table[key].value = val
  19. else:
  20. let node = newDoublyLinkedNode(val)
  21. t.valList.append(node)
  22. t.table[key] = node
  23. proc `[]`*[K, V](t: ListTable[K, V], key: K): var V {.inline.} =
  24. result = t.table[key].value
  25. proc len*[K, V](t: ListTable[K, V]): Natural {.inline.} =
  26. result = t.table.len
  27. iterator values*[K, V](t: ListTable[K, V]): V =
  28. for val in t.valList.items():
  29. yield val
  30. proc `[]=`*[K, V](t: ListTableRef[K, V], key: K, val: V) =
  31. t[][key] = val
  32. proc `[]`*[K, V](t: ListTableRef[K, V], key: K): var V {.inline.} =
  33. t[][key]
  34. proc len*[K, V](t: ListTableRef[K, V]): Natural {.inline.} =
  35. t[].len
  36. iterator values*[K, V](t: ListTableRef[K, V]): V =
  37. for val in t[].values:
  38. yield val
  39. proc main() =
  40. type SomeObj = ref object
  41. for outer in 0..10_000:
  42. let myObj = new(SomeObj)
  43. let table = newListTable[int, SomeObj]()
  44. table[0] = myObj
  45. for i in 1..100:
  46. table[i] = new(SomeObj)
  47. var myObj2: SomeObj
  48. for val in table.values():
  49. if myObj2.isNil:
  50. myObj2 = val
  51. doAssert(myObj == myObj2) # passes
  52. var tableCopy: ListTableRef[int, SomeObj]
  53. deepCopy(tableCopy, table)
  54. let myObjCopy = tableCopy[0]
  55. var myObjCopy2: SomeObj = nil
  56. for val in tableCopy.values():
  57. if myObjCopy2.isNil:
  58. myObjCopy2 = val
  59. #echo cast[int](myObj)
  60. #echo cast[int](myObjCopy)
  61. #echo cast[int](myObjCopy2)
  62. doAssert(myObjCopy == myObjCopy2) # fails
  63. type
  64. PtrTable = object
  65. counter, max: int
  66. data: array[0..99, (pointer, pointer)]
  67. doAssert(sizeof(PtrTable) == 2*sizeof(int)+sizeof(pointer)*2*100)
  68. main()
  69. echo "ok"