rubystructures 0.0.2 → 0.0.3
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/lib/rubystructures.rb +2 -0
- data/lib/rubystructures/linked_list.rb +206 -0
- data/lib/rubystructures/node.rb +22 -0
- data/lib/rubystructures/version.rb +1 -1
- data/spec/linked_list_spec.rb +258 -0
- data/spec/node_spec.rb +15 -0
- metadata +8 -2
data/lib/rubystructures.rb
CHANGED
@@ -0,0 +1,206 @@
|
|
1
|
+
module RubyStructures
|
2
|
+
class LinkedList
|
3
|
+
# Public: Create a new instance of LinkedList
|
4
|
+
#
|
5
|
+
# Examples
|
6
|
+
#
|
7
|
+
# @linked_list = RubyStructures::LinkedList.new
|
8
|
+
# # => LinkedList
|
9
|
+
#
|
10
|
+
# Returns a new instance of LinkedList.
|
11
|
+
def initialize
|
12
|
+
@head = RubyStructures::Node.new(self, nil)
|
13
|
+
end
|
14
|
+
|
15
|
+
# Public: Returns the value at the head of the LinkedList.
|
16
|
+
#
|
17
|
+
# Examples
|
18
|
+
#
|
19
|
+
# @linked_list.head
|
20
|
+
# # => 42
|
21
|
+
#
|
22
|
+
# Returns the value held by the Node at the head of the list, otherwise
|
23
|
+
# if the list is empty, returns nil.
|
24
|
+
def head
|
25
|
+
@head.next
|
26
|
+
end
|
27
|
+
|
28
|
+
# Public: Checks to see if the LinkedList is empty.
|
29
|
+
#
|
30
|
+
# Examples
|
31
|
+
#
|
32
|
+
# @linked_list.empty?
|
33
|
+
# # => false
|
34
|
+
#
|
35
|
+
# Returns true if the LinkedList is empty, returns false otherwise.
|
36
|
+
def empty?
|
37
|
+
@head.next == nil
|
38
|
+
end
|
39
|
+
|
40
|
+
# Public: Add a value to the beginning of the LinkedList
|
41
|
+
#
|
42
|
+
# value - Ruby object to be inserted into the LinkedList
|
43
|
+
#
|
44
|
+
# Examples
|
45
|
+
#
|
46
|
+
# @linked_list.prepend(42)
|
47
|
+
# # => Node
|
48
|
+
#
|
49
|
+
# Returns the Node added to the LinkedList.
|
50
|
+
def prepend(value)
|
51
|
+
element = RubyStructures::Node.new(self, value)
|
52
|
+
element.next = @head.next
|
53
|
+
@head.next = element
|
54
|
+
end
|
55
|
+
|
56
|
+
# Public: Add a value to the end of the LinkedList
|
57
|
+
#
|
58
|
+
# value - Ruby object to be inserted into the LinkedList
|
59
|
+
#
|
60
|
+
# Examples
|
61
|
+
#
|
62
|
+
# @linked_list.append(42)
|
63
|
+
# # => Node
|
64
|
+
#
|
65
|
+
# Returns the Node added to the LinkedList.
|
66
|
+
def append(value)
|
67
|
+
if self.empty?
|
68
|
+
self.prepend(value)
|
69
|
+
return
|
70
|
+
end
|
71
|
+
|
72
|
+
element = self.head
|
73
|
+
# loop through each element in the LinkedList, until element.next
|
74
|
+
# equals @head, signifying we have reached the end of the list.
|
75
|
+
while(element != self.head)
|
76
|
+
element = element.next
|
77
|
+
end
|
78
|
+
|
79
|
+
new_element = RubyStructures::Node.new(self, value)
|
80
|
+
# insert the new element at the end of the LinkedList.
|
81
|
+
new_element.next = element.next
|
82
|
+
element.next = new_element
|
83
|
+
end
|
84
|
+
|
85
|
+
# Public: Find an element by its value and return it.
|
86
|
+
#
|
87
|
+
# value - Ruby object to be inserted into the LinkedList
|
88
|
+
#
|
89
|
+
# Examples
|
90
|
+
#
|
91
|
+
# @linked_list.search(42)
|
92
|
+
# # => 42
|
93
|
+
#
|
94
|
+
# Returns the value of the element if it is in the LinkedList, returns
|
95
|
+
# nil otherwise.
|
96
|
+
def search(value)
|
97
|
+
return nil if self.empty?
|
98
|
+
element = self.head
|
99
|
+
while element.value != value
|
100
|
+
if element.next.nil?
|
101
|
+
return nil
|
102
|
+
else
|
103
|
+
element = element.next
|
104
|
+
end
|
105
|
+
end
|
106
|
+
element
|
107
|
+
end
|
108
|
+
|
109
|
+
# Public: Gets the Node at the head of the LinkedList.
|
110
|
+
#
|
111
|
+
# Examples
|
112
|
+
#
|
113
|
+
# @linked_list.item_at_head
|
114
|
+
# # => #<Node: >
|
115
|
+
#
|
116
|
+
# Returns the Node at the head of the LinkedList.
|
117
|
+
def item_at_head
|
118
|
+
@head.next
|
119
|
+
end
|
120
|
+
|
121
|
+
# Public: Returns the Node at the desired :index.
|
122
|
+
#
|
123
|
+
# index - the Integer index value of Node to return.
|
124
|
+
#
|
125
|
+
# Examples
|
126
|
+
#
|
127
|
+
# @linked_list.item_at(42)
|
128
|
+
# # => #<Node: >
|
129
|
+
#
|
130
|
+
# Returns a Node located at position :index in the LinkedList.
|
131
|
+
def item_at(index)
|
132
|
+
element = self.head
|
133
|
+
count = 0
|
134
|
+
while count < index
|
135
|
+
return nil if element.nil?
|
136
|
+
element = element.next
|
137
|
+
count += 1
|
138
|
+
end
|
139
|
+
element
|
140
|
+
end
|
141
|
+
|
142
|
+
# Public: Finds and removes the first occurrence of a Node with the
|
143
|
+
# desired value.
|
144
|
+
#
|
145
|
+
# value - the Ruby object value to find and remove from the LinkedList
|
146
|
+
#
|
147
|
+
# Examples
|
148
|
+
#
|
149
|
+
# @linked_list.remove(42)
|
150
|
+
# # => #<Node: >
|
151
|
+
#
|
152
|
+
# Returns the node that was removed from the LinkedList
|
153
|
+
def remove(value)
|
154
|
+
element = self.head
|
155
|
+
previous_element = @head
|
156
|
+
while element.value != value
|
157
|
+
if element.next.nil?
|
158
|
+
return nil
|
159
|
+
else
|
160
|
+
previous_element = element
|
161
|
+
element = element.next
|
162
|
+
end
|
163
|
+
end
|
164
|
+
|
165
|
+
previous_element.next = element.next
|
166
|
+
element
|
167
|
+
end
|
168
|
+
|
169
|
+
# Public: Removes the Node at the head of the LinkedList.
|
170
|
+
#
|
171
|
+
# Examples
|
172
|
+
#
|
173
|
+
# @linked_list.remove_at_head
|
174
|
+
# # => #<Node: >
|
175
|
+
#
|
176
|
+
# Returns the Node at the head of the list.
|
177
|
+
def remove_at_head
|
178
|
+
return nil if self.empty?
|
179
|
+
element = self.head
|
180
|
+
@head.next = nil || element.next
|
181
|
+
element
|
182
|
+
end
|
183
|
+
|
184
|
+
# Public: Removes the Node at the tail of the LinkedList.
|
185
|
+
#
|
186
|
+
# Examples
|
187
|
+
#
|
188
|
+
# @linked_list.remove_at_tail
|
189
|
+
# # => #<Node: >
|
190
|
+
#
|
191
|
+
# Returns
|
192
|
+
def remove_at_tail
|
193
|
+
return nil if self.empty?
|
194
|
+
element = self.head
|
195
|
+
previous_element = @head
|
196
|
+
|
197
|
+
until element.next.nil?
|
198
|
+
previous_element = element
|
199
|
+
element = element.next
|
200
|
+
end
|
201
|
+
|
202
|
+
previous_element.next = nil
|
203
|
+
element
|
204
|
+
end
|
205
|
+
end
|
206
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
module RubyStructures
|
2
|
+
class Node
|
3
|
+
attr_accessor :value
|
4
|
+
attr_accessor :next
|
5
|
+
attr_reader :list
|
6
|
+
|
7
|
+
# Internal: Creates a new instance of Node.
|
8
|
+
#
|
9
|
+
# list - instance of LinkedList to which the Node belongs.
|
10
|
+
# value - the value to be stored in the Node.
|
11
|
+
#
|
12
|
+
# Examples
|
13
|
+
#
|
14
|
+
# @node = RubyStructures::Node.new
|
15
|
+
#
|
16
|
+
# Returns a new instance of Node.
|
17
|
+
def initialize(list, value)
|
18
|
+
@list = list
|
19
|
+
@value = value
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,258 @@
|
|
1
|
+
require 'rubystructures'
|
2
|
+
|
3
|
+
describe RubyStructures::LinkedList do
|
4
|
+
before(:each) { @linked_list = RubyStructures::LinkedList.new }
|
5
|
+
|
6
|
+
describe "#initialize" do
|
7
|
+
it "class should be LinkedList" do
|
8
|
+
expect(@linked_list.class).to eql RubyStructures::LinkedList
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
describe "#head" do
|
13
|
+
context "when the LinkedList is empty" do
|
14
|
+
it "head has value of nil" do
|
15
|
+
expect(@linked_list.head).to eql nil
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
context "when the LinkedList is not empty" do
|
20
|
+
before { @linked_list.prepend(42) }
|
21
|
+
it "head returns an element" do
|
22
|
+
expect(@linked_list.head.class).to eql RubyStructures::Node
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
describe "#empty" do
|
28
|
+
context "when the LinkedList is empty" do
|
29
|
+
it "returns true" do
|
30
|
+
expect(@linked_list.empty?).to eql true
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
context "when the LinkedList is not empty" do
|
35
|
+
before { @linked_list.prepend(42) }
|
36
|
+
it "returns false" do
|
37
|
+
expect(@linked_list.empty?).to eql false
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
describe "#prepend" do
|
43
|
+
before(:each) { @linked_list.prepend(42) }
|
44
|
+
|
45
|
+
it "empty? returns false" do
|
46
|
+
expect(@linked_list.empty?).to eql false
|
47
|
+
end
|
48
|
+
|
49
|
+
it "has the correct value" do
|
50
|
+
expect(@linked_list.head.value).to eql 42
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
describe "#append" do
|
55
|
+
context "when the list is empty" do
|
56
|
+
it "adds the element to the LinkedList" do
|
57
|
+
expect(@linked_list.head).to eql nil
|
58
|
+
@linked_list.append(42)
|
59
|
+
expect(@linked_list.head.value).to eql 42
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
context "when the list is not empty" do
|
64
|
+
before { @linked_list.prepend(42) }
|
65
|
+
it "adds the element to the LinkedList" do
|
66
|
+
@linked_list.append(13)
|
67
|
+
expect(@linked_list.head.value).to eql 42
|
68
|
+
element = @linked_list.head
|
69
|
+
element = element.next
|
70
|
+
expect(element.value).to eql 13
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
describe "#item_at_head" do
|
76
|
+
before { @linked_list.prepend(42) }
|
77
|
+
before { @linked_list.prepend(13) }
|
78
|
+
|
79
|
+
it "returns the correct item" do
|
80
|
+
element = @linked_list.item_at_head
|
81
|
+
expect(element.value).to eql 13
|
82
|
+
end
|
83
|
+
end
|
84
|
+
|
85
|
+
describe "#item_at" do
|
86
|
+
before { @linked_list.prepend(42) }
|
87
|
+
before { @linked_list.prepend(7) }
|
88
|
+
before { @linked_list.prepend(13) }
|
89
|
+
|
90
|
+
context "item at index zero" do
|
91
|
+
it "returns correct value" do
|
92
|
+
expect(@linked_list.item_at(0).value).to eql 13
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
context "item at index one" do
|
97
|
+
it "returns correct value" do
|
98
|
+
expect(@linked_list.item_at(1).value).to eql 7
|
99
|
+
end
|
100
|
+
end
|
101
|
+
|
102
|
+
context "item at index two" do
|
103
|
+
it "returns correct value" do
|
104
|
+
expect(@linked_list.item_at(2).value).to eql 42
|
105
|
+
end
|
106
|
+
end
|
107
|
+
|
108
|
+
context "item at index out of range" do
|
109
|
+
it "returns nil" do
|
110
|
+
expect(@linked_list.item_at(3)).to eql nil
|
111
|
+
end
|
112
|
+
|
113
|
+
it "returns nil" do
|
114
|
+
expect(@linked_list.item_at(4)).to eql nil
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|
118
|
+
|
119
|
+
describe "#search" do
|
120
|
+
|
121
|
+
context "when the list is empty" do
|
122
|
+
it "returns nil" do
|
123
|
+
expect(@linked_list.search(42)).to eql nil
|
124
|
+
end
|
125
|
+
end
|
126
|
+
|
127
|
+
context "when the list is not empty" do
|
128
|
+
before(:each) { @linked_list.prepend(42) }
|
129
|
+
before(:each) { @linked_list.prepend(13) }
|
130
|
+
before(:each) { @linked_list.prepend(7) }
|
131
|
+
|
132
|
+
context "when item is at head of the list" do
|
133
|
+
it "returns the correct value" do
|
134
|
+
expect(@linked_list.search(7).value).to eql 7
|
135
|
+
end
|
136
|
+
end
|
137
|
+
|
138
|
+
context "when item is in the middle of the list" do
|
139
|
+
it "returns the correct value" do
|
140
|
+
expect(@linked_list.search(13).value).to eql 13
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
144
|
+
context "when item is at the end of the list" do
|
145
|
+
it "returns the correct value" do
|
146
|
+
expect(@linked_list.search(42).value).to eql 42
|
147
|
+
end
|
148
|
+
end
|
149
|
+
end
|
150
|
+
end
|
151
|
+
|
152
|
+
describe "#remove_at_head" do
|
153
|
+
|
154
|
+
context "list is not empty" do
|
155
|
+
before(:each) { @linked_list.prepend(42) }
|
156
|
+
|
157
|
+
context "only one Node" do
|
158
|
+
it "returns the Node at the head of the list" do
|
159
|
+
expect(@linked_list.remove_at_head.value).to eql 42
|
160
|
+
end
|
161
|
+
|
162
|
+
it "removes the Node from the list" do
|
163
|
+
expect(@linked_list.empty?).to eql false
|
164
|
+
@linked_list.remove_at_head
|
165
|
+
expect(@linked_list.empty?).to eql true
|
166
|
+
end
|
167
|
+
end
|
168
|
+
|
169
|
+
context "more than one Node" do
|
170
|
+
before(:each) { @linked_list.append(13) }
|
171
|
+
|
172
|
+
it "returns the correct Node" do
|
173
|
+
expect(@linked_list.remove_at_head.value).to eql 42
|
174
|
+
end
|
175
|
+
|
176
|
+
it "removes the value from the list" do
|
177
|
+
@linked_list.remove_at_head
|
178
|
+
expect(@linked_list.item_at_head.value).to eql 13
|
179
|
+
end
|
180
|
+
end
|
181
|
+
end
|
182
|
+
|
183
|
+
context "list is empty" do
|
184
|
+
it "returns nil" do
|
185
|
+
expect(@linked_list.remove_at_head).to eql nil
|
186
|
+
end
|
187
|
+
end
|
188
|
+
end
|
189
|
+
|
190
|
+
describe "#remove_at_tail" do
|
191
|
+
|
192
|
+
context "when the list is empty" do
|
193
|
+
it "returns nil" do
|
194
|
+
expect(@linked_list.remove_at_tail).to eql nil
|
195
|
+
end
|
196
|
+
end
|
197
|
+
|
198
|
+
context "when the list is not empty" do
|
199
|
+
before(:each) { @linked_list.prepend(42) }
|
200
|
+
|
201
|
+
context "list has one element" do
|
202
|
+
it "returns the correct value" do
|
203
|
+
expect(@linked_list.remove_at_tail.value).to eql 42
|
204
|
+
end
|
205
|
+
|
206
|
+
it "is empty after removal" do
|
207
|
+
expect(@linked_list.empty?).to eql false
|
208
|
+
@linked_list.remove_at_tail
|
209
|
+
expect(@linked_list.empty?).to eql true
|
210
|
+
end
|
211
|
+
end
|
212
|
+
|
213
|
+
context "list has two or more elements" do
|
214
|
+
before(:each) { @linked_list.prepend(13) }
|
215
|
+
|
216
|
+
it "returns the correct value" do
|
217
|
+
expect(@linked_list.remove_at_tail.value).to eql 42
|
218
|
+
end
|
219
|
+
|
220
|
+
it "Node is removed" do
|
221
|
+
@linked_list.remove_at_tail
|
222
|
+
element = @linked_list.head
|
223
|
+
expect(element.next).to eql nil
|
224
|
+
end
|
225
|
+
end
|
226
|
+
end
|
227
|
+
end
|
228
|
+
|
229
|
+
describe "#remove" do
|
230
|
+
before(:each) { @linked_list.prepend(42) }
|
231
|
+
before(:each) { @linked_list.prepend(7) }
|
232
|
+
before(:each) { @linked_list.prepend(13) }
|
233
|
+
|
234
|
+
context "value at index 0" do
|
235
|
+
it "returns Node" do
|
236
|
+
expect(@linked_list.remove(13).value).to eql 13
|
237
|
+
end
|
238
|
+
end
|
239
|
+
|
240
|
+
context "value at index 1" do
|
241
|
+
it "returns Node" do
|
242
|
+
expect(@linked_list.remove(7).value).to eql 7
|
243
|
+
end
|
244
|
+
end
|
245
|
+
|
246
|
+
context "value at index 2" do
|
247
|
+
it "returns Node" do
|
248
|
+
expect(@linked_list.remove(42).value).to eql 42
|
249
|
+
end
|
250
|
+
end
|
251
|
+
|
252
|
+
context "value not in LinkedList" do
|
253
|
+
it "returns nil" do
|
254
|
+
expect(@linked_list.remove(100)).to eql nil
|
255
|
+
end
|
256
|
+
end
|
257
|
+
end
|
258
|
+
end
|
data/spec/node_spec.rb
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
require 'rubystructures'
|
2
|
+
|
3
|
+
describe RubyStructures::Node do
|
4
|
+
describe "#initialize" do
|
5
|
+
before { @node = RubyStructures::Node.new(1, 42) }
|
6
|
+
|
7
|
+
it "has correct list" do
|
8
|
+
expect(@node.list).to eql 1
|
9
|
+
end
|
10
|
+
|
11
|
+
it "has correct value" do
|
12
|
+
expect(@node.value).to eql 42
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rubystructures
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.3
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2014-
|
12
|
+
date: 2014-06-02 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: bundler
|
@@ -72,10 +72,14 @@ files:
|
|
72
72
|
- README.md
|
73
73
|
- Rakefile
|
74
74
|
- lib/rubystructures.rb
|
75
|
+
- lib/rubystructures/linked_list.rb
|
76
|
+
- lib/rubystructures/node.rb
|
75
77
|
- lib/rubystructures/queue.rb
|
76
78
|
- lib/rubystructures/stack.rb
|
77
79
|
- lib/rubystructures/version.rb
|
78
80
|
- rubystructures.gemspec
|
81
|
+
- spec/linked_list_spec.rb
|
82
|
+
- spec/node_spec.rb
|
79
83
|
- spec/queue_spec.rb
|
80
84
|
- spec/stack_spec.rb
|
81
85
|
homepage: ''
|
@@ -104,5 +108,7 @@ signing_key:
|
|
104
108
|
specification_version: 3
|
105
109
|
summary: Simple, useful data structures in ruby.
|
106
110
|
test_files:
|
111
|
+
- spec/linked_list_spec.rb
|
112
|
+
- spec/node_spec.rb
|
107
113
|
- spec/queue_spec.rb
|
108
114
|
- spec/stack_spec.rb
|