hamster 1.0.0 → 1.0.1.pre.rc.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (509) hide show
  1. checksums.yaml +4 -4
  2. data/lib/hamster.rb +2 -3
  3. data/lib/hamster/core_ext.rb +1 -0
  4. data/lib/hamster/core_ext/enumerable.rb +17 -17
  5. data/lib/hamster/core_ext/enumerator.rb +16 -0
  6. data/lib/hamster/core_ext/io.rb +17 -15
  7. data/lib/hamster/enumerable.rb +107 -123
  8. data/lib/hamster/experimental/mutable_queue.rb +6 -2
  9. data/lib/hamster/experimental/mutable_set.rb +3 -1
  10. data/lib/hamster/experimental/mutable_stack.rb +30 -0
  11. data/lib/hamster/hash.rb +95 -713
  12. data/lib/hamster/immutable.rb +0 -4
  13. data/lib/hamster/list.rb +242 -1062
  14. data/lib/hamster/mutable_hash.rb +3 -1
  15. data/lib/hamster/queue.rb +87 -0
  16. data/lib/hamster/read_copy_update.rb +1 -2
  17. data/lib/hamster/set.rb +73 -478
  18. data/lib/hamster/sorter.rb +25 -0
  19. data/lib/hamster/stack.rb +75 -0
  20. data/lib/hamster/trie.rb +48 -199
  21. data/lib/hamster/tuple.rb +39 -0
  22. data/lib/hamster/undefined.rb +3 -1
  23. data/lib/hamster/vector.rb +72 -1326
  24. data/lib/hamster/version.rb +1 -1
  25. data/spec/hamster/core_ext/array_spec.rb +20 -0
  26. data/spec/{lib/hamster → hamster}/core_ext/enumerable_spec.rb +0 -5
  27. data/spec/hamster/core_ext/enumerator_spec.rb +19 -0
  28. data/spec/{lib/hamster → hamster}/core_ext/io_spec.rb +0 -0
  29. data/spec/hamster/experimental/mutable_set/add_qm_spec.rb +47 -0
  30. data/spec/hamster/experimental/mutable_set/add_spec.rb +51 -0
  31. data/spec/hamster/experimental/mutable_set/delete_qm_spec.rb +47 -0
  32. data/spec/hamster/experimental/mutable_set/delete_spec.rb +47 -0
  33. data/spec/hamster/experimental/mutable_stack/pop_spec.rb +41 -0
  34. data/spec/hamster/experimental/mutable_stack/push_spec.rb +41 -0
  35. data/spec/hamster/hash/all_spec.rb +59 -0
  36. data/spec/hamster/hash/any_spec.rb +67 -0
  37. data/spec/hamster/hash/clear_spec.rb +36 -0
  38. data/spec/hamster/hash/construction_spec.rb +35 -0
  39. data/spec/{lib/hamster → hamster}/hash/copying_spec.rb +12 -3
  40. data/spec/hamster/hash/delete_spec.rb +47 -0
  41. data/spec/hamster/hash/each_spec.rb +41 -0
  42. data/spec/hamster/hash/empty_spec.rb +27 -0
  43. data/spec/hamster/hash/eql_spec.rb +62 -0
  44. data/spec/hamster/hash/except_spec.rb +31 -0
  45. data/spec/hamster/hash/fetch_spec.rb +95 -0
  46. data/spec/hamster/hash/filter_spec.rb +63 -0
  47. data/spec/hamster/hash/find_spec.rb +58 -0
  48. data/spec/hamster/hash/get_spec.rb +55 -0
  49. data/spec/hamster/hash/has_key_spec.rb +35 -0
  50. data/spec/hamster/hash/hash_spec.rb +52 -0
  51. data/spec/{lib/hamster → hamster}/hash/immutable_spec.rb +3 -0
  52. data/spec/hamster/hash/inspect_spec.rb +32 -0
  53. data/spec/hamster/hash/keys_spec.rb +21 -0
  54. data/spec/hamster/hash/map_spec.rb +64 -0
  55. data/spec/{lib/hamster → hamster}/hash/marshal_spec.rb +3 -3
  56. data/spec/hamster/hash/merge_spec.rb +36 -0
  57. data/spec/{lib/hamster → hamster}/hash/none_spec.rb +14 -12
  58. data/spec/hamster/hash/put_spec.rb +65 -0
  59. data/spec/hamster/hash/reduce_spec.rb +60 -0
  60. data/spec/hamster/hash/remove_spec.rb +63 -0
  61. data/spec/{lib/hamster → hamster}/hash/size_spec.rb +2 -2
  62. data/spec/hamster/hash/slice_spec.rb +26 -0
  63. data/spec/hamster/hash/uniq_spec.rb +23 -0
  64. data/spec/hamster/hash/values_spec.rb +34 -0
  65. data/spec/{lib/hamster → hamster}/immutable/copying_spec.rb +8 -1
  66. data/spec/{lib/hamster → hamster}/immutable/immutable_spec.rb +14 -1
  67. data/spec/{lib/hamster → hamster}/immutable/memoize_spec.rb +3 -2
  68. data/spec/{lib/hamster → hamster}/immutable/new_spec.rb +0 -0
  69. data/spec/{lib/hamster → hamster}/immutable/transform_spec.rb +0 -0
  70. data/spec/{lib/hamster → hamster}/immutable/transform_unless_spec.rb +0 -0
  71. data/spec/hamster/list/add_spec.rb +16 -0
  72. data/spec/hamster/list/all_spec.rb +111 -0
  73. data/spec/hamster/list/any_spec.rb +79 -0
  74. data/spec/{lib/hamster → hamster}/list/append_spec.rb +22 -11
  75. data/spec/hamster/list/at_spec.rb +49 -0
  76. data/spec/hamster/list/break_spec.rb +85 -0
  77. data/spec/{lib/hamster → hamster}/list/cadr_spec.rb +17 -6
  78. data/spec/{lib/hamster → hamster}/list/chunk_spec.rb +17 -6
  79. data/spec/{lib/hamster → hamster}/list/clear_spec.rb +16 -5
  80. data/spec/hamster/list/combinations_spec.rb +51 -0
  81. data/spec/{lib/hamster → hamster}/list/compact_spec.rb +17 -6
  82. data/spec/hamster/list/cons_spec.rb +41 -0
  83. data/spec/hamster/list/construction_spec.rb +166 -0
  84. data/spec/{lib/hamster → hamster}/list/copying_spec.rb +16 -4
  85. data/spec/hamster/list/count_spec.rb +66 -0
  86. data/spec/hamster/list/cycle_spec.rb +45 -0
  87. data/spec/{lib/hamster → hamster}/list/drop_spec.rb +17 -6
  88. data/spec/hamster/list/drop_while_spec.rb +59 -0
  89. data/spec/hamster/list/each_slice_spec.rb +80 -0
  90. data/spec/hamster/list/each_spec.rb +72 -0
  91. data/spec/hamster/list/each_with_index_spec.rb +42 -0
  92. data/spec/hamster/list/elem_index_spec.rb +58 -0
  93. data/spec/hamster/list/elem_indices_spec.rb +45 -0
  94. data/spec/hamster/list/empty_spec.rb +47 -0
  95. data/spec/hamster/list/eql_spec.rb +78 -0
  96. data/spec/hamster/list/filter_spec.rb +70 -0
  97. data/spec/{lib/hamster → hamster}/list/find_all_spec.rb +2 -3
  98. data/spec/{lib/hamster → hamster}/list/find_index_spec.rb +27 -5
  99. data/spec/hamster/list/find_indices_spec.rb +45 -0
  100. data/spec/{lib/hamster → hamster}/list/find_spec.rb +33 -11
  101. data/spec/{lib/hamster → hamster}/list/flat_map_spec.rb +0 -0
  102. data/spec/{lib/hamster → hamster}/list/flatten_spec.rb +17 -6
  103. data/spec/{lib/hamster → hamster}/list/grep_spec.rb +33 -10
  104. data/spec/{lib/hamster → hamster}/list/group_by_spec.rb +44 -9
  105. data/spec/{lib/hamster → hamster}/list/hash_spec.rb +12 -4
  106. data/spec/{lib/hamster → hamster}/list/head_spec.rb +18 -3
  107. data/spec/{lib/hamster → hamster}/list/include_spec.rb +27 -6
  108. data/spec/{lib/hamster → hamster}/list/init_spec.rb +17 -6
  109. data/spec/hamster/list/inits_spec.rb +42 -0
  110. data/spec/hamster/list/inspect_spec.rb +43 -0
  111. data/spec/{lib/hamster → hamster}/list/intersperse_spec.rb +17 -6
  112. data/spec/hamster/list/join_spec.rb +81 -0
  113. data/spec/hamster/list/last_spec.rb +44 -0
  114. data/spec/{lib/hamster → hamster}/list/map_spec.rb +35 -12
  115. data/spec/hamster/list/maximum_spec.rb +77 -0
  116. data/spec/{lib/hamster → hamster}/list/merge_by_spec.rb +32 -5
  117. data/spec/{lib/hamster → hamster}/list/merge_spec.rb +20 -1
  118. data/spec/hamster/list/minimum_spec.rb +77 -0
  119. data/spec/{lib/hamster → hamster}/list/none_spec.rb +39 -12
  120. data/spec/{lib/hamster → hamster}/list/one_spec.rb +38 -13
  121. data/spec/hamster/list/partition_spec.rb +75 -0
  122. data/spec/{lib/hamster → hamster}/list/pop_spec.rb +1 -1
  123. data/spec/hamster/list/product_spec.rb +44 -0
  124. data/spec/hamster/list/reduce_spec.rb +73 -0
  125. data/spec/{lib/hamster/list/reject_spec.rb → hamster/list/remove_spec.rb} +35 -11
  126. data/spec/{lib/hamster → hamster}/list/reverse_spec.rb +25 -8
  127. data/spec/{lib/hamster → hamster}/list/select_spec.rb +2 -3
  128. data/spec/{lib/hamster → hamster}/list/size_spec.rb +26 -5
  129. data/spec/hamster/list/slice_spec.rb +50 -0
  130. data/spec/{lib/hamster → hamster}/list/sorting_spec.rb +34 -11
  131. data/spec/hamster/list/span_spec.rb +86 -0
  132. data/spec/{lib/hamster → hamster}/list/split_at_spec.rb +23 -14
  133. data/spec/hamster/list/sum_spec.rb +44 -0
  134. data/spec/hamster/list/tail_spec.rb +48 -0
  135. data/spec/hamster/list/tails_spec.rb +42 -0
  136. data/spec/{lib/hamster → hamster}/list/take_spec.rb +17 -6
  137. data/spec/{lib/hamster → hamster}/list/take_while_spec.rb +18 -11
  138. data/spec/hamster/list/to_a_spec.rb +54 -0
  139. data/spec/{lib/hamster → hamster}/list/to_ary_spec.rb +4 -1
  140. data/spec/{lib/hamster → hamster}/list/to_list_spec.rb +16 -4
  141. data/spec/hamster/list/to_set_spec.rb +33 -0
  142. data/spec/{lib/hamster → hamster}/list/union_spec.rb +23 -6
  143. data/spec/hamster/list/uniq_spec.rb +45 -0
  144. data/spec/{lib/hamster → hamster}/list/zip_spec.rb +9 -2
  145. data/spec/hamster/queue/clear_spec.rb +36 -0
  146. data/spec/hamster/queue/construction_spec.rb +43 -0
  147. data/spec/hamster/queue/dequeue_spec.rb +40 -0
  148. data/spec/hamster/queue/empty_spec.rb +47 -0
  149. data/spec/{lib/hamster/deque → hamster/queue}/enqueue_spec.rb +21 -8
  150. data/spec/hamster/queue/head_spec.rb +35 -0
  151. data/spec/hamster/queue/inspect_spec.rb +31 -0
  152. data/spec/{lib/hamster/deque → hamster/queue}/size_spec.rb +20 -5
  153. data/spec/hamster/queue/to_a_spec.rb +42 -0
  154. data/spec/{lib/hamster/deque → hamster/queue}/to_ary_spec.rb +6 -6
  155. data/spec/hamster/queue/to_list_spec.rb +44 -0
  156. data/spec/hamster/set/add_spec.rb +51 -0
  157. data/spec/hamster/set/all_spec.rb +67 -0
  158. data/spec/hamster/set/any_spec.rb +67 -0
  159. data/spec/hamster/set/clear_spec.rb +36 -0
  160. data/spec/{lib/hamster → hamster}/set/compact_spec.rb +16 -5
  161. data/spec/{lib/hamster → hamster}/set/construction_spec.rb +17 -5
  162. data/spec/{lib/hamster → hamster}/set/copying_spec.rb +12 -3
  163. data/spec/{lib/hamster → hamster}/set/count_spec.rb +28 -11
  164. data/spec/hamster/set/delete_spec.rb +47 -0
  165. data/spec/{lib/hamster/sorted_set → hamster/set}/difference_spec.rb +21 -7
  166. data/spec/{lib/hamster/set/reverse_each_spec.rb → hamster/set/each_spec.rb} +7 -8
  167. data/spec/hamster/set/empty_spec.rb +35 -0
  168. data/spec/{lib/hamster → hamster}/set/eqeq_spec.rb +0 -0
  169. data/spec/{lib/hamster → hamster}/set/eql_spec.rb +1 -7
  170. data/spec/{lib/hamster/sorted_set → hamster/set}/exclusion_spec.rb +20 -5
  171. data/spec/hamster/set/filter_spec.rb +79 -0
  172. data/spec/{lib/hamster → hamster}/set/find_spec.rb +25 -8
  173. data/spec/hamster/set/flatten_spec.rb +49 -0
  174. data/spec/hamster/set/foreach_spec.rb +39 -0
  175. data/spec/{lib/hamster → hamster}/set/grep_spec.rb +1 -1
  176. data/spec/hamster/set/group_by_spec.rb +65 -0
  177. data/spec/hamster/set/hash_spec.rb +20 -0
  178. data/spec/hamster/set/head_spec.rb +39 -0
  179. data/spec/{lib/hamster → hamster}/set/immutable_spec.rb +4 -1
  180. data/spec/hamster/set/include_spec.rb +35 -0
  181. data/spec/hamster/set/inspect_spec.rb +32 -0
  182. data/spec/hamster/set/intersection_spec.rb +46 -0
  183. data/spec/{lib/hamster/vector → hamster/set}/join_spec.rb +33 -23
  184. data/spec/hamster/set/map_spec.rb +64 -0
  185. data/spec/{lib/hamster → hamster}/set/marshal_spec.rb +9 -4
  186. data/spec/hamster/set/maximum_spec.rb +65 -0
  187. data/spec/hamster/set/minimum_spec.rb +65 -0
  188. data/spec/{lib/hamster → hamster}/set/none_spec.rb +30 -15
  189. data/spec/{lib/hamster → hamster}/set/one_spec.rb +29 -14
  190. data/spec/hamster/set/partition_spec.rb +71 -0
  191. data/spec/{lib/hamster → hamster}/set/product_spec.rb +15 -7
  192. data/spec/hamster/set/reduce_spec.rb +87 -0
  193. data/spec/hamster/set/remove_spec.rb +63 -0
  194. data/spec/{lib/hamster → hamster}/set/size_spec.rb +10 -1
  195. data/spec/{lib/hamster → hamster}/set/sorting_spec.rb +16 -18
  196. data/spec/hamster/set/subset_spec.rb +39 -0
  197. data/spec/{lib/hamster/vector → hamster/set}/sum_spec.rb +18 -4
  198. data/spec/hamster/set/superset_spec.rb +39 -0
  199. data/spec/hamster/set/to_a_spec.rb +42 -0
  200. data/spec/{lib/hamster/vector → hamster/set}/to_list_spec.rb +23 -8
  201. data/spec/{lib/hamster → hamster}/set/to_set_spec.rb +15 -3
  202. data/spec/hamster/set/union_spec.rb +45 -0
  203. data/spec/hamster/set/uniq_spec.rb +23 -0
  204. data/spec/hamster/sorter/immutable_spec.rb +12 -0
  205. data/spec/hamster/stack/clear_spec.rb +36 -0
  206. data/spec/hamster/stack/construction_spec.rb +43 -0
  207. data/spec/hamster/stack/copying_spec.rb +31 -0
  208. data/spec/hamster/stack/empty_spec.rb +31 -0
  209. data/spec/hamster/stack/eql_spec.rb +60 -0
  210. data/spec/hamster/stack/immutable_spec.rb +12 -0
  211. data/spec/hamster/stack/inspect_spec.rb +31 -0
  212. data/spec/hamster/stack/peek_spec.rb +40 -0
  213. data/spec/hamster/stack/pop_spec.rb +41 -0
  214. data/spec/hamster/stack/push_spec.rb +41 -0
  215. data/spec/hamster/stack/size_spec.rb +35 -0
  216. data/spec/hamster/stack/to_a_spec.rb +42 -0
  217. data/spec/hamster/stack/to_ary.rb +37 -0
  218. data/spec/hamster/stack/to_list_spec.rb +33 -0
  219. data/spec/hamster/trie/remove_spec.rb +117 -0
  220. data/spec/hamster/tuple/copying_spec.rb +24 -0
  221. data/spec/hamster/tuple/eql_spec.rb +61 -0
  222. data/spec/hamster/tuple/first_spec.rb +19 -0
  223. data/spec/hamster/tuple/immutable_spec.rb +12 -0
  224. data/spec/hamster/tuple/inspect_spec.rb +19 -0
  225. data/spec/hamster/tuple/last_spec.rb +19 -0
  226. data/spec/hamster/tuple/to_a_spec.rb +38 -0
  227. data/spec/hamster/tuple/to_ary_spec.rb +38 -0
  228. data/spec/hamster/undefined/erase_spec.rb +47 -0
  229. data/spec/hamster/vector/add_spec.rb +48 -0
  230. data/spec/{lib/hamster → hamster}/vector/any_spec.rb +0 -0
  231. data/spec/hamster/vector/clear_spec.rb +35 -0
  232. data/spec/{lib/hamster → hamster}/vector/copying_spec.rb +14 -4
  233. data/spec/hamster/vector/each_spec.rb +45 -0
  234. data/spec/hamster/vector/each_with_index_spec.rb +41 -0
  235. data/spec/hamster/vector/empty_spec.rb +34 -0
  236. data/spec/hamster/vector/eql_spec.rb +64 -0
  237. data/spec/hamster/vector/filter_spec.rb +62 -0
  238. data/spec/hamster/vector/first_spec.rb +35 -0
  239. data/spec/hamster/vector/get_spec.rb +80 -0
  240. data/spec/{lib/hamster → hamster}/vector/include_spec.rb +17 -4
  241. data/spec/hamster/vector/inspect_spec.rb +33 -0
  242. data/spec/{lib/hamster → hamster}/vector/last_spec.rb +3 -12
  243. data/spec/{lib/hamster → hamster}/vector/length_spec.rb +3 -12
  244. data/spec/hamster/vector/map_spec.rb +63 -0
  245. data/spec/{lib/hamster → hamster}/vector/reduce_spec.rb +47 -16
  246. data/spec/hamster/vector/set_spec.rb +113 -0
  247. data/spec/{lib/hamster → hamster}/vector/to_a_spec.rb +12 -11
  248. data/spec/{lib/hamster → hamster}/vector/to_ary_spec.rb +0 -0
  249. data/spec/lib/hamster/vector/cons_spec.rb +48 -0
  250. data/spec/lib/hamster/vector/exist_spec.rb +70 -0
  251. data/spec/lib/hamster/vector/exists_spec.rb +70 -0
  252. data/spec/lib/hamster/vector/ltlt_spec.rb +2 -20
  253. data/spec/spec_helper.rb +5 -36
  254. metadata +510 -723
  255. data/lib/hamster/deque.rb +0 -252
  256. data/lib/hamster/nested.rb +0 -36
  257. data/lib/hamster/sorted_set.rb +0 -1397
  258. data/spec/lib/hamster/core_ext/array_spec.rb +0 -14
  259. data/spec/lib/hamster/deque/clear_spec.rb +0 -34
  260. data/spec/lib/hamster/deque/construction_spec.rb +0 -30
  261. data/spec/lib/hamster/deque/copying_spec.rb +0 -20
  262. data/spec/lib/hamster/deque/dequeue_spec.rb +0 -35
  263. data/spec/lib/hamster/deque/empty_spec.rb +0 -40
  264. data/spec/lib/hamster/deque/first_spec.rb +0 -18
  265. data/spec/lib/hamster/deque/inspect_spec.rb +0 -24
  266. data/spec/lib/hamster/deque/last_spec.rb +0 -18
  267. data/spec/lib/hamster/deque/marshal_spec.rb +0 -34
  268. data/spec/lib/hamster/deque/new_spec.rb +0 -44
  269. data/spec/lib/hamster/deque/pop_spec.rb +0 -33
  270. data/spec/lib/hamster/deque/pretty_print_spec.rb +0 -24
  271. data/spec/lib/hamster/deque/random_modification_spec.rb +0 -34
  272. data/spec/lib/hamster/deque/to_a_spec.rb +0 -27
  273. data/spec/lib/hamster/deque/to_list_spec.rb +0 -26
  274. data/spec/lib/hamster/deque/unshift_spec.rb +0 -26
  275. data/spec/lib/hamster/experimental/mutable_set/add_qm_spec.rb +0 -39
  276. data/spec/lib/hamster/experimental/mutable_set/add_spec.rb +0 -37
  277. data/spec/lib/hamster/experimental/mutable_set/delete_qm_spec.rb +0 -38
  278. data/spec/lib/hamster/experimental/mutable_set/delete_spec.rb +0 -37
  279. data/spec/lib/hamster/hash/all_spec.rb +0 -54
  280. data/spec/lib/hamster/hash/any_spec.rb +0 -54
  281. data/spec/lib/hamster/hash/assoc_spec.rb +0 -52
  282. data/spec/lib/hamster/hash/clear_spec.rb +0 -43
  283. data/spec/lib/hamster/hash/construction_spec.rb +0 -39
  284. data/spec/lib/hamster/hash/default_proc_spec.rb +0 -73
  285. data/spec/lib/hamster/hash/delete_spec.rb +0 -40
  286. data/spec/lib/hamster/hash/each_spec.rb +0 -78
  287. data/spec/lib/hamster/hash/each_with_index_spec.rb +0 -30
  288. data/spec/lib/hamster/hash/empty_spec.rb +0 -44
  289. data/spec/lib/hamster/hash/eql_spec.rb +0 -70
  290. data/spec/lib/hamster/hash/except_spec.rb +0 -43
  291. data/spec/lib/hamster/hash/fetch_spec.rb +0 -58
  292. data/spec/lib/hamster/hash/find_spec.rb +0 -44
  293. data/spec/lib/hamster/hash/flat_map_spec.rb +0 -36
  294. data/spec/lib/hamster/hash/flatten_spec.rb +0 -99
  295. data/spec/lib/hamster/hash/get_spec.rb +0 -80
  296. data/spec/lib/hamster/hash/has_key_spec.rb +0 -32
  297. data/spec/lib/hamster/hash/has_value_spec.rb +0 -28
  298. data/spec/lib/hamster/hash/hash_spec.rb +0 -30
  299. data/spec/lib/hamster/hash/inspect_spec.rb +0 -31
  300. data/spec/lib/hamster/hash/invert_spec.rb +0 -31
  301. data/spec/lib/hamster/hash/key_spec.rb +0 -28
  302. data/spec/lib/hamster/hash/keys_spec.rb +0 -17
  303. data/spec/lib/hamster/hash/map_spec.rb +0 -46
  304. data/spec/lib/hamster/hash/merge_spec.rb +0 -83
  305. data/spec/lib/hamster/hash/min_max_spec.rb +0 -46
  306. data/spec/lib/hamster/hash/new_spec.rb +0 -71
  307. data/spec/lib/hamster/hash/partition_spec.rb +0 -36
  308. data/spec/lib/hamster/hash/pretty_print_spec.rb +0 -35
  309. data/spec/lib/hamster/hash/put_spec.rb +0 -103
  310. data/spec/lib/hamster/hash/reduce_spec.rb +0 -36
  311. data/spec/lib/hamster/hash/reject_spec.rb +0 -62
  312. data/spec/lib/hamster/hash/reverse_each_spec.rb +0 -28
  313. data/spec/lib/hamster/hash/sample_spec.rb +0 -14
  314. data/spec/lib/hamster/hash/select_spec.rb +0 -58
  315. data/spec/lib/hamster/hash/slice_spec.rb +0 -45
  316. data/spec/lib/hamster/hash/sort_spec.rb +0 -27
  317. data/spec/lib/hamster/hash/store_spec.rb +0 -76
  318. data/spec/lib/hamster/hash/take_spec.rb +0 -36
  319. data/spec/lib/hamster/hash/to_a_spec.rb +0 -14
  320. data/spec/lib/hamster/hash/to_hash_spec.rb +0 -22
  321. data/spec/lib/hamster/hash/update_in_spec.rb +0 -80
  322. data/spec/lib/hamster/hash/values_at_spec.rb +0 -14
  323. data/spec/lib/hamster/hash/values_spec.rb +0 -25
  324. data/spec/lib/hamster/list/add_spec.rb +0 -26
  325. data/spec/lib/hamster/list/all_spec.rb +0 -58
  326. data/spec/lib/hamster/list/any_spec.rb +0 -50
  327. data/spec/lib/hamster/list/at_spec.rb +0 -30
  328. data/spec/lib/hamster/list/break_spec.rb +0 -70
  329. data/spec/lib/hamster/list/combination_spec.rb +0 -34
  330. data/spec/lib/hamster/list/compare_spec.rb +0 -31
  331. data/spec/lib/hamster/list/cons_spec.rb +0 -26
  332. data/spec/lib/hamster/list/construction_spec.rb +0 -111
  333. data/spec/lib/hamster/list/count_spec.rb +0 -37
  334. data/spec/lib/hamster/list/cycle_spec.rb +0 -29
  335. data/spec/lib/hamster/list/delete_at_spec.rb +0 -19
  336. data/spec/lib/hamster/list/delete_spec.rb +0 -17
  337. data/spec/lib/hamster/list/drop_while_spec.rb +0 -39
  338. data/spec/lib/hamster/list/each_slice_spec.rb +0 -52
  339. data/spec/lib/hamster/list/each_spec.rb +0 -41
  340. data/spec/lib/hamster/list/each_with_index_spec.rb +0 -29
  341. data/spec/lib/hamster/list/empty_spec.rb +0 -24
  342. data/spec/lib/hamster/list/eql_spec.rb +0 -62
  343. data/spec/lib/hamster/list/fill_spec.rb +0 -50
  344. data/spec/lib/hamster/list/index_spec.rb +0 -34
  345. data/spec/lib/hamster/list/indices_spec.rb +0 -62
  346. data/spec/lib/hamster/list/inits_spec.rb +0 -29
  347. data/spec/lib/hamster/list/insert_spec.rb +0 -47
  348. data/spec/lib/hamster/list/inspect_spec.rb +0 -30
  349. data/spec/lib/hamster/list/join_spec.rb +0 -64
  350. data/spec/lib/hamster/list/last_spec.rb +0 -24
  351. data/spec/lib/hamster/list/ltlt_spec.rb +0 -20
  352. data/spec/lib/hamster/list/maximum_spec.rb +0 -40
  353. data/spec/lib/hamster/list/minimum_spec.rb +0 -40
  354. data/spec/lib/hamster/list/multithreading_spec.rb +0 -48
  355. data/spec/lib/hamster/list/partition_spec.rb +0 -116
  356. data/spec/lib/hamster/list/permutation_spec.rb +0 -56
  357. data/spec/lib/hamster/list/product_spec.rb +0 -24
  358. data/spec/lib/hamster/list/reduce_spec.rb +0 -54
  359. data/spec/lib/hamster/list/rotate_spec.rb +0 -37
  360. data/spec/lib/hamster/list/sample_spec.rb +0 -14
  361. data/spec/lib/hamster/list/slice_spec.rb +0 -230
  362. data/spec/lib/hamster/list/span_spec.rb +0 -77
  363. data/spec/lib/hamster/list/subsequences_spec.rb +0 -24
  364. data/spec/lib/hamster/list/sum_spec.rb +0 -24
  365. data/spec/lib/hamster/list/tail_spec.rb +0 -31
  366. data/spec/lib/hamster/list/tails_spec.rb +0 -29
  367. data/spec/lib/hamster/list/to_a_spec.rb +0 -40
  368. data/spec/lib/hamster/list/to_set_spec.rb +0 -19
  369. data/spec/lib/hamster/list/transpose_spec.rb +0 -20
  370. data/spec/lib/hamster/list/uniq_spec.rb +0 -30
  371. data/spec/lib/hamster/nested/construction_spec.rb +0 -44
  372. data/spec/lib/hamster/set/add_spec.rb +0 -76
  373. data/spec/lib/hamster/set/all_spec.rb +0 -52
  374. data/spec/lib/hamster/set/any_spec.rb +0 -52
  375. data/spec/lib/hamster/set/clear_spec.rb +0 -34
  376. data/spec/lib/hamster/set/delete_spec.rb +0 -72
  377. data/spec/lib/hamster/set/difference_spec.rb +0 -50
  378. data/spec/lib/hamster/set/disjoint_spec.rb +0 -26
  379. data/spec/lib/hamster/set/each_spec.rb +0 -46
  380. data/spec/lib/hamster/set/empty_spec.rb +0 -45
  381. data/spec/lib/hamster/set/exclusion_spec.rb +0 -48
  382. data/spec/lib/hamster/set/first_spec.rb +0 -29
  383. data/spec/lib/hamster/set/flatten_spec.rb +0 -47
  384. data/spec/lib/hamster/set/group_by_spec.rb +0 -60
  385. data/spec/lib/hamster/set/hash_spec.rb +0 -23
  386. data/spec/lib/hamster/set/include_spec.rb +0 -61
  387. data/spec/lib/hamster/set/inspect_spec.rb +0 -48
  388. data/spec/lib/hamster/set/intersect_spec.rb +0 -26
  389. data/spec/lib/hamster/set/intersection_spec.rb +0 -53
  390. data/spec/lib/hamster/set/join_spec.rb +0 -65
  391. data/spec/lib/hamster/set/map_spec.rb +0 -60
  392. data/spec/lib/hamster/set/maximum_spec.rb +0 -37
  393. data/spec/lib/hamster/set/minimum_spec.rb +0 -37
  394. data/spec/lib/hamster/set/new_spec.rb +0 -54
  395. data/spec/lib/hamster/set/partition_spec.rb +0 -53
  396. data/spec/lib/hamster/set/reduce_spec.rb +0 -56
  397. data/spec/lib/hamster/set/reject_spec.rb +0 -51
  398. data/spec/lib/hamster/set/sample_spec.rb +0 -14
  399. data/spec/lib/hamster/set/select_spec.rb +0 -74
  400. data/spec/lib/hamster/set/subset_spec.rb +0 -52
  401. data/spec/lib/hamster/set/sum_spec.rb +0 -24
  402. data/spec/lib/hamster/set/superset_spec.rb +0 -52
  403. data/spec/lib/hamster/set/to_a_spec.rb +0 -31
  404. data/spec/lib/hamster/set/to_list_spec.rb +0 -37
  405. data/spec/lib/hamster/set/union_spec.rb +0 -64
  406. data/spec/lib/hamster/sorted_set/above_spec.rb +0 -52
  407. data/spec/lib/hamster/sorted_set/add_spec.rb +0 -63
  408. data/spec/lib/hamster/sorted_set/at_spec.rb +0 -25
  409. data/spec/lib/hamster/sorted_set/below_spec.rb +0 -52
  410. data/spec/lib/hamster/sorted_set/between_spec.rb +0 -52
  411. data/spec/lib/hamster/sorted_set/clear_spec.rb +0 -44
  412. data/spec/lib/hamster/sorted_set/construction_spec.rb +0 -29
  413. data/spec/lib/hamster/sorted_set/delete_at_spec.rb +0 -19
  414. data/spec/lib/hamster/sorted_set/delete_spec.rb +0 -90
  415. data/spec/lib/hamster/sorted_set/disjoint_spec.rb +0 -26
  416. data/spec/lib/hamster/sorted_set/drop_spec.rb +0 -56
  417. data/spec/lib/hamster/sorted_set/drop_while_spec.rb +0 -35
  418. data/spec/lib/hamster/sorted_set/each_spec.rb +0 -29
  419. data/spec/lib/hamster/sorted_set/empty_spec.rb +0 -35
  420. data/spec/lib/hamster/sorted_set/eql_spec.rb +0 -121
  421. data/spec/lib/hamster/sorted_set/fetch_spec.rb +0 -65
  422. data/spec/lib/hamster/sorted_set/find_index_spec.rb +0 -41
  423. data/spec/lib/hamster/sorted_set/first_spec.rb +0 -19
  424. data/spec/lib/hamster/sorted_set/from_spec.rb +0 -52
  425. data/spec/lib/hamster/sorted_set/group_by_spec.rb +0 -58
  426. data/spec/lib/hamster/sorted_set/include_spec.rb +0 -24
  427. data/spec/lib/hamster/sorted_set/inspect_spec.rb +0 -38
  428. data/spec/lib/hamster/sorted_set/intersect_spec.rb +0 -26
  429. data/spec/lib/hamster/sorted_set/intersection_spec.rb +0 -29
  430. data/spec/lib/hamster/sorted_set/last_spec.rb +0 -37
  431. data/spec/lib/hamster/sorted_set/map_spec.rb +0 -36
  432. data/spec/lib/hamster/sorted_set/marshal_spec.rb +0 -37
  433. data/spec/lib/hamster/sorted_set/maximum_spec.rb +0 -37
  434. data/spec/lib/hamster/sorted_set/minimum_spec.rb +0 -20
  435. data/spec/lib/hamster/sorted_set/new_spec.rb +0 -52
  436. data/spec/lib/hamster/sorted_set/reverse_each_spec.rb +0 -29
  437. data/spec/lib/hamster/sorted_set/sample_spec.rb +0 -14
  438. data/spec/lib/hamster/sorted_set/select_spec.rb +0 -62
  439. data/spec/lib/hamster/sorted_set/size_spec.rb +0 -18
  440. data/spec/lib/hamster/sorted_set/slice_spec.rb +0 -257
  441. data/spec/lib/hamster/sorted_set/sorting_spec.rb +0 -45
  442. data/spec/lib/hamster/sorted_set/subset_spec.rb +0 -48
  443. data/spec/lib/hamster/sorted_set/superset_spec.rb +0 -48
  444. data/spec/lib/hamster/sorted_set/take_spec.rb +0 -55
  445. data/spec/lib/hamster/sorted_set/take_while_spec.rb +0 -34
  446. data/spec/lib/hamster/sorted_set/to_set_spec.rb +0 -19
  447. data/spec/lib/hamster/sorted_set/union_spec.rb +0 -28
  448. data/spec/lib/hamster/sorted_set/up_to_spec.rb +0 -52
  449. data/spec/lib/hamster/sorted_set/values_at_spec.rb +0 -34
  450. data/spec/lib/hamster/vector/add_spec.rb +0 -68
  451. data/spec/lib/hamster/vector/assoc_spec.rb +0 -36
  452. data/spec/lib/hamster/vector/bsearch_spec.rb +0 -58
  453. data/spec/lib/hamster/vector/clear_spec.rb +0 -34
  454. data/spec/lib/hamster/vector/combination_spec.rb +0 -82
  455. data/spec/lib/hamster/vector/compact_spec.rb +0 -30
  456. data/spec/lib/hamster/vector/compare_spec.rb +0 -32
  457. data/spec/lib/hamster/vector/concat_spec.rb +0 -35
  458. data/spec/lib/hamster/vector/count_spec.rb +0 -18
  459. data/spec/lib/hamster/vector/delete_at_spec.rb +0 -54
  460. data/spec/lib/hamster/vector/delete_spec.rb +0 -31
  461. data/spec/lib/hamster/vector/drop_spec.rb +0 -42
  462. data/spec/lib/hamster/vector/drop_while_spec.rb +0 -55
  463. data/spec/lib/hamster/vector/each_index_spec.rb +0 -41
  464. data/spec/lib/hamster/vector/each_spec.rb +0 -45
  465. data/spec/lib/hamster/vector/each_with_index_spec.rb +0 -40
  466. data/spec/lib/hamster/vector/empty_spec.rb +0 -42
  467. data/spec/lib/hamster/vector/eql_spec.rb +0 -77
  468. data/spec/lib/hamster/vector/fetch_spec.rb +0 -65
  469. data/spec/lib/hamster/vector/fill_spec.rb +0 -89
  470. data/spec/lib/hamster/vector/first_spec.rb +0 -19
  471. data/spec/lib/hamster/vector/flat_map_spec.rb +0 -51
  472. data/spec/lib/hamster/vector/flatten_spec.rb +0 -44
  473. data/spec/lib/hamster/vector/get_spec.rb +0 -75
  474. data/spec/lib/hamster/vector/group_by_spec.rb +0 -58
  475. data/spec/lib/hamster/vector/insert_spec.rb +0 -69
  476. data/spec/lib/hamster/vector/inspect_spec.rb +0 -50
  477. data/spec/lib/hamster/vector/map_spec.rb +0 -52
  478. data/spec/lib/hamster/vector/marshal_spec.rb +0 -32
  479. data/spec/lib/hamster/vector/maximum_spec.rb +0 -34
  480. data/spec/lib/hamster/vector/minimum_spec.rb +0 -34
  481. data/spec/lib/hamster/vector/multiply_spec.rb +0 -48
  482. data/spec/lib/hamster/vector/new_spec.rb +0 -51
  483. data/spec/lib/hamster/vector/partition_spec.rb +0 -53
  484. data/spec/lib/hamster/vector/permutation_spec.rb +0 -92
  485. data/spec/lib/hamster/vector/pop_spec.rb +0 -27
  486. data/spec/lib/hamster/vector/product_spec.rb +0 -71
  487. data/spec/lib/hamster/vector/reject_spec.rb +0 -44
  488. data/spec/lib/hamster/vector/repeated_combination_spec.rb +0 -78
  489. data/spec/lib/hamster/vector/repeated_permutation_spec.rb +0 -94
  490. data/spec/lib/hamster/vector/reverse_each_spec.rb +0 -32
  491. data/spec/lib/hamster/vector/reverse_spec.rb +0 -22
  492. data/spec/lib/hamster/vector/rindex_spec.rb +0 -37
  493. data/spec/lib/hamster/vector/rotate_spec.rb +0 -74
  494. data/spec/lib/hamster/vector/sample_spec.rb +0 -14
  495. data/spec/lib/hamster/vector/select_spec.rb +0 -64
  496. data/spec/lib/hamster/vector/set_spec.rb +0 -175
  497. data/spec/lib/hamster/vector/shift_spec.rb +0 -28
  498. data/spec/lib/hamster/vector/shuffle_spec.rb +0 -44
  499. data/spec/lib/hamster/vector/slice_spec.rb +0 -241
  500. data/spec/lib/hamster/vector/sorting_spec.rb +0 -57
  501. data/spec/lib/hamster/vector/take_spec.rb +0 -43
  502. data/spec/lib/hamster/vector/take_while_spec.rb +0 -35
  503. data/spec/lib/hamster/vector/to_set_spec.rb +0 -23
  504. data/spec/lib/hamster/vector/transpose_spec.rb +0 -49
  505. data/spec/lib/hamster/vector/uniq_spec.rb +0 -56
  506. data/spec/lib/hamster/vector/unshift_spec.rb +0 -29
  507. data/spec/lib/hamster/vector/update_in_spec.rb +0 -83
  508. data/spec/lib/hamster/vector/values_at_spec.rb +0 -34
  509. data/spec/lib/hamster/vector/zip_spec.rb +0 -58
