sleeping_king_studios-tools 0.2.0 → 0.3.0.alpha

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 2cbcab2d2d7823d4c8236c192e43624496156d31
4
- data.tar.gz: df39fa76136cc679066555eed5a9d047054a0162
3
+ metadata.gz: d2abf0235b1796184caa2b29cc3c2886d0b94f1b
4
+ data.tar.gz: 784bd7ea599838663906cde584cbcca474879ed6
5
5
  SHA512:
6
- metadata.gz: 37b3aab0adbf9e9c6715543fac51f3ff378e9502c1e31846a63b288ab89cf20a43c4506172cf0f2a80d35ff00e827c968854623f6eb95541051ac4e7da70ad1f
7
- data.tar.gz: e72a4bc32d601530b21de8323b361b9b2c297181ee2283271e8e201ba3ff1ed5fa54230c21731188ac05ac00f21d0e159bbde072062245985ec71048df289c9d
6
+ metadata.gz: 9554e42f6ac9fc4e584849d808872828b2091efdc645a3c22d65403c474e786eedbcb6eb61440ae7991508ff571bd358f940f4fe67fe87d9842d4c54d77dedba
7
+ data.tar.gz: 57137dcbd88ef5ca51d071b69315a819c9a3e3d00c92d2d620a602eb032ea546c59bebba62b2c7139615c0ab4b4956053bf4a86121b1a7c3f5341ea428425936
data/CHANGELOG.md CHANGED
@@ -2,6 +2,14 @@
2
2
 
3
3
  ## Pre-release Versions
4
4
 
5
+ ### 0.3.0
6
+
7
+ Implement ArrayTools#bisect and ArrayTools#splice.
8
+
9
+ #### StringTools
10
+
11
+ Implement #underscore.
12
+
5
13
  ### 0.2.0
6
14
 
7
15
  Split EnumerableTools into ArrayTools and HashTools.
data/README.md CHANGED
@@ -18,6 +18,17 @@ Hi, I'm Rob Smith, a Ruby Engineer and the developer of this library. I use thes
18
18
 
19
19
  Tools for working with array-like enumerable objects.
20
20
 
21
+ #### `#bisect`
22
+
23
+ Separates the array into two arrays, the first containing all items in the original array that matches the provided block, and the second containing all items in the original array that do not match the provided block.
24
+
25
+ original = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
26
+ selected, rejected = ArrayTools.bisect(original) { |item| item.even? }
27
+ selected
28
+ #=> [0, 2, 4, 6, 8]
29
+ rejected
30
+ #=> [1, 3, 5, 7, 9]
31
+
21
32
  #### `#count_values`
22
33
 
23
34
  Counts the number of times each value appears in the array, or if a block is given, calls the block with each item and counts the number of times each result appears.
@@ -64,6 +75,31 @@ Accepts a list of values and returns a human-readable string of the values, with
64
75
  ArrayTools.humanize_list(['spam', 'eggs', 'bacon', 'spam'])
65
76
  #=> 'spam, eggs, bacon, and spam'
66
77
 
78
+ #### `#splice`
79
+
80
+ Accepts an array, a start value, a number of items to delete, and zero or more items to insert at that index. Deletes the specified number of items, then inserts the given items at the index and returns the array of deleted items.
81
+
82
+ # Deleting items from an Array
83
+ values = %w(katana wakizashi tachi daito shoto)
84
+ ArrayTools.splice values, 1, 2
85
+ #=> ['wakizashi', 'tachi']
86
+ values
87
+ #=> ['katana', 'daito', 'shoto']
88
+
89
+ # Inserting items into an Array
90
+ values = %w(longsword broadsword claymore)
91
+ ArrayTools.splice values, 1, 0, 'zweihänder'
92
+ #=> []
93
+ values
94
+ #=> ['longsword', 'zweihänder', 'broadsword', 'claymore']
95
+
96
+ # Inserting and deleting items
97
+ values = %w(shortbow longbow crossbow)
98
+ ArrayTools.splice values, 2, 1, 'arbalest', 'chu-ko-nu'
99
+ #=> ['crossbow']
100
+ values
101
+ #=> ['shortbow', 'longbow', 'arbalest', 'chu-ko-nu']
102
+
67
103
  ### Hash Tools
68
104
 
69
105
  Tools for working with array-like enumerable objects.
@@ -202,6 +238,10 @@ Returns the singular or the plural value, depending on the provided item count.
202
238
  StringTools.pluralize 4, 'light', 'lights'
203
239
  #=> 'lights'
204
240
 
241
+ #### '#underscore'
242
+
243
+ Converts a mixed-case string expression to a lowercase, underscore separated string, as per ActiveSupport::Inflector#underscore.
244
+
205
245
  ## Additional Features
206
246
 
207
247
  ### Semantic Version
@@ -8,19 +8,57 @@ module SleepingKingStudios::Tools
8
8
  module ArrayTools
9
9
  extend self
10
10
 
