tables.nim 48 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414
  1. #
  2. #
  3. # Nim's Runtime Library
  4. # (c) Copyright 2015 Andreas Rumpf
  5. #
  6. # See the file "copying.txt", included in this
  7. # distribution, for details about the copyright.
  8. #
  9. ## The ``tables`` module implements variants of an efficient `hash table`:idx:
  10. ## (also often named `dictionary`:idx: in other programming languages) that is
  11. ## a mapping from keys to values. ``Table`` is the usual hash table,
  12. ## ``OrderedTable`` is like ``Table`` but remembers insertion order
  13. ## and ``CountTable`` is a mapping from a key to its number of occurrences.
  14. ##
  15. ## For consistency with every other data type in Nim these have **value**
  16. ## semantics, this means that ``=`` performs a copy of the hash table.
  17. ## For **reference** semantics use the ``Ref`` variant: ``TableRef``,
  18. ## ``OrderedTableRef``, ``CountTableRef``.
  19. ##
  20. ## To give an example, when ``a`` is a Table, then ``var b = a`` gives ``b``
  21. ## as a new independent table. ``b`` is initialised with the contents of ``a``.
  22. ## Changing ``b`` does not affect ``a`` and vice versa:
  23. ##
  24. ## .. code-block::
  25. ## import tables
  26. ##
  27. ## var
  28. ## a = {1: "one", 2: "two"}.toTable # creates a Table
  29. ## b = a
  30. ##
  31. ## echo a, b # output: {1: one, 2: two}{1: one, 2: two}
  32. ##
  33. ## b[3] = "three"
  34. ## echo a, b # output: {1: one, 2: two}{1: one, 2: two, 3: three}
  35. ## echo a == b # output: false
  36. ##
  37. ## On the other hand, when ``a`` is a TableRef instead, then changes to ``b``
  38. ## also affect ``a``. Both ``a`` and ``b`` reference the same data structure:
  39. ##
  40. ## .. code-block::
  41. ## import tables
  42. ##
  43. ## var
  44. ## a = {1: "one", 2: "two"}.newTable # creates a TableRef
  45. ## b = a
  46. ##
  47. ## echo a, b # output: {1: one, 2: two}{1: one, 2: two}
  48. ##
  49. ## b[3] = "three"
  50. ## echo a, b # output: {1: one, 2: two, 3: three}{1: one, 2: two, 3: three}
  51. ## echo a == b # output: true
  52. ##
  53. ##
  54. ## Here is an example of ``CountTable`` usage:
  55. ##
  56. ## .. code-block:: nim
  57. ## let myString = "abracadabra"
  58. ## var myTable = initCountTable[char]()
  59. ##
  60. ## for c in myString:
  61. ## myTable.inc(c)
  62. ##
  63. ## echo myTable # output: {'a': 5, 'b': 2, 'c': 1, 'd': 1, 'r': 2}
  64. ##
  65. ##
  66. ## If you are using simple standard types like ``int`` or ``string`` for the
  67. ## keys of the table you won't have any problems, but as soon as you try to use
  68. ## a more complex object as a key you will be greeted by a strange compiler
  69. ## error::
  70. ##
  71. ## Error: type mismatch: got (Person)
  72. ## but expected one of:
  73. ## hashes.hash(x: openarray[A]): Hash
  74. ## hashes.hash(x: int): Hash
  75. ## hashes.hash(x: float): Hash
  76. ## …
  77. ##
  78. ## What is happening here is that the types used for table keys require to have
  79. ## a ``hash()`` proc which will convert them to a `Hash <hashes.html#Hash>`_
  80. ## value, and the compiler is listing all the hash functions it knows.
  81. ## Additionally there has to be a ``==`` operator that provides the same
  82. ## semantics as its corresponding ``hash`` proc.
  83. ##
  84. ## After you add ``hash`` and ``==`` for your custom type everything will work.
  85. ## Currently, however, ``hash`` for objects is not defined, whereas
  86. ## ``system.==`` for objects does exist and performs a "deep" comparison (every
  87. ## field is compared) which is usually what you want. So in the following
  88. ## example implementing only ``hash`` suffices:
  89. ##
  90. ## .. code-block::
  91. ## type
  92. ## Person = object
  93. ## firstName, lastName: string
  94. ##
  95. ## proc hash(x: Person): Hash =
  96. ## ## Piggyback on the already available string hash proc.
  97. ## ##
  98. ## ## Without this proc nothing works!
  99. ## result = x.firstName.hash !& x.lastName.hash
  100. ## result = !$result
  101. ##
  102. ## var
  103. ## salaries = initTable[Person, int]()
  104. ## p1, p2: Person
  105. ##
  106. ## p1.firstName = "Jon"
  107. ## p1.lastName = "Ross"
  108. ## salaries[p1] = 30_000
  109. ##
  110. ## p2.firstName = "소진"
  111. ## p2.lastName = "박"
  112. ## salaries[p2] = 45_000
  113. import
  114. hashes, math
  115. include "system/inclrtl"
  116. type
  117. KeyValuePair[A, B] = tuple[hcode: Hash, key: A, val: B]
  118. KeyValuePairSeq[A, B] = seq[KeyValuePair[A, B]]
  119. Table*[A, B] = object ## generic hash table
  120. data: KeyValuePairSeq[A, B]
  121. counter: int
  122. TableRef*[A,B] = ref Table[A, B]
  123. template maxHash(t): untyped = high(t.data)
  124. template dataLen(t): untyped = len(t.data)
  125. include tableimpl
  126. proc clear*[A, B](t: var Table[A, B]) =
  127. ## resets the table so that it is empty.
  128. clearImpl()
  129. proc clear*[A, B](t: TableRef[A, B]) =
  130. ## resets the ref table so that it is empty.
  131. clearImpl()
  132. proc rightSize*(count: Natural): int {.inline.} =
  133. ## return the value of ``initialSize`` to support ``count`` items.
  134. ##
  135. ## If more items are expected to be added, simply add that
  136. ## expected extra amount to the parameter before calling this.
  137. ##
  138. ## Internally, we want mustRehash(rightSize(x), x) == false.
  139. result = nextPowerOfTwo(count * 3 div 2 + 4)
  140. proc len*[A, B](t: Table[A, B]): int =
  141. ## returns the number of keys in ``t``.
  142. result = t.counter
  143. template get(t, key): untyped =
  144. ## retrieves the value at ``t[key]``. The value can be modified.
  145. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  146. mixin rawGet
  147. var hc: Hash
  148. var index = rawGet(t, key, hc)
  149. if index >= 0: result = t.data[index].val
  150. else:
  151. when compiles($key):
  152. raise newException(KeyError, "key not found: " & $key)
  153. else:
  154. raise newException(KeyError, "key not found")
  155. template getOrDefaultImpl(t, key): untyped =
  156. mixin rawGet
  157. var hc: Hash
  158. var index = rawGet(t, key, hc)
  159. if index >= 0: result = t.data[index].val
  160. template getOrDefaultImpl(t, key, default: untyped): untyped =
  161. mixin rawGet
  162. var hc: Hash
  163. var index = rawGet(t, key, hc)
  164. result = if index >= 0: t.data[index].val else: default
  165. proc `[]`*[A, B](t: Table[A, B], key: A): B {.deprecatedGet.} =
  166. ## retrieves the value at ``t[key]``. If ``key`` is not in ``t``, the
  167. ## ``KeyError`` exception is raised. One can check with ``hasKey`` whether
  168. ## the key exists.
  169. get(t, key)
  170. proc `[]`*[A, B](t: var Table[A, B], key: A): var B {.deprecatedGet.} =
  171. ## retrieves the value at ``t[key]``. The value can be modified.
  172. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  173. get(t, key)
  174. proc mget*[A, B](t: var Table[A, B], key: A): var B {.deprecated.} =
  175. ## retrieves the value at ``t[key]``. The value can be modified.
  176. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  177. ## Use ``[]`` instead.
  178. get(t, key)
  179. proc getOrDefault*[A, B](t: Table[A, B], key: A): B =
  180. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise, the
  181. ## default initialization value for type ``B`` is returned (e.g. 0 for any
  182. ## integer type).
  183. getOrDefaultImpl(t, key)
  184. proc getOrDefault*[A, B](t: Table[A, B], key: A, default: B): B =
  185. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``.
  186. ## Otherwise, ``default`` is returned.
  187. getOrDefaultImpl(t, key, default)
  188. template withValue*[A, B](t: var Table[A, B], key: A, value, body: untyped) =
  189. ## retrieves the value at ``t[key]``.
  190. ## ``value`` can be modified in the scope of the ``withValue`` call.
  191. ##
  192. ## .. code-block:: nim
  193. ##
  194. ## sharedTable.withValue(key, value) do:
  195. ## # block is executed only if ``key`` in ``t``
  196. ## value.name = "username"
  197. ## value.uid = 1000
  198. ##
  199. mixin rawGet
  200. var hc: Hash
  201. var index = rawGet(t, key, hc)
  202. let hasKey = index >= 0
  203. if hasKey:
  204. var value {.inject.} = addr(t.data[index].val)
  205. body
  206. template withValue*[A, B](t: var Table[A, B], key: A,
  207. value, body1, body2: untyped) =
  208. ## retrieves the value at ``t[key]``.
  209. ## ``value`` can be modified in the scope of the ``withValue`` call.
  210. ##
  211. ## .. code-block:: nim
  212. ##
  213. ## table.withValue(key, value) do:
  214. ## # block is executed only if ``key`` in ``t``
  215. ## value.name = "username"
  216. ## value.uid = 1000
  217. ## do:
  218. ## # block is executed when ``key`` not in ``t``
  219. ## raise newException(KeyError, "Key not found")
  220. ##
  221. mixin rawGet
  222. var hc: Hash
  223. var index = rawGet(t, key, hc)
  224. let hasKey = index >= 0
  225. if hasKey:
  226. var value {.inject.} = addr(t.data[index].val)
  227. body1
  228. else:
  229. body2
  230. iterator allValues*[A, B](t: Table[A, B]; key: A): B =
  231. ## iterates over any value in the table ``t`` that belongs to the given ``key``.
  232. var h: Hash = genHash(key) and high(t.data)
  233. while isFilled(t.data[h].hcode):
  234. if t.data[h].key == key:
  235. yield t.data[h].val
  236. h = nextTry(h, high(t.data))
  237. proc hasKey*[A, B](t: Table[A, B], key: A): bool =
  238. ## returns true iff ``key`` is in the table ``t``.
  239. var hc: Hash
  240. result = rawGet(t, key, hc) >= 0
  241. proc contains*[A, B](t: Table[A, B], key: A): bool =
  242. ## alias of ``hasKey`` for use with the ``in`` operator.
  243. return hasKey[A, B](t, key)
  244. iterator pairs*[A, B](t: Table[A, B]): (A, B) =
  245. ## iterates over any ``(key, value)`` pair in the table ``t``.
  246. for h in 0..high(t.data):
  247. if isFilled(t.data[h].hcode): yield (t.data[h].key, t.data[h].val)
  248. iterator mpairs*[A, B](t: var Table[A, B]): (A, var B) =
  249. ## iterates over any ``(key, value)`` pair in the table ``t``. The values
  250. ## can be modified.
  251. for h in 0..high(t.data):
  252. if isFilled(t.data[h].hcode): yield (t.data[h].key, t.data[h].val)
  253. iterator keys*[A, B](t: Table[A, B]): A =
  254. ## iterates over any key in the table ``t``.
  255. for h in 0..high(t.data):
  256. if isFilled(t.data[h].hcode): yield t.data[h].key
  257. iterator values*[A, B](t: Table[A, B]): B =
  258. ## iterates over any value in the table ``t``.
  259. for h in 0..high(t.data):
  260. if isFilled(t.data[h].hcode): yield t.data[h].val
  261. iterator mvalues*[A, B](t: var Table[A, B]): var B =
  262. ## iterates over any value in the table ``t``. The values can be modified.
  263. for h in 0..high(t.data):
  264. if isFilled(t.data[h].hcode): yield t.data[h].val
  265. proc del*[A, B](t: var Table[A, B], key: A) =
  266. ## deletes ``key`` from hash table ``t``. Does nothing if the key does not exist.
  267. delImpl()
  268. proc take*[A, B](t: var Table[A, B], key: A, val: var B): bool =
  269. ## deletes the ``key`` from the table.
  270. ## Returns ``true``, if the ``key`` existed, and sets ``val`` to the
  271. ## mapping of the key. Otherwise, returns ``false``, and the ``val`` is
  272. ## unchanged.
  273. var hc: Hash
  274. var index = rawGet(t, key, hc)
  275. result = index >= 0
  276. if result:
  277. shallowCopy(val, t.data[index].val)
  278. delImplIdx(t, index)
  279. proc enlarge[A, B](t: var Table[A, B]) =
  280. var n: KeyValuePairSeq[A, B]
  281. newSeq(n, len(t.data) * growthFactor)
  282. swap(t.data, n)
  283. for i in countup(0, high(n)):
  284. let eh = n[i].hcode
  285. if isFilled(eh):
  286. var j: Hash = eh and maxHash(t)
  287. while isFilled(t.data[j].hcode):
  288. j = nextTry(j, maxHash(t))
  289. rawInsert(t, t.data, n[i].key, n[i].val, eh, j)
  290. proc mgetOrPut*[A, B](t: var Table[A, B], key: A, val: B): var B =
  291. ## retrieves value at ``t[key]`` or puts ``val`` if not present, either way
  292. ## returning a value which can be modified.
  293. mgetOrPutImpl(enlarge)
  294. proc hasKeyOrPut*[A, B](t: var Table[A, B], key: A, val: B): bool =
  295. ## returns true iff ``key`` is in the table, otherwise inserts ``value``.
  296. hasKeyOrPutImpl(enlarge)
  297. proc `[]=`*[A, B](t: var Table[A, B], key: A, val: B) =
  298. ## puts a ``(key, value)`` pair into ``t``.
  299. putImpl(enlarge)
  300. proc add*[A, B](t: var Table[A, B], key: A, val: B) =
  301. ## puts a new ``(key, value)`` pair into ``t`` even if ``t[key]`` already exists.
  302. ## This can introduce duplicate keys into the table!
  303. addImpl(enlarge)
  304. proc len*[A, B](t: TableRef[A, B]): int =
  305. ## returns the number of keys in ``t``.
  306. result = t.counter
  307. proc initTable*[A, B](initialSize=64): Table[A, B] =
  308. ## creates a new hash table that is empty.
  309. ##
  310. ## ``initialSize`` needs to be a power of two. If you need to accept runtime
  311. ## values for this you could use the ``nextPowerOfTwo`` proc from the
  312. ## `math <math.html>`_ module or the ``rightSize`` proc from this module.
  313. assert isPowerOfTwo(initialSize)
  314. result.counter = 0
  315. newSeq(result.data, initialSize)
  316. proc toTable*[A, B](pairs: openArray[(A, B)]): Table[A, B] =
  317. ## creates a new hash table that contains the given ``pairs``.
  318. result = initTable[A, B](rightSize(pairs.len))
  319. for key, val in items(pairs): result[key] = val
  320. template dollarImpl(): untyped {.dirty.} =
  321. if t.len == 0:
  322. result = "{:}"
  323. else:
  324. result = "{"
  325. for key, val in pairs(t):
  326. if result.len > 1: result.add(", ")
  327. result.addQuoted(key)
  328. result.add(": ")
  329. result.addQuoted(val)
  330. result.add("}")
  331. proc `$`*[A, B](t: Table[A, B]): string =
  332. ## the ``$`` operator for hash tables.
  333. dollarImpl()
  334. proc hasKey*[A, B](t: TableRef[A, B], key: A): bool =
  335. ## returns true iff ``key`` is in the table ``t``.
  336. result = t[].hasKey(key)
  337. template equalsImpl(s, t: typed): typed =
  338. if s.counter == t.counter:
  339. # different insertion orders mean different 'data' seqs, so we have
  340. # to use the slow route here:
  341. for key, val in s:
  342. if not t.hasKey(key): return false
  343. if t.getOrDefault(key) != val: return false
  344. return true
  345. proc `==`*[A, B](s, t: Table[A, B]): bool =
  346. ## The ``==`` operator for hash tables. Returns ``true`` iff the content of both
  347. ## tables contains the same key-value pairs. Insert order does not matter.
  348. equalsImpl(s, t)
  349. proc indexBy*[A, B, C](collection: A, index: proc(x: B): C): Table[C, B] =
  350. ## Index the collection with the proc provided.
  351. # TODO: As soon as supported, change collection: A to collection: A[B]
  352. result = initTable[C, B]()
  353. for item in collection:
  354. result[index(item)] = item
  355. iterator pairs*[A, B](t: TableRef[A, B]): (A, B) =
  356. ## iterates over any ``(key, value)`` pair in the table ``t``.
  357. for h in 0..high(t.data):
  358. if isFilled(t.data[h].hcode): yield (t.data[h].key, t.data[h].val)
  359. iterator mpairs*[A, B](t: TableRef[A, B]): (A, var B) =
  360. ## iterates over any ``(key, value)`` pair in the table ``t``. The values
  361. ## can be modified.
  362. for h in 0..high(t.data):
  363. if isFilled(t.data[h].hcode): yield (t.data[h].key, t.data[h].val)
  364. iterator keys*[A, B](t: TableRef[A, B]): A =
  365. ## iterates over any key in the table ``t``.
  366. for h in 0..high(t.data):
  367. if isFilled(t.data[h].hcode): yield t.data[h].key
  368. iterator values*[A, B](t: TableRef[A, B]): B =
  369. ## iterates over any value in the table ``t``.
  370. for h in 0..high(t.data):
  371. if isFilled(t.data[h].hcode): yield t.data[h].val
  372. iterator mvalues*[A, B](t: TableRef[A, B]): var B =
  373. ## iterates over any value in the table ``t``. The values can be modified.
  374. for h in 0..high(t.data):
  375. if isFilled(t.data[h].hcode): yield t.data[h].val
  376. proc `[]`*[A, B](t: TableRef[A, B], key: A): var B {.deprecatedGet.} =
  377. ## retrieves the value at ``t[key]``. If ``key`` is not in ``t``, the
  378. ## ``KeyError`` exception is raised. One can check with ``hasKey`` whether
  379. ## the key exists.
  380. result = t[][key]
  381. proc mget*[A, B](t: TableRef[A, B], key: A): var B {.deprecated.} =
  382. ## retrieves the value at ``t[key]``. The value can be modified.
  383. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  384. ## Use ``[]`` instead.
  385. t[][key]
  386. proc getOrDefault*[A, B](t: TableRef[A, B], key: A): B =
  387. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise, the
  388. ## default initialization value for type ``B`` is returned (e.g. 0 for any
  389. ## integer type).
  390. getOrDefault(t[], key)
  391. proc getOrDefault*[A, B](t: TableRef[A, B], key: A, default: B): B =
  392. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``.
  393. ## Otherwise, ``default`` is returned.
  394. getOrDefault(t[], key, default)
  395. proc mgetOrPut*[A, B](t: TableRef[A, B], key: A, val: B): var B =
  396. ## retrieves value at ``t[key]`` or puts ``val`` if not present, either way
  397. ## returning a value which can be modified.
  398. t[].mgetOrPut(key, val)
  399. proc hasKeyOrPut*[A, B](t: var TableRef[A, B], key: A, val: B): bool =
  400. ## returns true iff ``key`` is in the table, otherwise inserts ``value``.
  401. t[].hasKeyOrPut(key, val)
  402. proc contains*[A, B](t: TableRef[A, B], key: A): bool =
  403. ## Alias of ``hasKey`` for use with the ``in`` operator.
  404. return hasKey[A, B](t, key)
  405. proc `[]=`*[A, B](t: TableRef[A, B], key: A, val: B) =
  406. ## puts a ``(key, value)`` pair into ``t``.
  407. t[][key] = val
  408. proc add*[A, B](t: TableRef[A, B], key: A, val: B) =
  409. ## puts a new ``(key, value)`` pair into ``t`` even if ``t[key]`` already exists.
  410. ## This can introduce duplicate keys into the table!
  411. t[].add(key, val)
  412. proc del*[A, B](t: TableRef[A, B], key: A) =
  413. ## deletes ``key`` from hash table ``t``. Does nothing if the key does not exist.
  414. t[].del(key)
  415. proc take*[A, B](t: TableRef[A, B], key: A, val: var B): bool =
  416. ## deletes the ``key`` from the table.
  417. ## Returns ``true``, if the ``key`` existed, and sets ``val`` to the
  418. ## mapping of the key. Otherwise, returns ``false``, and the ``val`` is
  419. ## unchanged.
  420. result = t[].take(key, val)
  421. proc newTable*[A, B](initialSize=64): TableRef[A, B] =
  422. new(result)
  423. result[] = initTable[A, B](initialSize)
  424. proc newTable*[A, B](pairs: openArray[(A, B)]): TableRef[A, B] =
  425. ## creates a new hash table that contains the given ``pairs``.
  426. new(result)
  427. result[] = toTable[A, B](pairs)
  428. proc `$`*[A, B](t: TableRef[A, B]): string =
  429. ## The ``$`` operator for hash tables.
  430. dollarImpl()
  431. proc `==`*[A, B](s, t: TableRef[A, B]): bool =
  432. ## The ``==`` operator for hash tables. Returns ``true`` iff either both tables
  433. ## are ``nil`` or none is ``nil`` and the content of both tables contains the
  434. ## same key-value pairs. Insert order does not matter.
  435. if isNil(s): result = isNil(t)
  436. elif isNil(t): result = false
  437. else: equalsImpl(s[], t[])
  438. proc newTableFrom*[A, B, C](collection: A, index: proc(x: B): C): TableRef[C, B] =
  439. ## Index the collection with the proc provided.
  440. # TODO: As soon as supported, change collection: A to collection: A[B]
  441. result = newTable[C, B]()
  442. for item in collection:
  443. result[index(item)] = item
  444. # ------------------------------ ordered table ------------------------------
  445. type
  446. OrderedKeyValuePair[A, B] = tuple[
  447. hcode: Hash, next: int, key: A, val: B]
  448. OrderedKeyValuePairSeq[A, B] = seq[OrderedKeyValuePair[A, B]]
  449. OrderedTable* [A, B] = object ## table that remembers insertion order
  450. data: OrderedKeyValuePairSeq[A, B]
  451. counter, first, last: int
  452. OrderedTableRef*[A, B] = ref OrderedTable[A, B]
  453. proc len*[A, B](t: OrderedTable[A, B]): int {.inline.} =
  454. ## returns the number of keys in ``t``.
  455. result = t.counter
  456. proc clear*[A, B](t: var OrderedTable[A, B]) =
  457. ## resets the table so that it is empty.
  458. clearImpl()
  459. t.first = -1
  460. t.last = -1
  461. proc clear*[A, B](t: var OrderedTableRef[A, B]) =
  462. ## resets the table so that is is empty.
  463. clear(t[])
  464. template forAllOrderedPairs(yieldStmt: untyped): typed {.dirty.} =
  465. var h = t.first
  466. while h >= 0:
  467. var nxt = t.data[h].next
  468. if isFilled(t.data[h].hcode): yieldStmt
  469. h = nxt
  470. iterator pairs*[A, B](t: OrderedTable[A, B]): (A, B) =
  471. ## iterates over any ``(key, value)`` pair in the table ``t`` in insertion
  472. ## order.
  473. forAllOrderedPairs:
  474. yield (t.data[h].key, t.data[h].val)
  475. iterator mpairs*[A, B](t: var OrderedTable[A, B]): (A, var B) =
  476. ## iterates over any ``(key, value)`` pair in the table ``t`` in insertion
  477. ## order. The values can be modified.
  478. forAllOrderedPairs:
  479. yield (t.data[h].key, t.data[h].val)
  480. iterator keys*[A, B](t: OrderedTable[A, B]): A =
  481. ## iterates over any key in the table ``t`` in insertion order.
  482. forAllOrderedPairs:
  483. yield t.data[h].key
  484. iterator values*[A, B](t: OrderedTable[A, B]): B =
  485. ## iterates over any value in the table ``t`` in insertion order.
  486. forAllOrderedPairs:
  487. yield t.data[h].val
  488. iterator mvalues*[A, B](t: var OrderedTable[A, B]): var B =
  489. ## iterates over any value in the table ``t`` in insertion order. The values
  490. ## can be modified.
  491. forAllOrderedPairs:
  492. yield t.data[h].val
  493. proc rawGetKnownHC[A, B](t: OrderedTable[A, B], key: A, hc: Hash): int =
  494. rawGetKnownHCImpl()
  495. proc rawGetDeep[A, B](t: OrderedTable[A, B], key: A, hc: var Hash): int {.inline.} =
  496. rawGetDeepImpl()
  497. proc rawGet[A, B](t: OrderedTable[A, B], key: A, hc: var Hash): int =
  498. rawGetImpl()
  499. proc `[]`*[A, B](t: OrderedTable[A, B], key: A): B {.deprecatedGet.} =
  500. ## retrieves the value at ``t[key]``. If ``key`` is not in ``t``, the
  501. ## ``KeyError`` exception is raised. One can check with ``hasKey`` whether
  502. ## the key exists.
  503. get(t, key)
  504. proc `[]`*[A, B](t: var OrderedTable[A, B], key: A): var B{.deprecatedGet.} =
  505. ## retrieves the value at ``t[key]``. The value can be modified.
  506. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  507. get(t, key)
  508. proc mget*[A, B](t: var OrderedTable[A, B], key: A): var B {.deprecated.} =
  509. ## retrieves the value at ``t[key]``. The value can be modified.
  510. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  511. ## Use ``[]`` instead.
  512. get(t, key)
  513. proc getOrDefault*[A, B](t: OrderedTable[A, B], key: A): B =
  514. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise, the
  515. ## default initialization value for type ``B`` is returned (e.g. 0 for any
  516. ## integer type).
  517. getOrDefaultImpl(t, key)
  518. proc getOrDefault*[A, B](t: OrderedTable[A, B], key: A, default: B): B =
  519. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise,
  520. ## ``default`` is returned.
  521. getOrDefaultImpl(t, key, default)
  522. proc hasKey*[A, B](t: OrderedTable[A, B], key: A): bool =
  523. ## returns true iff ``key`` is in the table ``t``.
  524. var hc: Hash
  525. result = rawGet(t, key, hc) >= 0
  526. proc contains*[A, B](t: OrderedTable[A, B], key: A): bool =
  527. ## Alias of ``hasKey`` for use with the ``in`` operator.
  528. return hasKey[A, B](t, key)
  529. proc rawInsert[A, B](t: var OrderedTable[A, B],
  530. data: var OrderedKeyValuePairSeq[A, B],
  531. key: A, val: B, hc: Hash, h: Hash) =
  532. rawInsertImpl()
  533. data[h].next = -1
  534. if t.first < 0: t.first = h
  535. if t.last >= 0: data[t.last].next = h
  536. t.last = h
  537. proc enlarge[A, B](t: var OrderedTable[A, B]) =
  538. var n: OrderedKeyValuePairSeq[A, B]
  539. newSeq(n, len(t.data) * growthFactor)
  540. var h = t.first
  541. t.first = -1
  542. t.last = -1
  543. swap(t.data, n)
  544. while h >= 0:
  545. var nxt = n[h].next
  546. let eh = n[h].hcode
  547. if isFilled(eh):
  548. var j: Hash = eh and maxHash(t)
  549. while isFilled(t.data[j].hcode):
  550. j = nextTry(j, maxHash(t))
  551. rawInsert(t, t.data, n[h].key, n[h].val, n[h].hcode, j)
  552. h = nxt
  553. proc `[]=`*[A, B](t: var OrderedTable[A, B], key: A, val: B) =
  554. ## puts a ``(key, value)`` pair into ``t``.
  555. putImpl(enlarge)
  556. proc add*[A, B](t: var OrderedTable[A, B], key: A, val: B) =
  557. ## puts a new ``(key, value)`` pair into ``t`` even if ``t[key]`` already exists.
  558. ## This can introduce duplicate keys into the table!
  559. addImpl(enlarge)
  560. proc mgetOrPut*[A, B](t: var OrderedTable[A, B], key: A, val: B): var B =
  561. ## retrieves value at ``t[key]`` or puts ``value`` if not present, either way
  562. ## returning a value which can be modified.
  563. mgetOrPutImpl(enlarge)
  564. proc hasKeyOrPut*[A, B](t: var OrderedTable[A, B], key: A, val: B): bool =
  565. ## returns true iff ``key`` is in the table, otherwise inserts ``value``.
  566. hasKeyOrPutImpl(enlarge)
  567. proc initOrderedTable*[A, B](initialSize=64): OrderedTable[A, B] =
  568. ## creates a new ordered hash table that is empty.
  569. ##
  570. ## ``initialSize`` needs to be a power of two. If you need to accept runtime
  571. ## values for this you could use the ``nextPowerOfTwo`` proc from the
  572. ## `math <math.html>`_ module or the ``rightSize`` proc from this module.
  573. assert isPowerOfTwo(initialSize)
  574. result.counter = 0
  575. result.first = -1
  576. result.last = -1
  577. newSeq(result.data, initialSize)
  578. proc toOrderedTable*[A, B](pairs: openArray[(A, B)]): OrderedTable[A, B] =
  579. ## creates a new ordered hash table that contains the given ``pairs``.
  580. result = initOrderedTable[A, B](rightSize(pairs.len))
  581. for key, val in items(pairs): result[key] = val
  582. proc `$`*[A, B](t: OrderedTable[A, B]): string =
  583. ## The ``$`` operator for ordered hash tables.
  584. dollarImpl()
  585. proc `==`*[A, B](s, t: OrderedTable[A, B]): bool =
  586. ## The ``==`` operator for ordered hash tables. Returns true iff both the
  587. ## content and the order are equal.
  588. if s.counter != t.counter:
  589. return false
  590. var ht = t.first
  591. var hs = s.first
  592. while ht >= 0 and hs >= 0:
  593. var nxtt = t.data[ht].next
  594. var nxts = s.data[hs].next
  595. if isFilled(t.data[ht].hcode) and isFilled(s.data[hs].hcode):
  596. if (s.data[hs].key != t.data[ht].key) or (s.data[hs].val != t.data[ht].val):
  597. return false
  598. ht = nxtt
  599. hs = nxts
  600. return true
  601. proc sort*[A, B](t: var OrderedTable[A, B], cmp: proc (x,y: (A, B)): int) =
  602. ## sorts ``t`` according to ``cmp``. This modifies the internal list
  603. ## that kept the insertion order, so insertion order is lost after this
  604. ## call but key lookup and insertions remain possible after ``sort`` (in
  605. ## contrast to the ``sort`` for count tables).
  606. var list = t.first
  607. var
  608. p, q, e, tail, oldhead: int
  609. nmerges, psize, qsize, i: int
  610. if t.counter == 0: return
  611. var insize = 1
  612. while true:
  613. p = list; oldhead = list
  614. list = -1; tail = -1; nmerges = 0
  615. while p >= 0:
  616. inc(nmerges)
  617. q = p
  618. psize = 0
  619. i = 0
  620. while i < insize:
  621. inc(psize)
  622. q = t.data[q].next
  623. if q < 0: break
  624. inc(i)
  625. qsize = insize
  626. while psize > 0 or (qsize > 0 and q >= 0):
  627. if psize == 0:
  628. e = q; q = t.data[q].next; dec(qsize)
  629. elif qsize == 0 or q < 0:
  630. e = p; p = t.data[p].next; dec(psize)
  631. elif cmp((t.data[p].key, t.data[p].val),
  632. (t.data[q].key, t.data[q].val)) <= 0:
  633. e = p; p = t.data[p].next; dec(psize)
  634. else:
  635. e = q; q = t.data[q].next; dec(qsize)
  636. if tail >= 0: t.data[tail].next = e
  637. else: list = e
  638. tail = e
  639. p = q
  640. t.data[tail].next = -1
  641. if nmerges <= 1: break
  642. insize = insize * 2
  643. t.first = list
  644. t.last = tail
  645. proc len*[A, B](t: OrderedTableRef[A, B]): int {.inline.} =
  646. ## returns the number of keys in ``t``.
  647. result = t.counter
  648. iterator pairs*[A, B](t: OrderedTableRef[A, B]): (A, B) =
  649. ## iterates over any ``(key, value)`` pair in the table ``t`` in insertion
  650. ## order.
  651. forAllOrderedPairs:
  652. yield (t.data[h].key, t.data[h].val)
  653. iterator mpairs*[A, B](t: OrderedTableRef[A, B]): (A, var B) =
  654. ## iterates over any ``(key, value)`` pair in the table ``t`` in insertion
  655. ## order. The values can be modified.
  656. forAllOrderedPairs:
  657. yield (t.data[h].key, t.data[h].val)
  658. iterator keys*[A, B](t: OrderedTableRef[A, B]): A =
  659. ## iterates over any key in the table ``t`` in insertion order.
  660. forAllOrderedPairs:
  661. yield t.data[h].key
  662. iterator values*[A, B](t: OrderedTableRef[A, B]): B =
  663. ## iterates over any value in the table ``t`` in insertion order.
  664. forAllOrderedPairs:
  665. yield t.data[h].val
  666. iterator mvalues*[A, B](t: OrderedTableRef[A, B]): var B =
  667. ## iterates over any value in the table ``t`` in insertion order. The values
  668. ## can be modified.
  669. forAllOrderedPairs:
  670. yield t.data[h].val
  671. proc `[]`*[A, B](t: OrderedTableRef[A, B], key: A): var B =
  672. ## retrieves the value at ``t[key]``. If ``key`` is not in ``t``, the
  673. ## ``KeyError`` exception is raised. One can check with ``hasKey`` whether
  674. ## the key exists.
  675. result = t[][key]
  676. proc mget*[A, B](t: OrderedTableRef[A, B], key: A): var B {.deprecated.} =
  677. ## retrieves the value at ``t[key]``. The value can be modified.
  678. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  679. ## Use ``[]`` instead.
  680. result = t[][key]
  681. proc getOrDefault*[A, B](t: OrderedTableRef[A, B], key: A): B =
  682. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise, the
  683. ## default initialization value for type ``B`` is returned (e.g. 0 for any
  684. ## integer type).
  685. getOrDefault(t[], key)
  686. proc getOrDefault*[A, B](t: OrderedTableRef[A, B], key: A, default: B): B =
  687. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise,
  688. ## ``default`` is returned.
  689. getOrDefault(t[], key, default)
  690. proc mgetOrPut*[A, B](t: OrderedTableRef[A, B], key: A, val: B): var B =
  691. ## retrieves value at ``t[key]`` or puts ``val`` if not present, either way
  692. ## returning a value which can be modified.
  693. result = t[].mgetOrPut(key, val)
  694. proc hasKeyOrPut*[A, B](t: var OrderedTableRef[A, B], key: A, val: B): bool =
  695. ## returns true iff ``key`` is in the table, otherwise inserts ``val``.
  696. result = t[].hasKeyOrPut(key, val)
  697. proc hasKey*[A, B](t: OrderedTableRef[A, B], key: A): bool =
  698. ## returns true iff ``key`` is in the table ``t``.
  699. result = t[].hasKey(key)
  700. proc contains*[A, B](t: OrderedTableRef[A, B], key: A): bool =
  701. ## Alias of ``hasKey`` for use with the ``in`` operator.
  702. return hasKey[A, B](t, key)
  703. proc `[]=`*[A, B](t: OrderedTableRef[A, B], key: A, val: B) =
  704. ## puts a ``(key, value)`` pair into ``t``.
  705. t[][key] = val
  706. proc add*[A, B](t: OrderedTableRef[A, B], key: A, val: B) =
  707. ## puts a new ``(key, value)`` pair into ``t`` even if ``t[key]`` already exists.
  708. ## This can introduce duplicate keys into the table!
  709. t[].add(key, val)
  710. proc newOrderedTable*[A, B](initialSize=64): OrderedTableRef[A, B] =
  711. ## creates a new ordered hash table that is empty.
  712. ##
  713. ## ``initialSize`` needs to be a power of two. If you need to accept runtime
  714. ## values for this you could use the ``nextPowerOfTwo`` proc from the
  715. ## `math <math.html>`_ module or the ``rightSize`` proc from this module.
  716. new(result)
  717. result[] = initOrderedTable[A, B](initialSize)
  718. proc newOrderedTable*[A, B](pairs: openArray[(A, B)]): OrderedTableRef[A, B] =
  719. ## creates a new ordered hash table that contains the given ``pairs``.
  720. result = newOrderedTable[A, B](rightSize(pairs.len))
  721. for key, val in items(pairs): result.add(key, val)
  722. proc `$`*[A, B](t: OrderedTableRef[A, B]): string =
  723. ## The ``$`` operator for ordered hash tables.
  724. dollarImpl()
  725. proc `==`*[A, B](s, t: OrderedTableRef[A, B]): bool =
  726. ## The ``==`` operator for ordered hash tables. Returns true iff either both
  727. ## tables are ``nil`` or none is ``nil`` and the content and the order of
  728. ## both are equal.
  729. if isNil(s): result = isNil(t)
  730. elif isNil(t): result = false
  731. else: result = s[] == t[]
  732. proc sort*[A, B](t: OrderedTableRef[A, B], cmp: proc (x,y: (A, B)): int) =
  733. ## sorts ``t`` according to ``cmp``. This modifies the internal list
  734. ## that kept the insertion order, so insertion order is lost after this
  735. ## call but key lookup and insertions remain possible after ``sort`` (in
  736. ## contrast to the ``sort`` for count tables).
  737. t[].sort(cmp)
  738. proc del*[A, B](t: var OrderedTable[A, B], key: A) =
  739. ## deletes ``key`` from ordered hash table ``t``. O(n) complexity. Does nothing
  740. ## if the key does not exist.
  741. var n: OrderedKeyValuePairSeq[A, B]
  742. newSeq(n, len(t.data))
  743. var h = t.first
  744. t.first = -1
  745. t.last = -1
  746. swap(t.data, n)
  747. let hc = genHash(key)
  748. while h >= 0:
  749. var nxt = n[h].next
  750. if isFilled(n[h].hcode):
  751. if n[h].hcode == hc and n[h].key == key:
  752. dec t.counter
  753. else:
  754. var j = -1 - rawGetKnownHC(t, n[h].key, n[h].hcode)
  755. rawInsert(t, t.data, n[h].key, n[h].val, n[h].hcode, j)
  756. h = nxt
  757. proc del*[A, B](t: var OrderedTableRef[A, B], key: A) =
  758. ## deletes ``key`` from ordered hash table ``t``. O(n) complexity. Does nothing
  759. ## if the key does not exist.
  760. t[].del(key)
  761. # ------------------------------ count tables -------------------------------
  762. type
  763. CountTable* [
  764. A] = object ## table that counts the number of each key
  765. data: seq[tuple[key: A, val: int]]
  766. counter: int
  767. CountTableRef*[A] = ref CountTable[A]
  768. proc len*[A](t: CountTable[A]): int =
  769. ## returns the number of keys in ``t``.
  770. result = t.counter
  771. proc clear*[A](t: CountTableRef[A]) =
  772. ## resets the table so that it is empty.
  773. clearImpl()
  774. proc clear*[A](t: var CountTable[A]) =
  775. ## resets the table so that it is empty.
  776. clearImpl()
  777. iterator pairs*[A](t: CountTable[A]): (A, int) =
  778. ## iterates over any ``(key, value)`` pair in the table ``t``.
  779. for h in 0..high(t.data):
  780. if t.data[h].val != 0: yield (t.data[h].key, t.data[h].val)
  781. iterator mpairs*[A](t: var CountTable[A]): (A, var int) =
  782. ## iterates over any ``(key, value)`` pair in the table ``t``. The values can
  783. ## be modified.
  784. for h in 0..high(t.data):
  785. if t.data[h].val != 0: yield (t.data[h].key, t.data[h].val)
  786. iterator keys*[A](t: CountTable[A]): A =
  787. ## iterates over any key in the table ``t``.
  788. for h in 0..high(t.data):
  789. if t.data[h].val != 0: yield t.data[h].key
  790. iterator values*[A](t: CountTable[A]): int =
  791. ## iterates over any value in the table ``t``.
  792. for h in 0..high(t.data):
  793. if t.data[h].val != 0: yield t.data[h].val
  794. iterator mvalues*[A](t: CountTable[A]): var int =
  795. ## iterates over any value in the table ``t``. The values can be modified.
  796. for h in 0..high(t.data):
  797. if t.data[h].val != 0: yield t.data[h].val
  798. proc rawGet[A](t: CountTable[A], key: A): int =
  799. var h: Hash = hash(key) and high(t.data) # start with real hash value
  800. while t.data[h].val != 0:
  801. if t.data[h].key == key: return h
  802. h = nextTry(h, high(t.data))
  803. result = -1 - h # < 0 => MISSING; insert idx = -1 - result
  804. template ctget(t, key: untyped): untyped =
  805. var index = rawGet(t, key)
  806. if index >= 0: result = t.data[index].val
  807. else:
  808. when compiles($key):
  809. raise newException(KeyError, "key not found: " & $key)
  810. else:
  811. raise newException(KeyError, "key not found")
  812. proc `[]`*[A](t: CountTable[A], key: A): int {.deprecatedGet.} =
  813. ## retrieves the value at ``t[key]``. If ``key`` is not in ``t``,
  814. ## the ``KeyError`` exception is raised. One can check with ``hasKey``
  815. ## whether the key exists.
  816. ctget(t, key)
  817. proc `[]`*[A](t: var CountTable[A], key: A): var int {.deprecatedGet.} =
  818. ## retrieves the value at ``t[key]``. The value can be modified.
  819. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  820. ctget(t, key)
  821. proc mget*[A](t: var CountTable[A], key: A): var int {.deprecated.} =
  822. ## retrieves the value at ``t[key]``. The value can be modified.
  823. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  824. ## Use ``[]`` instead.
  825. ctget(t, key)
  826. proc getOrDefault*[A](t: CountTable[A], key: A): int =
  827. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise, 0 (the
  828. ## default initialization value of ``int``), is returned.
  829. var index = rawGet(t, key)
  830. if index >= 0: result = t.data[index].val
  831. proc getOrDefault*[A](t: CountTable[A], key: A, default: int): int =
  832. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise, the
  833. ## integer value of ``default`` is returned.
  834. var index = rawGet(t, key)
  835. result = if index >= 0: t.data[index].val else: default
  836. proc hasKey*[A](t: CountTable[A], key: A): bool =
  837. ## returns true iff ``key`` is in the table ``t``.
  838. result = rawGet(t, key) >= 0
  839. proc contains*[A](t: CountTable[A], key: A): bool =
  840. ## Alias of ``hasKey`` for use with the ``in`` operator.
  841. return hasKey[A](t, key)
  842. proc rawInsert[A](t: CountTable[A], data: var seq[tuple[key: A, val: int]],
  843. key: A, val: int) =
  844. var h: Hash = hash(key) and high(data)
  845. while data[h].val != 0: h = nextTry(h, high(data))
  846. data[h].key = key
  847. data[h].val = val
  848. proc enlarge[A](t: var CountTable[A]) =
  849. var n: seq[tuple[key: A, val: int]]
  850. newSeq(n, len(t.data) * growthFactor)
  851. for i in countup(0, high(t.data)):
  852. if t.data[i].val != 0: rawInsert(t, n, t.data[i].key, t.data[i].val)
  853. swap(t.data, n)
  854. proc `[]=`*[A](t: var CountTable[A], key: A, val: int) =
  855. ## puts a ``(key, value)`` pair into ``t``.
  856. assert val >= 0
  857. var h = rawGet(t, key)
  858. if h >= 0:
  859. t.data[h].val = val
  860. else:
  861. if mustRehash(len(t.data), t.counter): enlarge(t)
  862. rawInsert(t, t.data, key, val)
  863. inc(t.counter)
  864. #h = -1 - h
  865. #t.data[h].key = key
  866. #t.data[h].val = val
  867. proc inc*[A](t: var CountTable[A], key: A, val = 1) =
  868. ## increments ``t[key]`` by ``val``.
  869. var index = rawGet(t, key)
  870. if index >= 0:
  871. inc(t.data[index].val, val)
  872. if t.data[index].val == 0: dec(t.counter)
  873. else:
  874. if mustRehash(len(t.data), t.counter): enlarge(t)
  875. rawInsert(t, t.data, key, val)
  876. inc(t.counter)
  877. proc initCountTable*[A](initialSize=64): CountTable[A] =
  878. ## creates a new count table that is empty.
  879. ##
  880. ## ``initialSize`` needs to be a power of two. If you need to accept runtime
  881. ## values for this you could use the ``nextPowerOfTwo`` proc from the
  882. ## `math <math.html>`_ module or the ``rightSize`` proc in this module.
  883. assert isPowerOfTwo(initialSize)
  884. result.counter = 0
  885. newSeq(result.data, initialSize)
  886. proc toCountTable*[A](keys: openArray[A]): CountTable[A] =
  887. ## creates a new count table with every key in ``keys`` having a count
  888. ## of how many times it occurs in ``keys``.
  889. result = initCountTable[A](rightSize(keys.len))
  890. for key in items(keys): result.inc(key)
  891. proc `$`*[A](t: CountTable[A]): string =
  892. ## The ``$`` operator for count tables.
  893. dollarImpl()
  894. proc `==`*[A](s, t: CountTable[A]): bool =
  895. ## The ``==`` operator for count tables. Returns ``true`` iff both tables
  896. ## contain the same keys with the same count. Insert order does not matter.
  897. equalsImpl(s, t)
  898. proc smallest*[A](t: CountTable[A]): tuple[key: A, val: int] =
  899. ## returns the ``(key, value)`` pair with the smallest ``val``. Efficiency: O(n)
  900. assert t.len > 0
  901. var minIdx = -1
  902. for h in 0..high(t.data):
  903. if t.data[h].val > 0 and (minIdx == -1 or t.data[minIdx].val > t.data[h].val):
  904. minIdx = h
  905. result.key = t.data[minIdx].key
  906. result.val = t.data[minIdx].val
  907. proc largest*[A](t: CountTable[A]): tuple[key: A, val: int] =
  908. ## returns the ``(key, value)`` pair with the largest ``val``. Efficiency: O(n)
  909. assert t.len > 0
  910. var maxIdx = 0
  911. for h in 1..high(t.data):
  912. if t.data[maxIdx].val < t.data[h].val: maxIdx = h
  913. result.key = t.data[maxIdx].key
  914. result.val = t.data[maxIdx].val
  915. proc sort*[A](t: var CountTable[A]) =
  916. ## sorts the count table so that the entry with the highest counter comes
  917. ## first. This is destructive! You must not modify ``t`` afterwards!
  918. ## You can use the iterators ``pairs``, ``keys``, and ``values`` to iterate over
  919. ## ``t`` in the sorted order.
  920. # we use shellsort here; fast enough and simple
  921. var h = 1
  922. while true:
  923. h = 3 * h + 1
  924. if h >= high(t.data): break
  925. while true:
  926. h = h div 3
  927. for i in countup(h, high(t.data)):
  928. var j = i
  929. while t.data[j-h].val <= t.data[j].val:
  930. swap(t.data[j], t.data[j-h])
  931. j = j-h
  932. if j < h: break
  933. if h == 1: break
  934. proc len*[A](t: CountTableRef[A]): int =
  935. ## returns the number of keys in ``t``.
  936. result = t.counter
  937. iterator pairs*[A](t: CountTableRef[A]): (A, int) =
  938. ## iterates over any ``(key, value)`` pair in the table ``t``.
  939. for h in 0..high(t.data):
  940. if t.data[h].val != 0: yield (t.data[h].key, t.data[h].val)
  941. iterator mpairs*[A](t: CountTableRef[A]): (A, var int) =
  942. ## iterates over any ``(key, value)`` pair in the table ``t``. The values can
  943. ## be modified.
  944. for h in 0..high(t.data):
  945. if t.data[h].val != 0: yield (t.data[h].key, t.data[h].val)
  946. iterator keys*[A](t: CountTableRef[A]): A =
  947. ## iterates over any key in the table ``t``.
  948. for h in 0..high(t.data):
  949. if t.data[h].val != 0: yield t.data[h].key
  950. iterator values*[A](t: CountTableRef[A]): int =
  951. ## iterates over any value in the table ``t``.
  952. for h in 0..high(t.data):
  953. if t.data[h].val != 0: yield t.data[h].val
  954. iterator mvalues*[A](t: CountTableRef[A]): var int =
  955. ## iterates over any value in the table ``t``. The values can be modified.
  956. for h in 0..high(t.data):
  957. if t.data[h].val != 0: yield t.data[h].val
  958. proc `[]`*[A](t: CountTableRef[A], key: A): var int {.deprecatedGet.} =
  959. ## retrieves the value at ``t[key]``. The value can be modified.
  960. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  961. result = t[][key]
  962. proc mget*[A](t: CountTableRef[A], key: A): var int {.deprecated.} =
  963. ## retrieves the value at ``t[key]``. The value can be modified.
  964. ## If ``key`` is not in ``t``, the ``KeyError`` exception is raised.
  965. ## Use ``[]`` instead.
  966. result = t[][key]
  967. proc getOrDefault*[A](t: CountTableRef[A], key: A): int =
  968. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise, 0 (the
  969. ## default initialization value of ``int``), is returned.
  970. result = t[].getOrDefault(key)
  971. proc getOrDefault*[A](t: CountTableRef[A], key: A, default: int): int =
  972. ## retrieves the value at ``t[key]`` iff ``key`` is in ``t``. Otherwise, the
  973. ## integer value of ``default`` is returned.
  974. result = t[].getOrDefault(key, default)
  975. proc hasKey*[A](t: CountTableRef[A], key: A): bool =
  976. ## returns true iff ``key`` is in the table ``t``.
  977. result = t[].hasKey(key)
  978. proc contains*[A](t: CountTableRef[A], key: A): bool =
  979. ## Alias of ``hasKey`` for use with the ``in`` operator.
  980. return hasKey[A](t, key)
  981. proc `[]=`*[A](t: CountTableRef[A], key: A, val: int) =
  982. ## puts a ``(key, value)`` pair into ``t``. ``val`` has to be positive.
  983. assert val > 0
  984. t[][key] = val
  985. proc inc*[A](t: CountTableRef[A], key: A, val = 1) =
  986. ## increments ``t[key]`` by ``val``.
  987. t[].inc(key, val)
  988. proc newCountTable*[A](initialSize=64): CountTableRef[A] =
  989. ## creates a new count table that is empty.
  990. ##
  991. ## ``initialSize`` needs to be a power of two. If you need to accept runtime
  992. ## values for this you could use the ``nextPowerOfTwo`` proc from the
  993. ## `math <math.html>`_ module or the ``rightSize`` method in this module.
  994. new(result)
  995. result[] = initCountTable[A](initialSize)
  996. proc newCountTable*[A](keys: openArray[A]): CountTableRef[A] =
  997. ## creates a new count table with every key in ``keys`` having a count
  998. ## of how many times it occurs in ``keys``.
  999. result = newCountTable[A](rightSize(keys.len))
  1000. for key in items(keys): result.inc(key)
  1001. proc `$`*[A](t: CountTableRef[A]): string =
  1002. ## The ``$`` operator for count tables.
  1003. dollarImpl()
  1004. proc `==`*[A](s, t: CountTableRef[A]): bool =
  1005. ## The ``==`` operator for count tables. Returns ``true`` iff either both tables
  1006. ## are ``nil`` or none is ``nil`` and both contain the same keys with the same
  1007. ## count. Insert order does not matter.
  1008. if isNil(s): result = isNil(t)
  1009. elif isNil(t): result = false
  1010. else: result = s[] == t[]
  1011. proc smallest*[A](t: CountTableRef[A]): (A, int) =
  1012. ## returns the ``(key, value)`` pair with the smallest ``val``. Efficiency: O(n)
  1013. t[].smallest
  1014. proc largest*[A](t: CountTableRef[A]): (A, int) =
  1015. ## returns the ``(key, value)`` pair with the largest ``val``. Efficiency: O(n)
  1016. t[].largest
  1017. proc sort*[A](t: CountTableRef[A]) =
  1018. ## sorts the count table so that the entry with the highest counter comes
  1019. ## first. This is destructive! You must not modify ``t`` afterwards!
  1020. ## You can use the iterators ``pairs``, ``keys``, and ``values`` to iterate over
  1021. ## ``t`` in the sorted order.
  1022. t[].sort
  1023. proc merge*[A](s: var CountTable[A], t: CountTable[A]) =
  1024. ## merges the second table into the first one.
  1025. for key, value in t:
  1026. s.inc(key, value)
  1027. proc merge*[A](s, t: CountTable[A]): CountTable[A] =
  1028. ## merges the two tables into a new one.
  1029. result = initCountTable[A](nextPowerOfTwo(max(s.len, t.len)))
  1030. for table in @[s, t]:
  1031. for key, value in table:
  1032. result.inc(key, value)
  1033. proc merge*[A](s, t: CountTableRef[A]) =
  1034. ## merges the second table into the first one.
  1035. s[].merge(t[])
  1036. when isMainModule:
  1037. type
  1038. Person = object
  1039. firstName, lastName: string
  1040. proc hash(x: Person): Hash =
  1041. ## Piggyback on the already available string hash proc.
  1042. ##
  1043. ## Without this proc nothing works!
  1044. result = x.firstName.hash !& x.lastName.hash
  1045. result = !$result
  1046. var
  1047. salaries = initTable[Person, int]()
  1048. p1, p2: Person
  1049. p1.firstName = "Jon"
  1050. p1.lastName = "Ross"
  1051. salaries[p1] = 30_000
  1052. p2.firstName = "소진"
  1053. p2.lastName = "박"
  1054. salaries[p2] = 45_000
  1055. var
  1056. s2 = initOrderedTable[Person, int]()
  1057. s3 = initCountTable[Person]()
  1058. s2[p1] = 30_000
  1059. s2[p2] = 45_000
  1060. s3[p1] = 30_000
  1061. s3[p2] = 45_000
  1062. block: # Ordered table should preserve order after deletion
  1063. var
  1064. s4 = initOrderedTable[int, int]()
  1065. s4[1] = 1
  1066. s4[2] = 2
  1067. s4[3] = 3
  1068. var prev = 0
  1069. for i in s4.values:
  1070. doAssert(prev < i)
  1071. prev = i
  1072. s4.del(2)
  1073. doAssert(2 notin s4)
  1074. doAssert(s4.len == 2)
  1075. prev = 0
  1076. for i in s4.values:
  1077. doAssert(prev < i)
  1078. prev = i
  1079. block: # Deletion from OrderedTable should account for collision groups. See issue #5057.
  1080. # The bug is reproducible only with exact keys
  1081. const key1 = "boy_jackpot.inGamma"
  1082. const key2 = "boy_jackpot.outBlack"
  1083. var t = {
  1084. key1: 0,
  1085. key2: 0
  1086. }.toOrderedTable()
  1087. t.del(key1)
  1088. assert(t.len == 1)
  1089. assert(key2 in t)
  1090. var
  1091. t1 = initCountTable[string]()
  1092. t2 = initCountTable[string]()
  1093. t1.inc("foo")
  1094. t1.inc("bar", 2)
  1095. t1.inc("baz", 3)
  1096. t2.inc("foo", 4)
  1097. t2.inc("bar")
  1098. t2.inc("baz", 11)
  1099. merge(t1, t2)
  1100. assert(t1["foo"] == 5)
  1101. assert(t1["bar"] == 3)
  1102. assert(t1["baz"] == 14)
  1103. let
  1104. t1r = newCountTable[string]()
  1105. t2r = newCountTable[string]()
  1106. t1r.inc("foo")
  1107. t1r.inc("bar", 2)
  1108. t1r.inc("baz", 3)
  1109. t2r.inc("foo", 4)
  1110. t2r.inc("bar")
  1111. t2r.inc("baz", 11)
  1112. merge(t1r, t2r)
  1113. assert(t1r["foo"] == 5)
  1114. assert(t1r["bar"] == 3)
  1115. assert(t1r["baz"] == 14)
  1116. var
  1117. t1l = initCountTable[string]()
  1118. t2l = initCountTable[string]()
  1119. t1l.inc("foo")
  1120. t1l.inc("bar", 2)
  1121. t1l.inc("baz", 3)
  1122. t2l.inc("foo", 4)
  1123. t2l.inc("bar")
  1124. t2l.inc("baz", 11)
  1125. let
  1126. t1merging = t1l
  1127. t2merging = t2l
  1128. let merged = merge(t1merging, t2merging)
  1129. assert(merged["foo"] == 5)
  1130. assert(merged["bar"] == 3)
  1131. assert(merged["baz"] == 14)
  1132. block:
  1133. const testKey = "TESTKEY"
  1134. let t: CountTableRef[string] = newCountTable[string]()
  1135. # Before, does not compile with error message:
  1136. #test_counttable.nim(7, 43) template/generic instantiation from here
  1137. #lib/pure/collections/tables.nim(117, 21) template/generic instantiation from here
  1138. #lib/pure/collections/tableimpl.nim(32, 27) Error: undeclared field: 'hcode
  1139. doAssert 0 == t.getOrDefault(testKey)
  1140. t.inc(testKey, 3)
  1141. doAssert 3 == t.getOrDefault(testKey)
  1142. block:
  1143. # Clear tests
  1144. var clearTable = newTable[int, string]()
  1145. clearTable[42] = "asd"
  1146. clearTable[123123] = "piuyqwb "
  1147. doAssert clearTable[42] == "asd"
  1148. clearTable.clear()
  1149. doAssert(not clearTable.hasKey(123123))
  1150. doAssert clearTable.getOrDefault(42) == ""
  1151. block: #5482
  1152. var a = [("wrong?","foo"), ("wrong?", "foo2")].newOrderedTable()
  1153. var b = newOrderedTable[string, string](initialSize=2)
  1154. b.add("wrong?", "foo")
  1155. b.add("wrong?", "foo2")
  1156. assert a == b
  1157. block: #5482
  1158. var a = {"wrong?": "foo", "wrong?": "foo2"}.newOrderedTable()
  1159. var b = newOrderedTable[string, string](initialSize=2)
  1160. b.add("wrong?", "foo")
  1161. b.add("wrong?", "foo2")
  1162. assert a == b
  1163. block: #5487
  1164. var a = {"wrong?": "foo", "wrong?": "foo2"}.newOrderedTable()
  1165. var b = newOrderedTable[string, string]() # notice, default size!
  1166. b.add("wrong?", "foo")
  1167. b.add("wrong?", "foo2")
  1168. assert a == b
  1169. block: #5487
  1170. var a = [("wrong?","foo"), ("wrong?", "foo2")].newOrderedTable()
  1171. var b = newOrderedTable[string, string]() # notice, default size!
  1172. b.add("wrong?", "foo")
  1173. b.add("wrong?", "foo2")
  1174. assert a == b
  1175. block:
  1176. var a = {"wrong?": "foo", "wrong?": "foo2"}.newOrderedTable()
  1177. var b = [("wrong?","foo"), ("wrong?", "foo2")].newOrderedTable()
  1178. var c = newOrderedTable[string, string]() # notice, default size!
  1179. c.add("wrong?", "foo")
  1180. c.add("wrong?", "foo2")
  1181. assert a == b
  1182. assert a == c
  1183. block: #6250
  1184. let
  1185. a = {3: 1}.toOrderedTable
  1186. b = {3: 2}.toOrderedTable
  1187. assert((a == b) == false)
  1188. assert((b == a) == false)
  1189. block: #6250
  1190. let
  1191. a = {3: 2}.toOrderedTable
  1192. b = {3: 2}.toOrderedTable
  1193. assert((a == b) == true)
  1194. assert((b == a) == true)
  1195. block: # CountTable.smallest
  1196. let t = toCountTable([0, 0, 5, 5, 5])
  1197. doAssert t.smallest == (0, 2)
  1198. block:
  1199. var tp: Table[string, string] = initTable[string, string]()
  1200. doAssert "test1" == tp.getOrDefault("test1", "test1")
  1201. tp["test2"] = "test2"
  1202. doAssert "test2" == tp.getOrDefault("test2", "test1")
  1203. var tr: TableRef[string, string] = newTable[string, string]()
  1204. doAssert "test1" == tr.getOrDefault("test1", "test1")
  1205. tr["test2"] = "test2"
  1206. doAssert "test2" == tr.getOrDefault("test2", "test1")
  1207. var op: OrderedTable[string, string] = initOrderedTable[string, string]()
  1208. doAssert "test1" == op.getOrDefault("test1", "test1")
  1209. op["test2"] = "test2"
  1210. doAssert "test2" == op.getOrDefault("test2", "test1")
  1211. var orf: OrderedTableRef[string, string] = newOrderedTable[string, string]()
  1212. doAssert "test1" == orf.getOrDefault("test1", "test1")
  1213. orf["test2"] = "test2"
  1214. doAssert "test2" == orf.getOrDefault("test2", "test1")