@@ -1,823 +1,205 @@
1
+ require "forwardable"
2
+
1
3
  require "hamster/immutable"
2
4
  require "hamster/undefined"
3
- require "hamster/enumerable"
4
5
  require "hamster/trie"
5
- require "hamster/set"
6
- require "hamster/vector"
6
+ require "hamster/list"
7
7
 
8
8
  module Hamster
9
- def self.hash(pairs = nil, &block)
10
- (pairs.nil? && block.nil?) ? EmptyHash : Hash.new(pairs, &block)
9
+ def self.hash(pairs = {}, &block)
10
+ Hash.new(pairs, &block)
11
11
  end
12
12
 
13
- # A `Hamster::Hash` maps from a set of unique keys to corresponding values,
14
- # much like a dictionary maps from words to definitions. Given a key, it can
15
- # efficiently store and retrieve values. Looking up a key given its value is also
16
- # possible, but less efficient. If an existing key is stored again, the new value
17
- # will replace that which was previously stored.
18
- #
19
- # It behaves much like Ruby's built-in Hash, which we will call RubyHash
20
- # for clarity. Like RubyHash, `Hamster::Hash` uses `#hash` and `#eql?` to define
21
- # equality between keys. Keys with the same `#hash` code, but which are not `#eql?`
22
- # to each other, can coexist in the same `Hamster::Hash`. To retrieve a previously
23
- # stored value, the key provided must have the same `#hash` code and be `#eql?`
24
- # to the one used for storage.
25
- #
26
- # A `Hamster::Hash` can be created in several ways:
27
- #
28
- # Hamster.hash('Jane Doe' => 10, 'Jim Doe' => 6)
29
- # Hamster::Hash.new(font_size: 10, font_family: 'Arial')
30
- # Hamster::Hash[first_name: 'John', last_name: 'Smith']
31
- #
32
- # If you want to write your own class which inherits from `Hamster::Hash`, you can
33
- # use either of the latter 2 forms of initialization.
34
- #
35
- # Note that any `Enumerable` object which yields 2-element `[key, value]` arrays
36
- # can be used to initialize a `Hamster::Hash`. So this is also possible:
37
- #
38
- # Hamster::Hash.new([[:first_name, 'John'], [:last_name, 'Smith']])
39
- #
40
- # Like RubyHash, key/value pairs can be added using {#store}. Unlike RubyHash,
41
- # a new hash is returned, and the existing one is left unchanged:
42
- #
43
- # hash = Hamster::Hash[a: 100, b: 200]
44
- # hash.store(:c, 500) # => Hamster::Hash[:a => 100, :b => 200, :c => 500]
45
- # hash # => Hamster::Hash[:a => 100, :b => 200]
46
- #
47
- # You also use {#put}. The difference is that {#put} can optionally take a block which
48
- # is used to calculate the value to be stored:
49
- #
50
- # hash.put(:a) { hash[:b] + 100 } # => Hamster::Hash[:a => 300, :b => 200]
51
- #
52
- # Since it is immutable, all methods which you might expect to "modify" a `Hamster::Hash`
53
- # actually return a new hash and leave the existing one unchanged. This means that the
54
- # `hash[key] = value` syntax used with RubyHashes *cannot* be used with `Hamster::Hash`.
55
- #
56
- # While a `Hamster::Hash` can iterate over its keys (or values), it does not
57
- # guarantee any specific iteration order (unlike RubyHash). Likewise, methods like
58
- # {#flatten} do not guarantee which order the returned key/value pairs will appear
59
- # in.
60
- #
61
- # Like RubyHash, a `Hamster::Hash` can have a default block which is used when
62
- # looking up a key which does not exist in the hash. Unlike RubyHash, the default
63
- # block will only be passed the missing key, not the hash itself:
64
- #
65
- # hash = Hamster::Hash.new { |n| n * 10 }
66
- # hash[5] # => 50
67
- #
68
- # A default block can only be set when creating a `Hamster::Hash` with `Hamster::Hash.new` or
69
- # {Hamster.hash Hamster.hash}, not with {Hamster::Hash.[] Hamster::Hash[]}. Default blocks
70
- # do not survive marshalling and unmarshalling.
71
- #
72
13
  class Hash
