epitools 0.4.26 → 0.4.28

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.
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.4.26
1
+ 0.4.28
data/epitools.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{epitools}
8
- s.version = "0.4.26"
8
+ s.version = "0.4.28"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["epitron"]
12
- s.date = %q{2011-04-15}
12
+ s.date = %q{2011-04-27}
13
13
  s.description = %q{Miscellaneous utility libraries to make my life easier.}
14
14
  s.email = %q{chris@ill-logic.com}
15
15
  s.extra_rdoc_files = [
@@ -31,6 +31,7 @@ Gem::Specification.new do |s|
31
31
  "lib/epitools/clitools.rb",
32
32
  "lib/epitools/colored.rb",
33
33
  "lib/epitools/hexdump.rb",
34
+ "lib/epitools/its.rb",
34
35
  "lib/epitools/lcs.rb",
35
36
  "lib/epitools/metaclass.rb",
36
37
  "lib/epitools/niceprint.rb",
@@ -449,6 +449,21 @@ class Object
449
449
  obj
450
450
  end
451
451
 
452
+
453
+ #
454
+ # Return a copy of the class with modules mixed into it.
455
+ #
456
+ def self.using(*args)
457
+ if block_given?
458
+ yield using(*args)
459
+ else
460
+ copy = self.dup
461
+ args.each { |arg| copy.send(:include, arg) }
462
+ copy
463
+ end
464
+ end
465
+
466
+
452
467
  #
453
468
  # Instead of:
454
469
  # if cookie_jar.include? cookie
@@ -502,6 +517,7 @@ class Object
502
517
  end
503
518
 
504
519
 
520
+
505
521
  class Hash
506
522
 
507
523
  #
@@ -584,65 +600,57 @@ class Hash
584
600
  def self.of_integers
585
601
  new(0)
586
602
  end
587
-
588
- end
589
603
 
590
- unless defined?(BasicObject)
591
604
  #
592
- # A BasicObject class for Ruby 1.8
605
+ # Makes each element in the `path` array point to a hash containing the next element in the `path`.
606
+ # Useful for turning a bunch of strings (paths, module names, etc.) into a tree.
593
607
  #
594
- class BasicObject
595
- instance_methods.each { |m| undef_method m unless m =~ /^__/ }
608
+ # Example:
609
+ # h = {}
610
+ # h.mkdir_p(["a", "b", "c"]) #=> {"a"=>{"b"=>{"c"=>{}}}}
611
+ # h.mkdir_p(["a", "b", "whoa"]) #=> {"a"=>{"b"=>{"c"=>{}, "whoa"=>{}}}}
612
+ #
613
+ def mkdir_p(path)
614
+ return if path.empty?
615
+ dir = path.first
616
+ self[dir] ||= {}
617
+ self[dir].mkdir_p(path[1..-1])
618
+ self
596
619
  end
597
- end
598
-
599
-
600
- module Kernel
601
-
602
- protected
603
-
604
- #
605
- # Magic "its" Mapping
606
- # -------------------
620
+
607
621
  #
608
- # The pure-Ruby way:
609
- # User.find(:all).map{|x| x.contacts.map{|y| y.last_name.capitalize }}
622
+ # Turn some nested hashes into a tree (returns an array of strings, padded on the left with indents.)
610
623
  #
611
- # With Symbol#to_proc:
612
- # User.find(:all).map{|x|x.contacts.map(&:last_name).map(&:capitalize)}
624
+ def tree(level=0, indent=" ")
625
+ result = []
626
+ dent = indent * level
627
+ each do |key, val|
628
+ result << dent+key
629
+ result += val.tree(level+1) if val.any?
630
+ end
631
+ result
632
+ end
633
+
613
634
  #
614
- # Magic "its" way:
615
- # User.find(:all).map &its.contacts.map(&its.last_name.capitalize)
635
+ # Print the result of `tree`
616
636
  #
617
- def it()
618
- It.new
619
- end
620
-
621
- alias its it
622
-
637
+ def print_tree
638
+ tree.each { |row| puts row }
639
+ nil
640
+ end
641
+
623
642
  end
624
643
 
625
-
626
- class It < BasicObject # :nodoc:
627
- #undef_method( *(instance_methods - ["__id__", "__send__"]) )
628
-
629
- def initialize
630
- @methods = []
644
+ unless defined?(BasicObject)
645
+ #
646
+ # A BasicObject class for Ruby 1.8
647
+ #
648
+ class BasicObject
649
+ instance_methods.each { |m| undef_method m unless m =~ /^__/ }
631
650
  end
651
+ end
632
652
 
633
- def method_missing(*args, &block)
634
- @methods << [args, block] unless args == [:respond_to?, :to_proc]
635
- self
636
- end
637
653
 
638
- def to_proc
639
- lambda do |obj|
640
- @methods.inject(obj) do |current,(args,block)|
641
- current.send(*args, &block)
642
- end
643
- end
644
- end
645
- end
646
654
 
647
655
  class NotWrapper < BasicObject # :nodoc:
648
656
  def initialize(orig)
@@ -0,0 +1,48 @@
1
+
2
+ module Kernel
3
+
4
+ protected
5
+
6
+ #
7
+ # Magic "its" Mapping
8
+ # -------------------
9
+ #
10
+ # The pure-Ruby way:
11
+ # User.find(:all).map{|x| x.contacts.map{|y| y.last_name.capitalize }}
12
+ #
13
+ # With Symbol#to_proc:
14
+ # User.find(:all).map{|x|x.contacts.map(&:last_name).map(&:capitalize)}
15
+ #
16
+ # Magic "its" way:
17
+ # User.find(:all).map &its.contacts.map(&its.last_name.capitalize)
18
+ #
19
+ def it()
20
+ It.new
21
+ end
22
+
23
+ alias its it
24
+
25
+ end
26
+
27
+
28
+ class It < BasicObject # :nodoc:
29
+ #undef_method( *(instance_methods - ["__id__", "__send__"]) )
30
+
31
+ def initialize
32
+ @methods = []
33
+ end
34
+
35
+ def method_missing(*args, &block)
36
+ @methods << [args, block] unless args == [:respond_to?, :to_proc]
37
+ self
38
+ end
39
+
40
+ def to_proc
41
+ lambda do |obj|
42
+ @methods.inject(obj) do |current,(args,block)|
43
+ current.send(*args, &block)
44
+ end
45
+ end
46
+ end
47
+ end
48
+
@@ -2,29 +2,43 @@ require 'epitools/basetypes'
2
2
  require 'bigdecimal'
3
3
  require 'set'
4
4
 
5
+ #
6
+ # Allow numbers to be converted into words, or exprssed more easily with words.
7
+ #
8
+ # Examples:
9
+ # >> 1.thousand
10
+ # => 1_000
11
+
12
+ # >> 1.27.million.billion
13
+ # => 1_270_000_000_000_000
14
+ #
15
+ # >> 12873218731.to_words
16
+ # => "twelve billion, eight-hundred and seventy-three million, two-hundred and eighteen thousand, seven-hundred and thirty-one"
17
+ #
18
+ # Works on numbers up to a googol!
19
+ #
5
20
  class Numeric
6
21
 
22
+ # < 20
7
23
  NAMES_SMALL = [
8
24
  "zero", "one", "two", "three", "four", "five", "six", "seven", "eight", "nine", "ten", "eleven", "twelve", "thirteen", "fourteen", "fifteen", "sixteen", "seventeen", "eighteen", "nineteen"
9
25
  ]
10
26
 
27
+ # 20-90
11
28
  NAMES_MEDIUM = [
12
29
  "twenty", "thirty", "fourty", "fifty", "sixty", "seventy", "eighty", "ninety"
13
30
  ]
14
31
 
32
+ # >= 100
15
33
  NAMES_LARGE = [
16
34
  "thousand", "million", "billion", "trillion", "quadrillion", "quintillion", "sextillion", "septillion", "octillion", "nonillion", "decillion", "undecillion", "duodecillion", "tredecillion", "quattuordecillion", "quindecillion", "sexdecillion", "septendecillion", "octodecillion", "novemdecillion", "vigintillion", "unvigintillion", "duovigintillion", "trevigintillion", "quattuorvigintillion", "quinvigintillion", "sexvigintillion", "septenvigintillion", "octovigintillion", "novemvigintillion", "trigintillion", "untrigintillion", "duotrigintillion"
17
35
  ]
18
36
 
19
- NAMES_LARGE_LOOKUP = Set.new(NAMES_LARGE)
20
-
21
-
22
37
  #
23
38
  # Convert this number to words (eg: 69 => 'sixty-nine').
24
39
  # Works with numbers up to a googol (10^100).
25
40
  #
26
41
  def to_words
27
-
28
42
  if is_a? Integer
29
43
  num = self
30
44
  else
@@ -93,18 +107,13 @@ class Numeric
93
107
  end
94
108
 
95
109
  whole_thing.join ', '
96
-
97
110
  end
98
-
111
+
99
112
  #
100
- # Gives all numbers ".thousand", ".million", up to ".duotrigintillion" methods.
101
- # eg: 10.million #=> 10_000_000
113
+ # Define the .million, .thousand, .hundred, etc. methods.
102
114
  #
103
- def method_missing(meth, &block)
104
- super
105
- rescue NoMethodError
106
- if NAMES_LARGE_LOOKUP.include? meth.to_s
107
- magnitude = NAMES_LARGE.index(meth.to_s)
115
+ NAMES_LARGE.each_with_index do |name, magnitude|
116
+ define_method name do
108
117
  pow = (magnitude+1) * 3
109
118
  factor = 10**pow
110
119
 
@@ -113,8 +122,6 @@ class Numeric
113
122
  else
114
123
  self * factor
115
124
  end
116
- else
117
- raise NoMethodError.new(meth)
118
125
  end
119
126
  end
120
127
 
@@ -73,6 +73,32 @@ describe Object do
73
73
 
74
74
  end
75
75
 
76
+
77
+ describe Class do
78
+
79
+ it "uses" do
80
+ module Test1
81
+ def test1; :test1; end
82
+ end
83
+
84
+ module Test2
85
+ def test2; :test2; end
86
+ end
87
+
88
+ Hash.using(Test1).new.test1.should == :test1
89
+ Hash.using(Test2).new.test2.should == :test2
90
+ h = Hash.using(Test1, Test2).new
91
+ h.test1.should == :test1
92
+ h.test2.should == :test2
93
+
94
+ Hash.using(Test1) do |h|
95
+ h.new.test1.should == :test1
96
+ end
97
+ end
98
+
99
+ end
100
+
101
+
76
102
  describe Numeric do
77
103
 
78
104
  it "commatizes" do
@@ -85,6 +111,7 @@ describe Numeric do
85
111
 
86
112
  end
87
113
 
114
+
88
115
  describe String do
89
116
 
90
117
  it "rot13s" do
@@ -95,6 +122,7 @@ describe String do
95
122
 
96
123
  end
97
124
 
125
+
98
126
  describe Integer do
99
127
 
100
128
  it "integer?" do
@@ -242,6 +270,16 @@ describe Hash do
242
270
  h.values.should == [1,1]
243
271
  end
244
272
 
273
+ it "mkdir_p's and trees" do
274
+ h = {}
275
+ h.mkdir_p(["a", "b", "c"]).should == {"a"=>{"b"=>{"c"=>{}}}}
276
+ h.mkdir_p(["a", "b", "whoa"]).should == {"a"=>{"b"=>{"c"=>{}, "whoa"=>{}}}}
277
+
278
+ lambda {
279
+ h.tree.should == ["a", " b", " c", " whoa"]
280
+ }.should_not raise_error
281
+ end
282
+
245
283
  end
246
284
 
247
285
 
metadata CHANGED
@@ -2,7 +2,7 @@
2
2
  name: epitools
3
3
  version: !ruby/object:Gem::Version
4
4
  prerelease:
5
- version: 0.4.26
5
+ version: 0.4.28
6
6
  platform: ruby
7
7
  authors:
8
8
  - epitron
@@ -10,7 +10,7 @@ autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
12
 
13
- date: 2011-04-15 00:00:00 -04:00
13
+ date: 2011-04-27 00:00:00 -04:00
14
14
  default_executable:
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
@@ -70,6 +70,7 @@ files:
70
70
  - lib/epitools/clitools.rb
71
71
  - lib/epitools/colored.rb
72
72
  - lib/epitools/hexdump.rb
73
+ - lib/epitools/its.rb
73
74
  - lib/epitools/lcs.rb
74
75
  - lib/epitools/metaclass.rb
75
76
  - lib/epitools/niceprint.rb