11
- # @overload count_values(values)
11
+ # Separates the array into two arrays, the first containing all items in the
12
+ # original array that matches the provided block, and the second containing
13
+ # all items in the original array that do not match the provided block.
14
+ #
15
+ # @example
16
+ # selected, rejected = ArrayTools.bisect([*0...10]) { |item| item.even? }
17
+ # selected
18
+ # #=> [0, 2, 4, 6, 8]
19
+ # rejected
20
+ # #=> [1, 3, 5, 7, 9]
21
+ #
22
+ # @param [Array<Object>] ary The array to bisect.
23
+ #
24
+ # @yieldparam item [Object] An item in the array to matched.
25
+ #
26
+ # @yieldreturn [Boolean] True if the item matches the criteria, otherwise
27
+ # false.
28
+ #
29
+ # @raise ArgumentError If the first argument is not an Array-like object or
30
+ # if no block is given.
31
+ #
32
+ # @return [Array<Array<Object>>] An array containing two arrays.
33
+ def bisect ary, &block
34
+ require_array! ary
35
+
36
+ raise ArgumentError.new('no block given') unless block_given?
37
+
38
+ selected, rejected = [], []
39
+
40
+ ary.each do |item|
41
+ (yield(item) ? selected : rejected) << item
42
+ end # each
43
+
44
+ [selected, rejected]
45
+ end # method bisect
46
+
47
+ # @overload count_values(ary)
12
48
  # Counts the number of times each value appears in the enumerable object.
13
49
  #
14
50
  # @example
15
51
  # ArrayTools.count_values([1, 1, 1, 2, 2, 3])
16
52
  # #=> { 1 => 3, 2 => 2, 3 => 1 }
17
53
  #
18
- # @param [Array<Object>] values The values to count.
54
+ # @param [Array<Object>] ary The values to count.
55
+ #
56
+ # @raise ArgumentError If the first argument is not an Array-like object.
19
57
  #
20
58
  # @return [Hash{Object, Integer}] The number of times each value appears
21
59
  # in the enumerable object.
22
60
  #
23
- # @overload count_values(values, &block)
61
+ # @overload count_values(ary, &block)
24
62
  # Calls the block with each item and counts the number of times each
25
63
  # result appears.
26
64
  #
@@ -28,15 +66,20 @@ module SleepingKingStudios::Tools
28
66
  # ArrayTools.count_values([1, 1, 1, 2, 2, 3]) { |i| i ** 2 }
29
67
  # #=> { 1 => 3, 4 => 2, 9 => 1 }
30
68
  #
31
- # @param [Array<Object>] values The values to count.
69
+ # @param [Array<Object>] ary The values to count.
70
+ #
71
+ # @yieldparam item [Object] An item in the array to matched.
72
+ #
73
+ # @raise ArgumentError If the first argument is not an Array-like object.
32
74
  #
33
75
  # @return [Hash{Object, Integer}] The number of times each result
34
76
  # appears.
35
- #
36
- # @yield item An item in the array to be converted to a countable result.
37
- def count_values values, &block
38
- values.each.with_object({}) do |item, hsh|
77
+ def count_values ary, &block
78
+ require_array! ary
79
+
80
+ ary.each.with_object({}) do |item, hsh|
39
81
  value = block_given? ? block.call(item) : item
82
+
40
83
  hsh[value] = hsh.fetch(value, 0) + 1
41
84
  end # each
42
85
  end # method count_values
@@ -48,6 +91,8 @@ module SleepingKingStudios::Tools
48
91
  #
49
92
  # @return [Array] The copy of the array.
50
93
  def deep_dup ary
94
+ require_array! ary
95
+
51
96
  ary.map { |obj| ObjectTools.deep_dup obj }
52
97
  end # method deep_dup
53
98
 
@@ -74,7 +119,7 @@ module SleepingKingStudios::Tools
74
119
  # ArrayTools.humanize_list(['spam', 'eggs', 'bacon', 'spam'], :last_separator => ' or ')
75
120
  # #=> 'spam, eggs, bacon, or spam'
76
121
  #
77
- # @param [Array<String>] values The list of values to format. Will be
122
+ # @param [Array<String>] ary The list of values to format. Will be
78
123
  # coerced to strings using #to_s.
79
124
  # @param [Hash] options Optional configuration hash.
80
125
  # @option options [String] :last_separator The value to use to separate
@@ -85,18 +130,22 @@ module SleepingKingStudios::Tools
85
130
  # of values before the last in lists of length 3 or greater. Defaults to
86
131
  # ", " (note the trailing space).
87
132
  #
133
+ # @raise ArgumentError If the first argument is not an Array-like object.
134
+ #
88
135
  # @return [String] The formatted string.
89
- def humanize_list values, options = {}
136
+ def humanize_list ary, options = {}
137
+ require_array! ary
138
+
90
139
  separator = options.fetch(:separator, ', ')
91
140
  last_separator = options.fetch(:last_separator, ' and ')
92
141
 
93
- case values.count
142
+ case ary.count
94
143
  when 0
95
144
  ''
96
145
  when 1
97
- values.first.to_s
146
+ ary.first.to_s
98
147
  when 2
99
- "#{values[0]}#{last_separator}#{values[1]}"
148
+ "#{ary[0]}#{last_separator}#{ary[1]}"
100
149
  else