14
+ extend Forwardable
73
15
  include Immutable
74
- include Enumerable
75
16
 
76
17
  class << self
77
- # Create a new `Hash` populated with the given key/value pairs.
78
- #
79
- # @example
80
- # Hamster::Hash["A" => 1, "B" => 2]
81
- # # => Hamster::Hash["A" => 1, "B" => 2]
82
- # Hamster::Hash[["A", 1], ["B", 2]]
83
- # # => Hamster::Hash["A" => 1, "B" => 2]
84
- #
85
- # @return [Hash]
86
- def [](pairs = nil)
87
- (pairs.nil? || pairs.empty?) ? empty : new(pairs)
88
- end
89
-
90
- # Return an empty `Hash`. If used on a subclass, returns an empty instance
91
- # of that class.
92
- #
93
- # @return [Hash]
94
- def empty
95
- @empty ||= self.new
18
+ def new(pairs = {}, &block)
19
+ @empty ||= super()
20
+ pairs.reduce(block_given? ? super(&block) : @empty) { |hash, pair| hash.put(pair.first, pair.last) }
96
21
  end
97
22
 
98
- # "Raw" allocation of a new `Hash`. Used internally to create a new
99
- # instance quickly after obtaining a modified {Trie}.
100
- #
101
- # @return [Hash]
102
- # @private
103
- def alloc(trie = EmptyTrie, block = nil)
104
- obj = allocate
105
- obj.instance_variable_set(:@trie, trie)
106
- obj.instance_variable_set(:@default, block)
107
- obj
108
- end
23
+ attr_reader :empty
109
24
  end
