/
d_linked_list.py
297 lines (244 loc) · 9.28 KB
/
d_linked_list.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
from d_linked_node import d_linked_node
class d_linked_list:
def __init__(self):
self.__head=None
self.__tail=None
self.__size=0
def search(self, item):
current = self.__head
found = False
while current != None and not found:
if current.getData() == item:
found= True
else:
current = current.getNext()
return found
def index(self, item):
current = self.__head
found = False
index = 0
while current != None and not found:
if current.getData() == item:
found= True
else:
current = current.getNext()
index = index + 1
if not found:
index = -1
return index
def add(self, item):
# add item to beginning of list (index 0)
temp = d_linked_node(item, self.__head, None)
if self.__head != None: # if list is not empty
self.__head.setPrevious(temp) # add temp to front
else: # if list is empty, head is also the tail
self.__tail = temp
self.__head = temp # new item is head cuz we're adding to front
self.__size += 1
def remove(self, item):
# searches item and removes it
current = self.__head
previous = None
found = False
while not found:
if current.getData() == item:
found = True
else:
previous = current
current = current.getNext()
if found:
if previous == None: # if the index is 0, set a new head
self.__head = current.getNext()
else:
previous.setNext(current.getNext()) # previous points to item after current (so current can be ignored and removed)
if (current.getNext() != None): # if NOT removing the last item
current.getNext().setPrevious(previous) # remove node from current so it can be ignored and deleted
else:
self.__tail = previous # if nothing after current (current is last item) and current gets removed, the previous one will be last item
self.__size -= 1
def append(self, item):
# adds item to the end of list
temp = d_linked_node(item, None, None)
if (self.__head == None):
self.__head = temp
else:
self.__tail.setNext(temp)
temp.setPrevious(self.__tail)
self.__tail = temp
self.__size += 1
def insert(self, pos, item):
assert pos <= self.get_size(), "Error in insert: position exceed limit"
current = self.__head
previous = None
temp = d_linked_node(item, None, None)
if (self.__head == None):
self.__head = temp
self.__tail = temp
else: # find position to add item
i = 0
while i != pos:
previous = current
current = current.getNext()
i += 1
if previous == None:
self.__head = temp
else:
previous.setNext(temp)
temp.setPrevious(previous)
if current == None:
self.__tail = temp
else:
temp.setNext(current)
current.setPrevious(temp)
self.__size += 1
def pop1(self):
# removes and returns the last item in the list
temp = self.__tail
previous = temp.getPrevious()
self.__tail = previous
if previous != None:
previous.setNext(None)
temp.setPrevious(None)
self.__size -= 1
return temp.getData()
def pop(self, pos):
assert pos < self.get_size(), "Error in pop: position exceed limit"
assert self.get_size() != 0, "Error in pop: list is empty"
current = self.__head
previous = None
i = 0
while i != pos: # find position to pop item
previous = current
current = current.getNext()
i += 1
if current == None:
after = None
else:
after = current.getNext()
if previous == None:
self.__head = after
after.setPrevious(None)
else:
if after == None:
self.__tail = previous
previous.setNext(None)
else:
previous.setNext(after)
after.setPrevious(previous)
if current != None:
current.setNext(None)
current.setPrevious(None)
self.__size -= 1
return current.getData()
def search_larger(self, item):
current = self.__head
found = False
pos = 0
while current != None and not found:
if current.getData() > item:
found= True
else:
current = current.getNext()
pos += 1
if not found:
pos = -1
return pos
def get_size(self):
return self.__size
def get_item(self, pos):
if pos>=0:
assert pos<self.get_size(), "IndexError: position does not exist"
current = self.__head
i = 0
while i != pos: # find position
current = current.getNext()
i += 1
else:
pos = pos*-1
assert pos<=self.get_size(), "IndexError: position does not exist"
current = self.__tail
i = 1
while i!= pos:
current = current.getPrevious()
i += 1
return current.getData()
def __str__(self):
s= ""
i=0
current=self.__head
while current != None:
if i>0:
s = s + ' '
dataObject = current.getData()
if dataObject != None:
s = s + "%s" % dataObject
i = i + 1
current = current.getNext()
return s
def test():
linked_list = d_linked_list()
is_pass = (linked_list.get_size() == 0)
assert is_pass == True, "fail the test"
linked_list.add("World")
linked_list.add("Hello")
is_pass = (str(linked_list) == "Hello World")
assert is_pass == True, "fail the test"
is_pass = (linked_list.get_size() == 2)
assert is_pass == True, "fail the test"
is_pass = (linked_list.get_item(0) == "Hello")
assert is_pass == True, "fail the test"
is_pass = (linked_list.get_item(1) == "World")
assert is_pass == True, "fail the test"
is_pass = (linked_list.get_item(0) == "Hello" and linked_list.get_size() == 2)
assert is_pass == True, "fail the test"
is_pass = (linked_list.pop(1) == "World")
assert is_pass == True, "fail the test"
is_pass = (linked_list.pop1() == "Hello")
assert is_pass == True, "fail the test"
is_pass = (linked_list.get_size() == 0)
assert is_pass == True, "fail the test"
int_list2 = d_linked_list()
for i in range(0, 10):
int_list2.add(i)
int_list2.remove(1)
int_list2.remove(3)
int_list2.remove(2)
int_list2.remove(0)
is_pass = (str(int_list2) == "9 8 7 6 5 4")
assert is_pass == True, "fail the test"
for i in range(11, 13):
int_list2.append(i)
is_pass = (str(int_list2) == "9 8 7 6 5 4 11 12")
assert is_pass == True, "fail the test"
for i in range(21, 23):
int_list2.insert(0,i)
is_pass = (str(int_list2) == "22 21 9 8 7 6 5 4 11 12")
assert is_pass == True, "fail the test"
is_pass = (int_list2.get_size() == 10)
assert is_pass == True, "fail the test"
int_list = d_linked_list()
is_pass = (int_list.get_size() == 0)
assert is_pass == True, "fail the test"
for i in range(0, 1000):
int_list.append(i)
correctOrder = True
is_pass = (int_list.get_size() == 1000)
assert is_pass == True, "fail the test"
for i in range(0, 200):
if int_list.pop1() != 999 - i:
correctOrder = False
is_pass = correctOrder
assert is_pass == True, "fail the test"
is_pass = (int_list.search_larger(200) == 201)
assert is_pass == True, "fail the test"
int_list.insert(7,801)
is_pass = (int_list.search_larger(800) == 7)
assert is_pass == True, "fail the test"
is_pass = (int_list.get_item(-1) == 799)
assert is_pass == True, "fail the test"
is_pass = (int_list.get_item(-4) == 796)
assert is_pass == True, "fail the test"
if is_pass == True:
print ("=========== Congratulations! Your have finished exercise 1! ============")
if __name__ == '__main__':
test()