rand 0.9.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (8) hide show
  1. data/History.txt +25 -0
  2. data/Manifest.txt +7 -0
  3. data/README.txt +62 -0
  4. data/Rakefile +52 -0
  5. data/lib/rand.rb +319 -0
  6. data/setup.rb +1585 -0
  7. data/test/test_rand.rb +183 -0
  8. metadata +70 -0
@@ -0,0 +1,25 @@
1
+ == 0.9.1 / 2007-05-27
2
+
3
+ * (setup.rb) Added setup 3.4.1, for non-gem users.
4
+
5
+ * (Rakefile) Now we just require 'hoe' from seattle.rb and override
6
+ a few tasks which aren't generated to our liking. (Keegan Quinn, 2007-05-29)
7
+
8
+ * Rearranged files to match the usual Ruby project layout.
9
+ (Keegan Quinn, 2007-05-29)
10
+
11
+ * (install.rb) Removed old installation script. (Keegan Quinn, 2007-05-29)
12
+
13
+ * lib/rand.rb: New shuffle. (Ilmari Heikkinen, 2005-01-04)
14
+
15
+ * test/test_rand.rb: Bias tests. (Ilmari Heikkinen, 2005-01-04)
16
+
17
+ * lib/rand.rb: Document _with_index methods. (Christian Neukirchen, 2004-12-03)
18
+
19
+ * lib/rand.rb: Add pick_with_index. (Christian Neukirchen, 2004-12-02)
20
+
21
+
22
+ == 0.9.0 / 2004-11-29
23
+
24
+ * Initial release.
25
+
@@ -0,0 +1,7 @@
1
+ History.txt
2
+ Manifest.txt
3
+ README.txt
4
+ Rakefile
5
+ lib/rand.rb
6
+ setup.rb
7
+ test/test_rand.rb
@@ -0,0 +1,62 @@
1
+ = rand.rb -- library for picking random elements and shuffling
2
+
3
+ == Overview
4
+
5
+ rand.rb adds new methods to Enumerable, Array, and Hash to:
6
+
7
+ * return a random element (+pick+, +pick_index+, +pick_key+,
8
+ +pick_value+ and their destructive versions suffixed with
9
+ <tt>!</tt>).
10
+
11
+ * arrange elements in new, random order (+shuffle+,
12
+ +shuffle_hash_pairs+, +shuffle_hash+).
13
+
14
+ * use above methods in convenient ways (+each_random+, +map_random+).
15
+
16
+
17
+ It also provides these new facilities to String:
18
+
19
+ * +shuffle_chars+, to arrange the characters of the string in new order.
20
+
21
+ * +pick_byte+, +pick_char+ and +pick_index+, to return random bytes,
22
+ characters or elements.
23
+
24
+
25
+ == Limitations
26
+
27
+ * Enumerable#pick does not work for infinite Enumerables. (Doesn't
28
+ make sense, anyway.)
29
+
30
+ * Enumerable#pick has O(n) memory usage in worst case. There is an
31
+ alternative solution at [ruby-talk:94451], but not yet integrated
32
+ into rand.rb.
33
+
34
+ * Enumerable#shuffle is sightly biased due the limited number of
35
+ Floats between 0 and 1. This will possibly be addressed in a later
36
+ release.
37
+
38
+
39
+ == Authors
40
+
41
+ Ilmari Heikkinen <mailto:kig@misfiring.net>:: Code and unit tests
42
+ Christian Neukirchen <mailto:chneukirchen@gmail.com>:: Documentation and
43
+ housekeeping.
44
+
45
+ Please mail bugs, feature requests or patches to the mail addresses
46
+ above or use IRC[irc://freenode.net/#ruby-lang] to contact the
47
+ developers.
48
+
49
+
50
+ == History
51
+
52
+ November 26, 2004:: Initial version done as IRC collaboration project
53
+ between <tt>kig</tt> and <tt>chris2</tt>.
54
+
55
+ November 29, 2004:: First public release 0.9.
56
+
57
+
58
+ == Copyright
59
+
60
+ Copyright (C) 2004 Ilmari Heikkinen
61
+ Parts Copyright (C) 2004 Christian Neukirchen
62
+ This work is licensed under the same terms as Ruby itself.
@@ -0,0 +1,52 @@
1
+ # $Id: Rakefile 24 2007-07-14 13:24:11Z keegan $
2
+ # Copyright 2007 Keegan Quinn
3
+ #
4
+ # Rakefile for rand, a library to shuffle and pick elements at random.
5
+ #
6
+ # This script can be redistributed and/or modified under the terms of the
7
+ # Ruby license. It comes without any warranty, to the extent permitted by
8
+ # applicable law.
9
+
10
+
11
+ SHORTNAME = 'rand'
12
+ PKG_FILES = [ '[A-Z]*', 'setup.rb', 'lib/**/*.rb', 'test/**/*.rb' ]
13
+ PKG_VERSION = '0.9.1'
14
+ RDOC_OPTIONS = [
15
+ '--title', 'rand -- Random elements and shuffling', '--main', 'README.txt',
16
+ '--line-numbers', '--inline-source', '--all'
17
+ ]
18
+
19
+
20
+ # Generate tasks with hoe
21
+ require 'hoe'
22
+
23
+ h = Hoe.new(SHORTNAME, PKG_VERSION) do |p|
24
+ p.rubyforge_name = SHORTNAME
25
+ p.summary = 'A library for picking random elements and shuffling.'
26
+ p.description = p.summary
27
+
28
+ p.changes = p.paragraphs_of('History.txt', 0..1).join("\n\n")
29
+
30
+ p.url = 'http://rand.rubyforge.org'
31
+ p.email = 'keegan@rubyforge.org'
32
+ p.author = [ 'Ilmari Heikkinen', 'Christian Neukirchen', 'Keegan Quinn' ]
33
+
34
+ p.need_zip = true
35
+ p.remote_rdoc_dir = 'rdoc'
36
+
37
+ p.spec_extras = { 'rdoc_options' => RDOC_OPTIONS }
38
+ end
39
+
40
+ Rake::RDocTask.new(:docs) do |rd|
41
+ rd.main = "README.txt"
42
+ rd.options << '-d' if RUBY_PLATFORM !~ /win32/ and `which dot` =~ /\/dot/
43
+ rd.rdoc_dir = 'doc'
44
+
45
+ files = h.spec.files.grep(/^(lib|bin)|txt$/)
46
+ files -= ['Manifest.txt']
47
+ rd.rdoc_files.push(*files)
48
+
49
+ title = "#{h.name}-#{h.version} Documentation"
50
+
51
+ rd.options << "-t #{title}"
52
+ end
@@ -0,0 +1,319 @@
1
+ # $Id: rand.rb 23 2007-07-14 13:13:48Z keegan $
2
+ # Copyright 2007 Keegan Quinn
3
+ # Copyright 2004 Christian Neukirchen
4
+ # Copyright 2004 Ilmari Heikkinen
5
+ #
6
+ # rand.rb -- library for picking random elements and shuffling
7
+
8
+
9
+ module Enumerable
10
+ # Choose and return a random element of the Enumerable.
11
+ # [1, 2, 3, 4].pick #=> 2 (or 1, 3, 4)
12
+ def pick
13
+ entries.pick
14
+ end
15
+
16
+ # Return an array of the elements in random order.
17
+ # [1, 2, 3, 4].shuffle #=> [3, 4, 1, 2]
18
+ def shuffle
19
+ entries.shuffle
20
+ end
21
+
22
+ # Calls _block_ once for each element in _self_ in random order,
23
+ # passing that element as a parameter.
24
+ def each_random(&block)
25
+ shuffle.each(&block)
26
+ end
27
+
28
+ # Invokes _block_ once for each element of _self_ in random order.
29
+ # Creates a new array containing the values returned by the block.
30
+ def map_random(&block)
31
+ shuffle.map(&block)
32
+ end
33
+ end
34
+
35
+
36
+ class Array
37
+ # Choose and return a random element of _self_.
38
+ # [1, 2, 3, 4].pick #=> 2 (or 1, 3, 4)
39
+ def pick
40
+ self[pick_index]
41
+ end
42
+
43
+ # Deletes a random element of _self_, returning that element.
44
+ # a = [1, 2, 3, 4]
45
+ # a.pick #=> 2
46
+ # a #=> [1, 3, 4]
47
+ def pick!
48
+ i = pick_index
49
+ rv = self[i]
50
+ delete_at(i)
51
+ rv
52
+ end
53
+
54
+ # Return the index of an random element of _self_.
55
+ # ["foo", "bar", "baz"].pick_index #=> 1 (or 0, or 2)
56
+ def pick_index
57
+ rand(size)
58
+ end
59
+
60
+ # Destructive pick_index. Delete a random element of _self_ and
61
+ # return its index.
62
+ # a = [11, 22, 33, 44]
63
+ # a.pick_index! #=> 2
64
+ # a #=> [11, 22, 44]
65
+ def pick_index!
66
+ i = pick_index
67
+ delete_at i
68
+ i
69
+ end
70
+
71
+ # Return a random element of _self_ with its index.
72
+ # a = ["a", "b", "c", "d"]
73
+ # a.pick_with_index #=> ["b", 1]
74
+ # a #=> ["a", "b", "c", "d"]
75
+ def pick_with_index
76
+ i = pick_index
77
+ [self[i], i]
78
+ end
79
+
80
+ # Delete and return a random element of _self_ with its index.
81
+ # a = ["a", "b", "c", "d"]
82
+ # a.pick_with_index! #=> ["b", 1]
83
+ # a #=> ["a", "c", "d"]
84
+ def pick_with_index!
85
+ rv = pick_with_index
86
+ delete_at rv[1]
87
+ rv
88
+ end
89
+
90
+ # Return an array of the elements in random order.
91
+ # [11, 22, 33, 44].shuffle #=> [33, 11, 44, 22]
92
+ def shuffle
93
+ dup.shuffle!
94
+ end
95
+
96
+ # Destructive shuffle. Arrange the elements of _self_ in new order.
97
+ # Using Fisher-Yates shuffle.
98
+ # a = [11, 22, 33, 44]
99
+ # a.shuffle!
100
+ # a #=> [33, 11, 44, 22]
101
+ def shuffle!
102
+ (size-1).downto(1) {|index|
103
+ other_index = rand(index+1)
104
+ next if index == other_index
105
+ tmp = self[index]
106
+ self[index] = self[other_index]
107
+ self[other_index] = tmp
108
+ }
109
+ self
110
+ end
111
+ end
112
+
113
+
114
+ class Hash
115
+ # Choose and return a random key-value pair of _self_.
116
+ # {:one => 1, :two => 2, :three => 3}.pick #=> [:one, 1]
117
+ def pick
118
+ k = keys.pick
119
+ [k, self[k]]
120
+ end
121
+
122
+ # Deletes a random key-value pair of _self_, returning that pair.
123
+ # a = {:one => 1, :two => 2, :three => 3}
124
+ # a.pick #=> [:two, 2]
125
+ # a #=> {:one => 1, :three => 3}
126
+ def pick!
127
+ rv = pick
128
+ delete rv.first
129
+ rv
130
+ end
131
+
132
+ # Return a random key of _self_.
133
+ # {:one => 1, :two => 2, :three => 3}.pick_key #=> :three
134
+ def pick_key
135
+ keys.pick
136
+ end
137
+
138
+ # Return a random value of _self_.
139
+ # {:one => 1, :two => 2, :three => 3}.pick_value #=> 3
140
+ def pick_value
141
+ values.pick
142
+ end
143
+
144
+ # Delete a random key-value pair of _self_ and return the key.
145
+ # a = {:one => 1, :two => 2, :three => 3}
146
+ # a.pick_key! #=> :two
147
+ # a #=> {:one => 1, :three => 3}
148
+ def pick_key!
149
+ pick!.first
150
+ end
151
+
152
+ # Delete a random key-value pair of _self_ and return the value.
153
+ # a = {:one => 1, :two => 2, :three => 3}
154
+ # a.pick_value! #=> 2
155
+ # a #=> {:one => 1, :three => 3}
156
+ def pick_value!
157
+ pick!.last
158
+ end
159
+
160
+ # Return the key-value pairs of _self_ with _keys_ and _values_
161
+ # shuffled independedly.
162
+ # {:one => 1, :two => 2, :three => 3}.shuffle_hash_pairs
163
+ # #=> [[:one, 3], [:two, 1], [:three, 2]]
164
+ def shuffle_hash_pairs
165
+ keys.shuffle.zip(values.shuffle)
166
+ end
167
+
168
+ # Return a copy of _self_ with _values_ arranged in random order.
169
+ # {:one => 1, :two => 2, :three => 3}.shuffle_hash
170
+ # #=> {:two=>2, :three=>1, :one=>3}
171
+ def shuffle_hash
172
+ shuffled = {}
173
+ shuffle_hash_pairs.each{|k, v|
174
+ shuffled[k] = v
175
+ }
176
+ shuffled
177
+ end
178
+
179
+ # Destructive shuffle_hash. Arrange the values of _self_ in
180
+ # new, random order.
181
+ # h = {:one => 1, :two => 2, :three => 3}
182
+ # h.shuffle_hash!
183
+ # h #=> {:two=>2, :three=>1, :one=>3}
184
+ def shuffle_hash!
185
+ shuffle_hash_pairs.each{|k, v|
186
+ self[k] = v
187
+ }
188
+ self
189
+ end
190
+ end
191
+
192
+
193
+ class String
194
+ # Return the string with characters arranged in random order.
195
+ # "Ruby rules".shuffle_chars #=> "e lybRsuur"
196
+ def shuffle_chars
197
+ dup.shuffle_chars!
198
+ end
199
+
200
+ # Destructive shuffle_chars. Arrange the characters of the string
201
+ # in new, random order.
202
+ # s = "Ruby rules".shuffle_chars
203
+ # s.shuffle_chars!
204
+ # s #=> "e lybRsuur"
205
+ def shuffle_chars!
206
+ (0...size).each {|j|
207
+ i = rand(size-j)
208
+ self[j], self[j+i] = self[j+i], self[j]
209
+ }
210
+ self
211
+ end
212
+
213
+ # Return a random byte of _self_.
214
+ # "Ruby rules".pick_byte #=> 121
215
+ def pick_byte
216
+ self[pick_index]
217
+ end
218
+
219
+ # Return a single-character string of a random character in _self_.
220
+ # "Ruby rules".pick_char #=> "y"
221
+ def pick_char
222
+ pick_byte.chr
223
+ end
224
+
225
+ # Destructive pick_char. Delete a random character of the string
226
+ # and return it as a single-character string.
227
+ # s = "Ruby rules"
228
+ # s.pick_char! #=> "y"
229
+ # s #=> "Rub rules"
230
+ def pick_char!
231
+ i = pick_index
232
+ rv = self[i,1]
233
+ self[i,1] = ""
234
+ rv
235
+ end
236
+
237
+ # Destructive pick_byte. Delete a random byte of _self_ and return it.
238
+ # s = "Ruby rules"
239
+ # s.pick_byte! #=> 121
240
+ # s #=> "Rub rules"
241
+ def pick_byte!
242
+ pick_char![0]
243
+ end
244
+
245
+ # Return a random byte index of _self_.
246
+ # "Ruby rules".pick_index #=> 3
247
+ def pick_index
248
+ rand(size)
249
+ end
250
+
251
+ # Destructive pick_index. Delete a random byte of _self_ and
252
+ # return it's index.
253
+ # s = "Ruby rules"
254
+ # s.pick_index #=> 3
255
+ # s #=> "Rub rules"
256
+ def pick_index!
257
+ i = pick_index
258
+ self[i,1] = ""
259
+ i
260
+ end
261
+
262
+ # Return a two element array consisting of an random byte of _self_
263
+ # and it's index.
264
+ # "Ruby rules".pick_byte_with_index #=> [121, 3]
265
+ def pick_byte_with_index
266
+ i = pick_index
267
+ [self[i], i]
268
+ end
269
+
270
+ # Destructive pick_byte_with_index. Delete a random byte of _self_
271
+ # and return it and it's index.
272
+ # s = "Ruby rules"
273
+ # s.pick_byte_with index! #=> [121, 3]
274
+ # s #=> "Rub rules"
275
+ def pick_byte_with_index!
276
+ rv = pick_byte_with_index
277
+ delete_at(rv[0])
278
+ rv
279
+ end
280
+
281
+ # Return a single-character string of a random character in _self_
282
+ # and it's index.
283
+ # "Ruby rules".pick_char_with_index #=> ["y", 3]
284
+ def pick_char_with_index
285
+ byte, index = pick_byte_with_index
286
+ [byte.chr, index]
287
+ end
288
+
289
+ # Destructive pick_char_with_index. Delete a random character of
290
+ # the string and return it as a single-character string together
291
+ # with it's index.
292
+ # s = "Ruby rules"
293
+ # s.pick_char_with_index! #=> ["y", 3]
294
+ # s #=> "Rub rules"
295
+ def pick_char_with_index!
296
+ byte, index = pick_byte_with_index!
297
+ [byte.chr, index]
298
+ end
299
+
300
+ def pick
301
+ to_a.pick
302
+ end
303
+
304
+ def pick!
305
+ pick_with_index![0]
306
+ end
307
+
308
+ def pick_with_index
309
+ to_a.pick_with_index
310
+ end
311
+
312
+ def pick_with_index!
313
+ tokens = to_a
314
+ s, index = tokens.pick_with_index
315
+ start = tokens[0, index].join
316
+ self[start.size, s.size] = ""
317
+ [s, index]
318
+ end
319
+ end