110
25
 
111
- def initialize(pairs = nil, &block)
112
- @trie = pairs ? Trie[pairs] : EmptyTrie
26
+ def initialize(&block)
27
+ @trie = EmptyTrie
113
28
  @default = block
114
29
  end
115
30
 
116
- # Return the default block if there is one. Otherwise, return `nil`.
117
- #
118
- # @return [Proc]
119
- def default_proc
120
- @default
121
- end
122
-
123
- # Return the number of key/value pairs in this `Hash`.
124
- #
125
- # @example
126
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].size # => 3
127
- #
128
- # @return [Integer]
129
31
  def size
130
32
  @trie.size
131
33
  end
132
- alias :length :size
34
+ def_delegator :self, :size, :length
133
35
 
134
- # Return `true` if this `Hash` contains no key/value pairs.
135
- #
136
- # @return [Boolean]
137
36
  def empty?
138
37
  @trie.empty?
139
38
  end
39
+ def_delegator :self, :empty?, :null?
140
40
 
141
- # Return `true` if the given key object is present in this `Hash`. More precisely,
142
- # return `true` if a key with the same `#hash` code, and which is also `#eql?`
143
- # to the given key object is present.
144
- #
145
- # @example
146
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].key?("B") # => true
147
- #
148
- # @param key [Object] The key to check for
149
- # @return [Boolean]
150
41
  def key?(key)