101
150
  if last_separator =~ /\A,?\s*/
102
151
  last_separator = last_separator.sub /\A,?\s*/, separator
@@ -104,8 +153,64 @@ module SleepingKingStudios::Tools
104
153
  last_separator = "#{separator}#{last_separator}"
105
154
  end # if-else
106
155
 
107
- "#{values[0...-1].join(separator)}#{last_separator}#{values.last}"
156
+ "#{ary[0...-1].join(separator)}#{last_separator}#{ary.last}"
108
157
  end # case
109
158
  end # method humanize_list
159
+
160
+ # Accepts an array, a start value, a number of items to delete, and zero or
161
+ # more items to insert at that index. Deletes the specified number of items,
162
+ # then inserts the given items at the index and returns the array of deleted
163
+ # items.
164
+ #
165
+ # @example Deleting items from an Array
166
+ # values = %w(katana wakizashi tachi daito shoto)
167
+ # ArrayTools.splice values, 1, 2
168
+ # #=> ['wakizashi', 'tachi']
169
+ # values
170
+ # #=> ['katana', 'daito', 'shoto']
171
+ #
172
+ # @example Inserting items into an Array
173
+ # values = %w(longsword broadsword claymore)
174
+ # ArrayTools.splice values, 1, 0, 'zweihänder'
175
+ # #=> []
176
+ # values
177
+ # #=> ['longsword', 'zweihänder', 'broadsword', 'claymore']
178
+ #
179
+ # @example Inserting and deleting items
180
+ # values = %w(shortbow longbow crossbow)
181
+ # ArrayTools.splice values, 2, 1, 'arbalest', 'chu-ko-nu'
182
+ # #=> ['crossbow']
183
+ # values
184
+ # #=> ['shortbow', 'longbow', 'arbalest', 'chu-ko-nu']
185
+ #
186
+ # @param [Array<Object>] ary The array to splice.
187
+ # @param [Integer] start The starting index to delete or insert values from
188
+ # or into. If negative, counts backward from the end of the array.
189
+ # @param [Integer] delete_count The number of items to delete.
190
+ # @param [Array<Object>] insert The items to insert, if any.
191
+ #
192
+ # @raise ArgumentError If the first argument is not an Array-like object.
193
+ #
194
+ # @return [Array<Object>] The deleted items, or an empty array if no items
195
+ # were deleted.
196
+ def splice ary, start, delete_count, *insert
197
+ require_array! ary
198
+
199
+ start = start < 0 ? start + ary.count : start
200
+ range = start...(start + delete_count)
201
+ deleted = ary[range]
202
+
203
+ ary[range] = insert
204
+
205
+ deleted
206
+ end # method splice
207
+
208
+ private
209
+
210
+ def require_array! value
211
+ methods = %i([] count each)
212
+
213
+ raise ArgumentError.new('argument must be an array') unless methods.reduce(true) { |memo, method_name| memo && value.respond_to?(method_name) }
214
+ end # method require_array
110
215
  end # module
111
216
  end # module
@@ -23,5 +23,30 @@ module SleepingKingStudios::Tools
23
23
  def pluralize count, single, plural
24
24
  1 == count ? single : plural
25
25
  end # method pluralize
26
+
27
+ # Converts a mixed-case string expression to a lowercase, underscore
28
+ # separated string.
29
+ #
30
+ # @param str [String] The string to convert.
31
+ #
32
+ # @return [String] The converted string.
33
+ #
34
+ # @see ActiveSupport::Inflector#underscore.
35
+ def underscore str
36
+ require_string! str
37
+
38
+ str = str.dup
39
+ str.gsub!(/([A-Z\d]+)([A-Z][a-z])/, '\1_\2')
40
+ str.gsub!(/([a-z\d])([A-Z])/, '\1_\2')
41
+ str.tr!("-", "_")
42
+ str.downcase!
43
+ str
44
+ end # method underscore
45
+
46
+ private
47
+
48
+ def require_string! value
49
+ raise ArgumentError.new('argument must be a string') unless value.is_a?(String)
50
+ end # method require_array
26
51
  end # module
27
52
  end # module
@@ -13,8 +13,9 @@ module SleepingKingStudios
13
13
  private
14
14
 
15
15
  MAJOR = 0
16
- MINOR = 2
16
+ MINOR = 3
17
17
  PATCH = 0
18
+ PRERELEASE = 'alpha'
18
19
  end # module
19
20
 
20
21
  VERSION = Version.to_gem_version
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sleeping_king_studios-tools
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 0.3.0.alpha
5
5
  platform: ruby
6
6
  authors:
7
7
  - Rob "Merlin" Smith
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-03-07 00:00:00.000000000 Z
11
+ date: 2016-04-03 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rake
@@ -114,9 +114,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
114
114
  version: '0'
115
115
  required_rubygems_version: !ruby/object:Gem::Requirement
116
116
  requirements:
117
- - - ">="
117
+ - - ">"
118
118
  - !ruby/object:Gem::Version
119
- version: '0'
119
+ version: 1.3.1
120
120
  requirements: []
121
121
  rubyforge_project:
122
122
  rubygems_version: 2.5.1