151
42
  @trie.key?(key)
152
43
  end
153
- alias :has_key? :key?
154
- alias :include? :key?
155
- alias :member? :key?
156
-
157
- # Return `true` if this `Hash` has one or more keys which map to the provided value.
158
- #
159
- # @example
160
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].value?(2) # => true
161
- #
162
- # @param value [Object] The value to check for
163
- # @return [Boolean]
164
- def value?(value)
165
- each { |k,v| return true if value == v }
166
- false
167
- end
168
- alias :has_value? :value?
169
-
170
- # Retrieve the value corresponding to the provided key object. If not found, and
171
- # this `Hash` has a default block, the default block is called to provide the
172
- # value.
173
- #
174
- # @example
175
- # h = Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
176
- # h["B"] # => 2
177
- # h.get("B") # => 2
178
- # h.get("Elephant") # => nil
179
- #
180
- # # Hamster Hash with a default proc:
181
- # h = Hamster::Hash.new("A" => 1, "B" => 2, "C" => 3) { |key| key.size }
182
- # h.get("B") # => 2
183
- # h.get("Elephant") # => 8
184
- #
185
- # @param key [Object] The key to look up
186
- # @return [Object]
44
+ def_delegator :self, :key?, :has_key?
45
+ def_delegator :self, :key?, :include?
46
+ def_delegator :self, :key?, :member?
47
+
187
48
  def get(key)
188
49
  entry = @trie.get(key)
189
50
  if entry
190
- entry[1]
51
+ entry.value
191
52
  elsif @default
192
53
  @default.call(key)
193
54
  end
194
55
  end
195
- alias :[] :get
196
-
197
- # Retrieve the value corresponding to the given key object, or use the provided
198
- # default value or block, or otherwise raise a `KeyError`.
199
- #
200
- # @overload fetch(key)
201
- # Retrieve the value corresponding to the given key, or raise a `KeyError`
202
- # if it is not found.
203
- # @param key [Object] The key to look up
204
- # @overload fetch(key) { |key| ... }
205
- # Retrieve the value corresponding to the given key, or call the optional
206
- # code block (with the missing key) and get its return value.
207
- # @yield [key] The key which was not found
208
- # @yieldreturn [Object] Object to return since the key was not found
209
- # @param key [Object] The key to look up
210
- # @overload fetch(key, default)
211
- # Retrieve the value corresponding to the given key, or else return
212
- # the provided `default` value.
213
- # @param key [Object] The key to look up
214
- # @param default [Object] Object to return if the key is not found
215
- #
216
- # @example
217
- # h = Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
218
- # h.fetch("B") # => 2
219
- # h.fetch("Elephant") # => KeyError: key not found: "Elephant"
220
- #
221
- # # with a default value:
222
- # h.fetch("B", 99) # => 2
223
- # h.fetch("Elephant", 99) # => 99
224
- #
225
- # # with a block:
226
- # h.fetch("B") { |key| key.size } # => 2
227
- # h.fetch("Elephant") { |key| key.size } # => 8
228
- #
229
- # @return [Object]
56
+ def_delegator :self, :get, :[]
57
+
230
58
  def fetch(key, default = Undefined)
231
59
  entry = @trie.get(key)
232
60
  if entry
233
- entry[1]
234
- elsif block_given?
235
- yield(key)
61
+ entry.value
236
62
  elsif default != Undefined
237
63
  default
64
+ elsif block_given?
65
+ yield
238
66
  else
239
67
  raise KeyError, "key not found: #{key.inspect}"
240
68
  end
241
69
  end
242
70
 
243
- # Return a new `Hash` with the existing key/value associations, plus an association
244
- # between the provided key and value. If an equivalent key is already present, its
245
- # associated value will be replaced with the provided one.
246
- #
247
- # If the `value` argument is missing, but an optional code block is provided,
248
- # it will be passed the existing value (or `nil` if there is none) and what it
249
- # returns will replace the existing value. This is useful for "transforming"
250
- # the value associated with a certain key.
251
- #
252
- # Avoid mutating objects which are used as keys. `String`s are an exception --
253
- # unfrozen `String`s which are used as keys are internally duplicated and
254
- # frozen.
255
- #
256
- # @example
257
- # h = Hamster::Hash["A" => 1, "B" => 2]
258
- # h.put("C", 3)
259
- # # => Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
260
- # h.put("B") { |value| value * 10 }
261
- # # => Hamster::Hash["A" => 1, "B" => 20]
262
- #
263
- # @param key [Object] The key to store
264
- # @param value [Object] The value to associate it with
265
- # @yield [value] The previously stored value
266
- # @yieldreturn [Object] The new value to store
267
- # @return [Hash]
268
- def put(key, value = yield(get(key)))
269
- new_trie = @trie.put(key, value)
270
- if new_trie.equal?(@trie)
271
- self
272
- else
273
- self.class.alloc(new_trie, @default)
274
- end
71
+ def put(key, value = Undefined)
72
+ return put(key, yield(get(key))) if value.equal?(Undefined)
73
+ transform { @trie = @trie.put(key, value) }
275
74
  end
276
75
 
277
- # Return a new `Hash` with a deeply nested value modified to the result of
278
- # the given code block. When traversing the nested `Hash`es and `Vector`s,
279
- # non-existing keys are created with empty `Hash` values.
280
- #
281
- # The code block receives the existing value of the deeply nested key (or
282
- # `nil` if it doesn't exist). This is useful for "transforming" the value
283
- # associated with a certain key.
284
- #
285
- # Note that the original `Hash` and sub-`Hash`es and sub-`Vector`s are left
286
- # unmodified; new data structure copies are created along the path wherever
287
- # needed.
288
- #
289
- # @example
290
- # hash = Hamster::Hash["a" => Hamster::Hash["b" => Hamster::Hash["c" => 42]]]
291
- # hash.update_in("a", "b", "c") { |value| value + 5 }
292
- # # => Hamster::Hash["a" => Hamster::Hash["b" => Hamster::Hash["c" => 47]]]
293
- #
294
- # @param key_path [Object(s)] List of keys which form the path to the key to be modified
295
- # @yield [value] The previously stored value
296
- # @yieldreturn [Object] The new value to store
297
- # @return [Hash]
298
- def update_in(*key_path, &block)
299
- if key_path.empty?
300
- raise ArgumentError, "must have at least one key in path"
301
- end
302
- key = key_path[0]
303
- if key_path.size == 1
304
- new_value = block.call(get(key))
305
- else
306
- value = fetch(key, EmptyHash)
307
- new_value = value.update_in(*key_path[1..-1], &block)
308
- end
309
- put(key, new_value)
76
+ def delete(key)
77
+ trie = @trie.delete(key)
78
+ transform_unless(trie.equal?(@trie)) { @trie = trie }
310
79
  end
311
80
 
312
- # Return a new `Hash` with the existing key/value associations, plus an association
313
- # between the provided key and value. If an equivalent key is already present, its
314
- # associated value will be replaced with the provided one.
315
- #
316
- # Avoid mutating objects which are used as keys. `String`s are an exception --
317
- # unfrozen `String`s which are used as keys are internally duplicated and
318
- # frozen.
319
- #
320
- # @example
321
- # Hamster::Hash["A" => 1, "B" => 2].store("C", 3)
322
- # # => Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
323
- #
324
- # @param key [Object] The key to store
325
- # @param value [Object] The value to associate it with
326
- # @return [Hash]
327
- def store(key, value)
328
- put(key, value)
81
+ def each
82
+ return self unless block_given?
83
+ @trie.each { |entry| yield(entry.key, entry.value) }
329
84
  end
85
+ def_delegator :self, :each, :foreach
330
86
 
331
- # Return a new `Hash` with the association for `key` removed. If `key` is not
332
- # present, return `self`.
333
- #
334
- # @example
335
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].delete("B")
336
- # # => Hamster::Hash["A" => 1, "C" => 3]
337
- #
338
- # @param key [Object] The key to remove
339
- # @return [Hash]
340
- def delete(key)
341
- derive_new_hash(@trie.delete(key))
87
+ def map
88
+ return self unless block_given?
89
+ return self if empty?
90
+ transform { @trie = @trie.reduce(EmptyTrie) { |trie, entry| trie.put(*yield(entry.key, entry.value)) } }
342
91
  end
92
+ def_delegator :self, :map, :collect
343
93
 
344
- # Call the block once for each key/value pair in this `Hash`, passing the key/value
345
- # pair as parameters. No specific iteration order is guaranteed (but the order will
346
- # be stable for any particular `Hash`.)
347
- #
348
- # @example
349
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].each { |k, v| puts "k=#{k} v=#{v}" }
350
- #
351
- # k=A v=1
352
- # k=B v=2
353
- # k=C v=3
354
- # # => Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
355
- #
356
- # @return [self]
357
- def each(&block)
358
- return to_enum if not block_given?
359
- @trie.each(&block)
360
- self
361
- end
362
- alias :each_pair :each
363
-
364
- # Call the block once for each key/value pair in this `Hash`, passing the key/value
365
- # pair as parameters. Iteration order will be the opposite of {#each}.
366
- #
367
- # @example
368
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].reverse_each { |k, v| puts "k=#{k} v=#{v}" }
369
- #
370
- # k=C v=3
371
- # k=B v=2
372
- # k=A v=1
373
- # # => Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
374
- #
375
- # @return [self]
376
- def reverse_each(&block)
377
- return enum_for(:reverse_each) if not block_given?
378
- @trie.reverse_each(&block)
379
- self
94
+ def reduce(memoization)
95
+ return memoization unless block_given?
96
+ @trie.reduce(memoization) { |memo, entry| yield(memo, entry.key, entry.value) }
380
97
  end
98
+ def_delegator :self, :reduce, :inject
99
+ def_delegator :self, :reduce, :fold
100
+ def_delegator :self, :reduce, :foldr
381
101
 
382
- # Call the block once for each key/value pair in this `Hash`, passing the key as a
383
- # parameter.
384
- #
385
- # @example
386
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].each_key { |k| puts "k=#{k}" }
387
- #
388
- # k=A
389
- # k=B
390
- # k=C
391
- # # => Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
392
- #
393
- # @return [self]
394
- def each_key
395
- return enum_for(:each_key) if not block_given?
396
- @trie.each { |k,v| yield k }
397
- self
102
+ def filter
103
+ return self unless block_given?
104
+ trie = @trie.filter { |entry| yield(entry.key, entry.value) }
105
+ return self.class.empty if trie.empty?
106
+ transform_unless(trie.equal?(@trie)) { @trie = trie }
398
107
  end
108
+ def_delegator :self, :filter, :select
109
+ def_delegator :self, :filter, :find_all
399
110
 
400
- # Call the block once for each key/value pair in this `Hash`, passing the value as a
401
- # parameter.
402
- #
403
- # @example
404
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].each_value { |v| puts "v=#{v}" }
405
- #
406
- # v=1
407
- # v=2
408
- # v=3
409
- # # => Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
410
- #
411
- # @return [self]
412
- def each_value
413
- return enum_for(:each_value) if not block_given?
414
- @trie.each { |k,v| yield v }
415
- self
111
+ def remove
112
+ return self unless block_given?
113
+ filter { |key, value| !yield(key, value) }
416
114
  end
115
+ def_delegator :self, :remove, :reject
116
+ def_delegator :self, :remove, :delete_if
417
117
 
418
- # Call the block once for each key/value pair in this `Hash`, passing the key/value
419
- # pair as parameters. The block should return a `[key, value]` array each time.
420
- # All the returned `[key, value]` arrays will be gathered into a new `Hash`.
421
- #
422
- # @example
423
- # h = Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
424
- # h.map { |k, v| ["new-#{k}", v * v] }
425
- # # => Hash["new-C" => 9, "new-B" => 4, "new-A" => 1]
426
- #
427
- # @return [Hash]
428
- def map
429
- return enum_for(:map) unless block_given?
430
- return self if empty?
431
- self.class.new(super, &@default)
432
- end
433
- alias :collect :map
434
-
435
- # Return a new `Hash` with all the key/value pairs for which the block returns true.
436
- #
437
- # @example
438
- # h = Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
439
- # h.select { |k, v| v >= 2 }
440
- # # => Hamster::Hash["B" => 2, "C" => 3]
441
- #
442
- # @return [Hash]
443
- def select(&block)
444
- return enum_for(:select) unless block_given?
445
- derive_new_hash(@trie.select(&block))
118
+ def any?
119
+ return !empty? unless block_given?
120
+ each { |key, value| return true if yield(key, value) }
121
+ false
446
122
  end
447
- alias :find_all :select
448
- alias :keep_if :select
449
-
450
- # Yield `[key, value]` pairs until one is found for which the block returns true.
451
- # Return that `[key, value]` pair. If the block never returns true, return `nil`.
452
- #
453
- # @example
454
- # h = Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
455
- # h.find { |k, v| v.even? }
456
- # # => ["B", 2]
457
- #
458
- # @return [Array]
459
- def find
460
- return enum_for(:find) unless block_given?
461
- each { |entry| return entry if yield entry }
462
- nil
123
+ def_delegator :self, :any?, :exist?
124
+ def_delegator :self, :any?, :exists?
125
+
126
+ def all?
127
+ each { |key, value| return false unless yield(key, value) } if block_given?
128
+ true
463
129
  end
464
- alias :detect :find
465
-
466
- # Return a new `Hash` containing all the key/value pairs from this `Hash` and
467
- # `other`. If no block is provided, the value for entries with colliding keys
468
- # will be that from `other`. Otherwie, the value for each duplicate key is
469
- # determined by called the block with the key, its value in this `Hash`, and
470
- # its value in `other`.
471
- #
472
- # `other` can be a `Hamster::Hash`, a built-in Ruby `Hash`, or any `Enumerable`
473
- # object which yields `[key, value]` pairs.
474
- #
475
- # @example
476
- # h1 = Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
477
- # h2 = Hamster::Hash["C" => 70, "D" => 80]
478
- # h1.merge(h2)
479
- # # => Hamster::Hash["C" => 70, "A" => 1, "D" => 80, "B" => 2]
480
- # h1.merge(h2) { |key, v1, v2| v1 + v2 }
481
- # # => Hamster::Hash["C" => 73, "A" => 1, "D" => 80, "B" => 2]
482
- #
483
- # @param other [Enumerable] The collection to merge with
484
- # @yieldparam key [Object] The key which was present in both collections
485
- # @yieldparam my_value [Object] The associated value from this `Hash`
486
- # @yieldparam other_value [Object] The associated value from the other collection
487
- # @yieldreturn [Object] The value to associate this key with in the new `Hash`
488
- # @return [Hash]
489
- def merge(other)
490
- trie = if block_given?
491
- other.reduce(@trie) do |trie, (key, value)|
492
- if entry = trie.get(key)
493
- trie.put(key, yield(key, entry[1], value))
494
- else
495
- trie.put(key, value)
496
- end
497
- end
498
- else
499
- @trie.bulk_put(other)
500
- end
130
+ def_delegator :self, :all?, :forall?
501
131
 
502
- derive_new_hash(trie)
132
+ def none?
133
+ return empty? unless block_given?
134
+ each { |key, value| return false if yield(key, value) }
135
+ true
503
136
  end
504
137
 
505
- # Return a {Vector} which contains all the `[key, value]` pairs in this `Hash`
506
- # as 2-element Arrays, either in their natural sorted order as determined by
507
- # `#<=>`, or if an optional block is supplied, by using the block as a comparator.
508
- # See `Enumerable#sort`.
509
- #
510
- # @example
511
- # h = Hamster::Hash["Dog" => 1, "Elephant" => 2, "Lion" => 3]
512
- # h.sort { |(k1, v1), (k2, v2)| k1.size <=> k2.size }
513
- # # => Hamster::Vector[["Dog", 1], ["Lion", 3], ["Elephant", 2]]
514
- #
515
- # @return [Vector]
516
- def sort
517
- Vector.new(super)
138
+ def find
139
+ return nil unless block_given?
140
+ each { |key, value| return Tuple.new(key, value) if yield(key, value) }
141
+ nil
518
142
  end
143
+ def_delegator :self, :find, :detect
519
144
 
520
- # Return a {Vector} which contains all the `[key, value]` pairs in this `Hash`
521
- # as 2-element Arrays. The order which the pairs will appear in is determined by
522
- # passing each pair to the code block to obtain a sort key object, and comparing
523
- # the sort keys using `#<=>`.
524
- # See `Enumerable#sort_by`.
525
- #
526
- # @example
527
- # h = Hamster::Hash["Dog" => 1, "Elephant" => 2, "Lion" => 3]
528
- # h.sort_by { |key, value| key.size }
529
- # # => Hamster::Vector[["Dog", 1], ["Lion", 3], ["Elephant", 2]]
530
- #
531
- # @return [Vector]
532
- def sort_by
533
- Vector.new(super)
145
+ def merge(other)
146
+ transform { @trie = other.reduce(@trie, &:put) }
534
147
  end
148
+ def_delegator :self, :merge, :+
535
149
 
536
- # Return a new `Hash` with the associations for all of the given `keys` removed.
537
- #
538
- # @example
539
- # h = Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
540
- # h.except("A", "C") # => Hamster::Hash["B" => 2]
541
- #
542
- # @param keys [Array] The keys to remove
543
- # @return [Hash]
544
150
  def except(*keys)
545
151
  keys.reduce(self) { |hash, key| hash.delete(key) }
546
152
  end
547
153
 
548
- # Return a new `Hash` with only the associations for the `wanted` keys retained.
549
- # If any of the `wanted` keys are not present in this `Hash`, they will not be present
550
- # in the returned `Hash` either.
551
- #
552
- # @example
553
- # h = Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
554
- # h.slice("B", "C") # => Hamster::Hash["B" => 2, "C" => 3]
555
- #
556
- # @param wanted [Array] The keys to retain
557
- # @return [Hash]
558
154
  def slice(*wanted)
559
- trie = Trie.new(0)
560
- wanted.each { |key| trie.put!(key, get(key)) if key?(key) }
561
- self.class.alloc(trie, @default)
562
- end
563
-
564
- # Return a {Vector} of the values which correspond to the `wanted` keys.
565
- # If any of the `wanted` keys are not present in this `Hash`, they will be skipped.
566
- #
567
- # @example
568
- # h = Hamster::Hash["A" => 1, "B" => 2, "C" => 3]
569
- # h.values_at("B", "A") # => Hamster::Vector[2, 1]
570
- #
571
- # @param wanted [Array] The keys to retrieve
572
- # @return [Vector]
573
- def values_at(*wanted)
574
- array = []
575
- wanted.each { |key| array << get(key) if key?(key) }
576
- Vector.new(array.freeze)
155
+ except(*keys - wanted)
577
156
  end
578
157
 
579
- # Return a new {Set} populated with the keys from this `Hash`.
580
- #
581
- # @example
582
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3, "D" => 2].keys
583
- # # => Hamster::Set["D", "C", "B", "A"]
584
- #
585
- # @return [Set]
586
158
  def keys
587
- Set.alloc(@trie)
159
+ reduce(Hamster.set) { |keys, key, value| keys.add(key) }
588
160
  end
589
161
 
590
- # Return a new {Vector} populated with the values from this `Hash`.
591
- #
592
- # @example
593
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3, "D" => 2].values
594
- # # => Hamster::Vector[2, 3, 2, 1]
595
- #
596
- # @return [Vector]
597
162
  def values
598
- Vector.new(each_value.to_a.freeze)
599
- end
600
-
601
- # Return a new `Hash` created by using our keys as values, and values as keys.
602
- # If there are multiple values which are equivalent (as determined by `#hash` and
603
- # `#eql?`), only one out of each group of equivalent values will be retained.
604
- #
605
- # @example
606
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3, "D" => 2].invert
607
- # # => Hamster::Hash[1 => "A", 3 => "C", 2 => "B"]
608
- #
609
- # @return [Hash]
610
- def invert
611
- pairs = []
612
- each { |k,v| pairs << [v, k] }
613
- self.class.new(pairs, &@default)
614
- end
615
-
616
- # Return a new {Vector} which is a one-dimensional flattening of this `Hash`.
617
- # If `level` is 1, all the `[key, value]` pairs in the hash will be concatenated
618
- # into one {Vector}. If `level` is greater than 1, keys or values which are
619
- # themselves `Array`s or {Vector}s will be recursively flattened into the output
620
- # {Vector}. The depth to which that flattening will be recursively applied is
621
- # determined by `level`.
622
- #
623
- # As a special case, if `level` is 0, each `[key, value]` pair will be a
624
- # separate element in the returned {Vector}.
625
- #
626
- # @example
627
- # h = Hamster::Hash["A" => 1, "B" => [2, 3, 4]]
628
- # h.flatten
629
- # # => Hamster::Vector["A", 1, "B", [2, 3, 4]]
630
- # h.flatten(2)
631
- # # => Hamster::Vector["A", 1, "B", 2, 3, 4]
632
- #
633
- # @param level [Integer] The number of times to recursively flatten the `[key, value]` pairs in this `Hash`.
634
- # @return [Vector]
635
- def flatten(level = 1)
636
- return Vector.new(self) if level == 0
637
- array = []
638
- each { |k,v| array << k; array << v }
639
- array.flatten!(level-1) if level > 1
640
- Vector.new(array.freeze)
641
- end
642
-
643
- # Searches through the `Hash`, comparing `obj` with each key (using `#==`).
644
- # When a matching key is found, return the `[key, value]` pair as an array.
645
- # Return `nil` if no match is found.
646
- #
647
- # @example
648
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].assoc("B") # => ["B", 2]
649
- #
650
- # @param obj [Object] The key to search for (using #==)
651
- # @return [Array]
652
- def assoc(obj)
653
- each { |entry| return entry if obj == entry[0] }
654
- nil
655
- end
656
-
657
- # Searches through the `Hash`, comparing `obj` with each value (using `#==`).
658
- # When a matching value is found, return the `[key, value]` pair as an array.
659
- # Return `nil` if no match is found.
660
- #
661
- # @example
662
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].rassoc(2) # => ["B", 2]
663
- #
664
- # @param obj [Object] The value to search for (using #==)
665
- # @return [Array]
666
- def rassoc(obj)
667
- each { |entry| return entry if obj == entry[1] }
668
- nil
669
- end
670
-
671
- # Searches through the `Hash`, comparing `value` with each value (using `#==`).
672
- # When a matching value is found, return its associated key object.
673
- # Return `nil` if no match is found.
674
- #
675
- # @example
676
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].key(2) # => "B"
677
- #
678
- # @param value [Object] The value to search for (using #==)
679
- # @return [Object]
680
- def key(value)
681
- each { |entry| return entry[0] if value == entry[1] }
682
- nil
683
- end
684
-
685
- # Return a randomly chosen `[key, value]` pair from this `Hash`. If the hash is empty,
686
- # return `nil`.
687
- #
688
- # @example
689
- # Hamster::Hash["A" => 1, "B" => 2, "C" => 3].sample
690
- # # => ["C", 3]
691
- #
692
- # @return [Array]
693
- def sample
694
- @trie.at(rand(size))
163
+ reduce(Hamster.list) { |values, key, value| values.cons(value) }
695
164
  end
696
165
 
697
- # Return an empty `Hash` instance, of the same class as this one. Useful if you
698
- # have multiple subclasses of `Hash` and want to treat them polymorphically.
699
- # Maintains the default block, if there is one.
700
- #
701
- # @return [Hash]
702
166
  def clear
703
- if @default
704
- self.class.alloc(EmptyTrie, @default)
705
- else
706
- self.class.empty
707
- end
167
+ self.class.empty
708
168
  end
709
169
 
710
- # Return true if `other` has the same type and contents as this `Hash`.
711
- #
712
- # @param other [Object] The collection to compare with
713
- # @return [Boolean]
714
170
  def eql?(other)
715
- return true if other.equal?(self)
716
171
  instance_of?(other.class) && @trie.eql?(other.instance_variable_get(:@trie))
717
172
  end
173
+ def_delegator :self, :eql?, :==
718
174
 
719
- # Return true if `other` has the same contents as this `Hash`. Will convert
720
- # `other` to a Ruby `Hash` using `#to_hash` if necessary.
721
- #
722
- # @param other [Object] The object to compare with
723
- # @return [Boolean]
724
- def ==(other)
725
- self.eql?(other) || (other.respond_to?(:to_hash) && to_hash.eql?(other.to_hash))
726
- end
727
-
728
- # See `Object#hash`.
729
- # @return [Integer]
730
175
  def hash
731
- keys.to_a.sort.reduce(0) do |hash, key|
176
+ keys.sort.reduce(0) do |hash, key|
732
177
  (hash << 32) - hash + key.hash + get(key).hash
733
178
  end
734
179
  end
735
180
 
736
- # Return the contents of this `Hash` as a programmer-readable `String`. If all the
737
- # keys and values are serializable as Ruby literal strings, the returned string can
738
- # be passed to `eval` to reconstitute an equivalent `Hash`. However, the default
739
- # block (if there is one) will be lost when doing this.
740
- #
741
- # @return [String]
742
- def inspect
743
- result = "#{self.class}["
744
- i = 0
745
- each do |key, val|
746
- result << ', ' if i > 0
747
- result << key.inspect << ' => ' << val.inspect
748
- i += 1
749
- end
750
- result << "]"
751
- end
181
+ def_delegator :self, :dup, :uniq
182
+ def_delegator :self, :dup, :nub
183
+ def_delegator :self, :dup, :remove_duplicates
752
184
 
753
- # Allows this `Hash` to be printed at the `pry` console, or using `pp` (from the
754
- # Ruby standard library), in a way which takes the amount of horizontal space on
755
- # the screen into account, and which indents nested structures to make them easier
756
- # to read.
757
- #
758
- # @private
759
- def pretty_print(pp)
760
- pp.group(1, "#{self.class}[", "]") do
761
- pp.breakable ''
762
- pp.seplist(self, nil) do |key, val|
763
- pp.group do
764
- key.pretty_print(pp)
765
- pp.text ' => '
766
- pp.group(1) do
767
- pp.breakable ''
768
- val.pretty_print(pp)
769
- end
770
- end
771
- end
772
- end
185
+ def inspect
186
+ "{#{reduce([]) { |memo, key, value| memo << "#{key.inspect} => #{value.inspect}" }.join(", ")}}"
773
187
  end
774
188
 
775
- # Convert this `Hamster::Hash` to an instance of Ruby's built-in `Hash`.
776
- #
777
- # @return [::Hash]
778
- def to_hash
189
+ def marshal_dump
779
190
  output = {}
780
191
  each do |key, value|
781
192
  output[key] = value
782
193
  end
783
194
  output
784
195
  end
785
- alias :to_h :to_hash
786
-
787
- # @return [::Hash]
788
- # @private
789
- def marshal_dump
790
- to_hash
791
- end
792
196
 
793
- # @private
794
197
  def marshal_load(dictionary)
795
- @trie = Trie[dictionary]
796
- end
797
-
798
- private
799
-
800
- # Return a new `Hash` which is derived from this one, using a modified {Trie}.
801
- # The new `Hash` will retain the existing default block, if there is one.
802
- #
803
- def derive_new_hash(trie)
804
- if trie.equal?(@trie)
805
- self
806
- elsif trie.empty?
807
- if @default
808
- self.class.alloc(EmptyTrie, @default)
809
- else
810
- self.class.empty
811
- end
812
- else
813
- self.class.alloc(trie, @default)
198
+ @trie = dictionary.reduce EmptyTrie do |trie, key_value|
199
+ trie.put(key_value.first, key_value.last)
814
200
  end
815
201
  end
816
202
  end
817
203
 
818
- # The canonical empty `Hash`. Returned by `Hamster.hash` and `Hash[]` when
819
- # invoked with no arguments; also returned by `Hash.empty`. Prefer using this
820
- # one rather than creating many empty hashes using `Hash.new`.
821
- #
822
- EmptyHash = Hamster::Hash.empty
204
+ EmptyHash = Hamster::Hash.new
823
205
  end