mirror of
https://github.com/autistic-symposium/master-algorithms-py.git
synced 2025-04-29 20:26:07 -04:00
initial and final commit
This commit is contained in:
parent
4061fa6df1
commit
227a0efc0e
@ -1,4 +0,0 @@
|
|||||||
python_and_alg
|
|
||||||
==============
|
|
||||||
|
|
||||||
This repository contains a comprehensive study of Algorithms and Python, including an "ebook" that I wrote. In the folder /src/examples_in_my_book/, I made available all the examples and cases I used in my ebook. In the folder /futher_examples/ you can find all the solutions for the book Cracking the Code, and many examples from the websites Project Euler and Topcoder.
|
|
BIN
review_algorithms_in_python.pdf
Normal file
BIN
review_algorithms_in_python.pdf
Normal file
Binary file not shown.
0
src/examples_in_my_book/adt/heap/__init__.py
Normal file
0
src/examples_in_my_book/adt/heap/__init__.py
Normal file
@ -0,0 +1,51 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import heapq
|
||||||
|
|
||||||
|
def find_N_largest_items_seq(seq, N):
|
||||||
|
''' find the N largest items in a sequence '''
|
||||||
|
return heapq.nlargest(N,seq)
|
||||||
|
|
||||||
|
def find_N_smallest_items_seq(seq, N):
|
||||||
|
''' find the N smallest items in a sequence '''
|
||||||
|
return heapq.nsmallest(N, seq)
|
||||||
|
|
||||||
|
def find_smallest_items_seq_heap(seq):
|
||||||
|
''' find the smallest items in a sequence using heapify first'''
|
||||||
|
''' heap[0] is always the smallest item '''
|
||||||
|
''' pops the smallest item, O(logN) '''
|
||||||
|
heapq.heapify(seq)
|
||||||
|
return heapq.heappop(seq)
|
||||||
|
|
||||||
|
def find_smallest_items_seq(seq):
|
||||||
|
''' if it is only one item, min() is faster '''
|
||||||
|
return min(seq)
|
||||||
|
|
||||||
|
def find_N_smallest_items_seq_sorted(seq, N):
|
||||||
|
''' N ~ len(seq), better sort instead'''
|
||||||
|
return sorted(seq)[:N]
|
||||||
|
|
||||||
|
def find_N_largest_items_seq_sorted(seq, N):
|
||||||
|
''' N ~ len(seq), better sort instead'''
|
||||||
|
return sorted(seq)[len(seq)-N:]
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_N_largest_smallest_items_seq(module_name='this module'):
|
||||||
|
seq = [1, 3, 2, 8, 6, 10, 9]
|
||||||
|
N = 3
|
||||||
|
assert(find_N_largest_items_seq(seq, N) == [10, 9, 8])
|
||||||
|
assert(find_N_largest_items_seq_sorted(seq, N) == [8, 9, 10])
|
||||||
|
assert(find_N_smallest_items_seq(seq, N) == [1,2,3])
|
||||||
|
assert(find_N_smallest_items_seq_sorted(seq, N) == [1,2,3])
|
||||||
|
assert(find_smallest_items_seq(seq) == 1)
|
||||||
|
assert(find_smallest_items_seq_heap(seq) == 1)
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_N_largest_smallest_items_seq()
|
||||||
|
|
49
src/examples_in_my_book/adt/heap/heap.py~
Normal file
49
src/examples_in_my_book/adt/heap/heap.py~
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class Heapify(object):
|
||||||
|
def __init__(self, data=None):
|
||||||
|
self.data = data or []
|
||||||
|
for i in range(len(data)//2, -1, -1):
|
||||||
|
self.__max_heapify__(i)
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
return '{}'.format(self.data)
|
||||||
|
|
||||||
|
def parent(self, i):
|
||||||
|
return i >> 1
|
||||||
|
|
||||||
|
def left_child(self, i):
|
||||||
|
return (i << 1) + 1
|
||||||
|
|
||||||
|
def right_child(self, i):
|
||||||
|
return (i << 1) + 2 # +2 instead of +1 because it's 0-indexed.
|
||||||
|
|
||||||
|
def __max_heapify__(self, i):
|
||||||
|
largest = i
|
||||||
|
left = self.left_child(i)
|
||||||
|
right = self.right_child(i)
|
||||||
|
n = len(self.data)
|
||||||
|
largest = (left < n and self.data[left] > self.data[i]) and left or i
|
||||||
|
largest = (right < n and self.data[right] > self.data[largest]) and right or largest
|
||||||
|
if i is not largest:
|
||||||
|
self.data[i], self.data[largest] = self.data[largest], self.data[i]
|
||||||
|
self.__max_heapify__(largest)
|
||||||
|
|
||||||
|
def extract_max(self):
|
||||||
|
n = len(self.data)
|
||||||
|
max_element = self.data[0]
|
||||||
|
self.data[0] = self.data[n - 1]
|
||||||
|
self.data = self.data[:n - 1]
|
||||||
|
self.__max_heapify__(0)
|
||||||
|
return max_element
|
||||||
|
|
||||||
|
|
||||||
|
def test_Heapify():
|
||||||
|
l1 = [3, 2, 5, 1, 7, 8, 2]
|
||||||
|
h = Heapify(l1)
|
||||||
|
assert(h.extract_max() == 8)
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_Heapify()
|
50
src/examples_in_my_book/adt/heap/heapify.py
Normal file
50
src/examples_in_my_book/adt/heap/heapify.py
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class Heapify(object):
|
||||||
|
def __init__(self, data=None):
|
||||||
|
self.data = data or []
|
||||||
|
for i in range(len(data)//2, -1, -1):
|
||||||
|
self.__max_heapify__(i)
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
return '{}'.format(self.data)
|
||||||
|
|
||||||
|
def parent(self, i):
|
||||||
|
return i >> 1
|
||||||
|
|
||||||
|
def left_child(self, i):
|
||||||
|
return (i << 1) + 1
|
||||||
|
|
||||||
|
def right_child(self, i):
|
||||||
|
return (i << 1) + 2 # +2 instead of +1 because it's 0-indexed.
|
||||||
|
|
||||||
|
def __max_heapify__(self, i):
|
||||||
|
largest = i
|
||||||
|
left = self.left_child(i)
|
||||||
|
right = self.right_child(i)
|
||||||
|
n = len(self.data)
|
||||||
|
largest = (left < n and self.data[left] > self.data[i]) and left or i
|
||||||
|
largest = (right < n and self.data[right] > self.data[largest]) and right or largest
|
||||||
|
if i is not largest:
|
||||||
|
self.data[i], self.data[largest] = self.data[largest], self.data[i]
|
||||||
|
self.__max_heapify__(largest)
|
||||||
|
|
||||||
|
def extract_max(self):
|
||||||
|
n = len(self.data)
|
||||||
|
max_element = self.data[0]
|
||||||
|
self.data[0] = self.data[n - 1]
|
||||||
|
self.data = self.data[:n - 1]
|
||||||
|
self.__max_heapify__(0)
|
||||||
|
return max_element
|
||||||
|
|
||||||
|
|
||||||
|
def test_Heapify():
|
||||||
|
l1 = [3, 2, 5, 1, 7, 8, 2]
|
||||||
|
h = Heapify(l1)
|
||||||
|
assert(h.extract_max() == 8)
|
||||||
|
print ("Tests Passed!")
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_Heapify()
|
29
src/examples_in_my_book/adt/heap/merge_sorted_seqs.py
Normal file
29
src/examples_in_my_book/adt/heap/merge_sorted_seqs.py
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import heapq
|
||||||
|
|
||||||
|
|
||||||
|
def merge_sorted_seq(seq1, seq2):
|
||||||
|
''' merge two sorted sequences with little ovehead. the result
|
||||||
|
will be sorted, which is different of doing just +'''
|
||||||
|
result = []
|
||||||
|
for c in heapq.merge(seq1, seq2):
|
||||||
|
result.append(c)
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
def test_merge_sorted_seq(module_name='this module'):
|
||||||
|
seq1 = [1, 2, 3, 8, 9, 10]
|
||||||
|
seq2 = [2, 3, 4, 5, 6, 7, 9]
|
||||||
|
seq3 = seq1 + seq2
|
||||||
|
assert(merge_sorted_seqseq1, seq2) == sorted(seq3))
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_merge_sorted_seq()
|
||||||
|
|
41
src/examples_in_my_book/adt/heap/priority_queue.py
Normal file
41
src/examples_in_my_book/adt/heap/priority_queue.py
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import heapq
|
||||||
|
|
||||||
|
class PriorityQueue(object):
|
||||||
|
''' implements a priority queue class '''
|
||||||
|
def __init__(self):
|
||||||
|
self._queue = []
|
||||||
|
self._index = 0 # comparying same priority level
|
||||||
|
|
||||||
|
def push(self, item, priority):
|
||||||
|
heapq.heappush(self._queue, (-priority, self._index, item))
|
||||||
|
self._index += 1
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
return heapq.heappop(self._queue)[-1]
|
||||||
|
|
||||||
|
|
||||||
|
class Item:
|
||||||
|
def __init__(self, name):
|
||||||
|
self.name = name
|
||||||
|
def __repr__(self):
|
||||||
|
return "Item({!r})".format(self.name)
|
||||||
|
|
||||||
|
|
||||||
|
def test_PriorityQueue():
|
||||||
|
''' push and pop are all O(logN) '''
|
||||||
|
q = PriorityQueue()
|
||||||
|
q.push(Item('test1'), 1)
|
||||||
|
q.push(Item('test2'), 4)
|
||||||
|
q.push(Item('test3'), 3)
|
||||||
|
assert(str(q.pop()) == "Item('test2')")
|
||||||
|
print('Tests passed!'.center(20,'*'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_PriorityQueue()
|
||||||
|
|
||||||
|
|
41
src/examples_in_my_book/adt/heap/priority_queue.py~
Normal file
41
src/examples_in_my_book/adt/heap/priority_queue.py~
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import heapq
|
||||||
|
|
||||||
|
class PriorityQueue(object):
|
||||||
|
''' implements a priority queue class '''
|
||||||
|
def __init__(self):
|
||||||
|
self._queue = []
|
||||||
|
self._index = 0 # index property order items with same priority level, good for comparisons
|
||||||
|
|
||||||
|
def push(self, item, priority):
|
||||||
|
heapq.heappush(self._queue, (-priority, self._index, item)) # notice the tuple
|
||||||
|
self._index += 1
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
return heapq.heappop(self._queue)[-1]
|
||||||
|
|
||||||
|
|
||||||
|
class Item:
|
||||||
|
def __init__(self, name):
|
||||||
|
self.name = name
|
||||||
|
def __repr__(self):
|
||||||
|
return "Item({!r})".format(self.name)
|
||||||
|
|
||||||
|
|
||||||
|
def test_PriorityQueue():
|
||||||
|
''' push and pop are all O(logN) '''
|
||||||
|
q = PriorityQueue()
|
||||||
|
q.push(Item('test1'), 1)
|
||||||
|
q.push(Item('test2'), 4)
|
||||||
|
q.push(Item('test3'), 3)
|
||||||
|
assert(str(q.pop()) == "Item('test2')")
|
||||||
|
print('Tests passed!'.center(20,'*'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_PriorityQueue()
|
||||||
|
|
||||||
|
|
44
src/examples_in_my_book/adt/linked_lists/Node.py~
Normal file
44
src/examples_in_my_book/adt/linked_lists/Node.py~
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
'''The structure of an unordered list is a collection of items where each item holds a relative position with respect to the others '''
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class Node:
|
||||||
|
''' The basic building block for the linked list implementation is the node.
|
||||||
|
Each node object must hold at least two pieces of information:
|
||||||
|
First, the node must contain the list item itself (data field),
|
||||||
|
second each node must hold a reference to the next node '''
|
||||||
|
|
||||||
|
def __init__(self,initdata):
|
||||||
|
self.data = initdata
|
||||||
|
self.next = None
|
||||||
|
|
||||||
|
def getData(self):
|
||||||
|
return self.data
|
||||||
|
|
||||||
|
def getNext(self):
|
||||||
|
return self.next
|
||||||
|
|
||||||
|
def setData(self,newdata):
|
||||||
|
self.data = newdata
|
||||||
|
|
||||||
|
def setNext(self,newnext):
|
||||||
|
self.next = newnext
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_Node(module_name='this module'):
|
||||||
|
temp = Node(40)
|
||||||
|
assert(temp.getData() == 40)
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_Node()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,71 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class Node(object):
|
||||||
|
def __init__(self,data=None,next=None):
|
||||||
|
self.data = data
|
||||||
|
self.next = next
|
||||||
|
|
||||||
|
def setnext(self,next):
|
||||||
|
self.next = next
|
||||||
|
|
||||||
|
def __str__(self):
|
||||||
|
return "%s" % self.data
|
||||||
|
|
||||||
|
|
||||||
|
class LinkedListStack(object):
|
||||||
|
''' linked list from stack '''
|
||||||
|
def __init__(self, max=0):
|
||||||
|
self.max = max
|
||||||
|
self.head = None
|
||||||
|
self.z = None
|
||||||
|
self.size = 0
|
||||||
|
|
||||||
|
def push(self, data):
|
||||||
|
if self.size == 0:
|
||||||
|
self.head = Node(data=data)
|
||||||
|
self.size += 1
|
||||||
|
else:
|
||||||
|
head = self.head
|
||||||
|
temp = Node(data = data)
|
||||||
|
self.head = temp
|
||||||
|
self.head = temp
|
||||||
|
temp.setnext(head)
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
temp = self.head.next
|
||||||
|
self.head = temp
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return self.size == 0
|
||||||
|
|
||||||
|
def __str__(self):
|
||||||
|
d = ""
|
||||||
|
if self.isEmpty(): return ""
|
||||||
|
else:
|
||||||
|
temp = self.head
|
||||||
|
d += "%s\n" % temp
|
||||||
|
while temp.next != None:
|
||||||
|
temp = temp.next
|
||||||
|
d += "%s\n" % temp
|
||||||
|
return d
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_ll_from_stack():
|
||||||
|
ll = LinkedListStack(max = 20)
|
||||||
|
ll.push("1")
|
||||||
|
ll.push("2")
|
||||||
|
ll.push("3")
|
||||||
|
ll.push("4")
|
||||||
|
print(ll)
|
||||||
|
ll.pop()
|
||||||
|
print(ll)
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_ll_from_stack()
|
65
src/examples_in_my_book/adt/linked_lists/linkedlist.py
Normal file
65
src/examples_in_my_book/adt/linked_lists/linkedlist.py
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from node import Node
|
||||||
|
|
||||||
|
class UnorderedList(object):
|
||||||
|
def __init__(self):
|
||||||
|
self.head = None
|
||||||
|
|
||||||
|
def add(self, item):
|
||||||
|
temp = Node(item)
|
||||||
|
temp.setNext(self.head)
|
||||||
|
self.head = temp
|
||||||
|
|
||||||
|
def length(self):
|
||||||
|
current = self.head
|
||||||
|
count = 0
|
||||||
|
while current != None:
|
||||||
|
count = count + 1
|
||||||
|
current = current.getNext()
|
||||||
|
return count
|
||||||
|
|
||||||
|
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 remove(self, item):
|
||||||
|
current = self.head
|
||||||
|
previous = None
|
||||||
|
found = False
|
||||||
|
while not found:
|
||||||
|
if current.getData() == item:
|
||||||
|
found = True
|
||||||
|
else:
|
||||||
|
previous = current
|
||||||
|
current = current.getNext()
|
||||||
|
if previous == None:
|
||||||
|
self.head = current.getNext()
|
||||||
|
else:
|
||||||
|
previous.setNext(current.getNext())
|
||||||
|
|
||||||
|
|
||||||
|
def test_UnorderedList(module_name='this module'):
|
||||||
|
llist = UnorderedList()
|
||||||
|
llist.add(31)
|
||||||
|
llist.add(22)
|
||||||
|
llist.add(10)
|
||||||
|
assert(llist.search(22) == True)
|
||||||
|
llist.remove(22)
|
||||||
|
assert(llist.search(22) == False)
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_UnorderedList()
|
||||||
|
|
||||||
|
|
65
src/examples_in_my_book/adt/linked_lists/linkedlist.py~
Normal file
65
src/examples_in_my_book/adt/linked_lists/linkedlist.py~
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from node import Node
|
||||||
|
|
||||||
|
class UnorderedList(object):
|
||||||
|
def __init__(self):
|
||||||
|
self.head = None
|
||||||
|
|
||||||
|
def add(self, item):
|
||||||
|
temp = Node(item)
|
||||||
|
temp.setNext(self.head)
|
||||||
|
self.head = temp
|
||||||
|
|
||||||
|
def length(self):
|
||||||
|
current = self.head
|
||||||
|
count = 0
|
||||||
|
while current != None:
|
||||||
|
count = count + 1
|
||||||
|
current = current.getNext()
|
||||||
|
return count
|
||||||
|
|
||||||
|
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 remove(self,item):
|
||||||
|
current = self.head
|
||||||
|
previous = None
|
||||||
|
found = False
|
||||||
|
while not found:
|
||||||
|
if current.getData() == item:
|
||||||
|
found = True
|
||||||
|
else:
|
||||||
|
previous = current
|
||||||
|
current = current.getNext()
|
||||||
|
if previous == None:
|
||||||
|
self.head = current.getNext()
|
||||||
|
else:
|
||||||
|
previous.setNext(current.getNext())
|
||||||
|
|
||||||
|
|
||||||
|
def test_UnorderedList(module_name='this module'):
|
||||||
|
llist = UnorderedList()
|
||||||
|
llist.add(31)
|
||||||
|
llist.add(22)
|
||||||
|
llist.add(10)
|
||||||
|
assert(llist.search(22) == True)
|
||||||
|
llist.remove(22)
|
||||||
|
assert(llist.search(22) == False)
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_UnorderedList()
|
||||||
|
|
||||||
|
|
23
src/examples_in_my_book/adt/linked_lists/node.py
Normal file
23
src/examples_in_my_book/adt/linked_lists/node.py
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
class Node(object):
|
||||||
|
def __init__(self, value):
|
||||||
|
self.value = value
|
||||||
|
self.next = None
|
||||||
|
|
||||||
|
def getData(self):
|
||||||
|
return self.value
|
||||||
|
|
||||||
|
def getNext(self):
|
||||||
|
return self.next
|
||||||
|
|
||||||
|
def setData(self, newdata):
|
||||||
|
self.value = newdata
|
||||||
|
|
||||||
|
def setNext(self, newnext):
|
||||||
|
self.next = newnext
|
||||||
|
|
||||||
|
|
39
src/examples_in_my_book/adt/linked_lists/node.py~
Normal file
39
src/examples_in_my_book/adt/linked_lists/node.py~
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
'''The structure of an unordered list is a collection of items where each item holds a relative position with respect to the others '''
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class Node:
|
||||||
|
def __init__(self,initdata):
|
||||||
|
self.data = initdata
|
||||||
|
self.next = None
|
||||||
|
|
||||||
|
def getData(self):
|
||||||
|
return self.data
|
||||||
|
|
||||||
|
def getNext(self):
|
||||||
|
return self.next
|
||||||
|
|
||||||
|
def setData(self,newdata):
|
||||||
|
self.data = newdata
|
||||||
|
|
||||||
|
def setNext(self,newnext):
|
||||||
|
self.next = newnext
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_Node(module_name='this module'):
|
||||||
|
temp = Node(40)
|
||||||
|
assert(temp.getData() == 40)
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_Node()
|
||||||
|
|
||||||
|
|
97
src/examples_in_my_book/adt/linked_lists/ordered_list.py
Normal file
97
src/examples_in_my_book/adt/linked_lists/ordered_list.py
Normal file
@ -0,0 +1,97 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
from Node import Node
|
||||||
|
|
||||||
|
class OrderedList:
|
||||||
|
""" The structure of an ordered list is a collection of items where each item
|
||||||
|
holds a relative position that is based upon some underlying characteristic of
|
||||||
|
the item. The ordering is typically either ascending or descending and we assume
|
||||||
|
that list items have a meaningful comparison operation that is already defined.
|
||||||
|
Many of the ordered list operations are the same as those of the unordered list.
|
||||||
|
"""
|
||||||
|
def __init__(self):
|
||||||
|
self.head = None
|
||||||
|
|
||||||
|
|
||||||
|
def add(self,item):
|
||||||
|
''' this method is different from linked list '''
|
||||||
|
current = self.head
|
||||||
|
previous = None
|
||||||
|
stop = False
|
||||||
|
while current != None and not stop:
|
||||||
|
if current.getData() > item:
|
||||||
|
stop = True
|
||||||
|
else:
|
||||||
|
previous = current
|
||||||
|
current = current.getNext()
|
||||||
|
temp = Node(item)
|
||||||
|
if previous == None:
|
||||||
|
temp.setNext(self.head)
|
||||||
|
self.head = temp
|
||||||
|
else:
|
||||||
|
temp.setNext(current)
|
||||||
|
previous.setNext(temp)
|
||||||
|
|
||||||
|
|
||||||
|
def length(self):
|
||||||
|
current = self.head
|
||||||
|
count = 0
|
||||||
|
while current != None:
|
||||||
|
count = count + 1
|
||||||
|
current = current.getNext()
|
||||||
|
return count
|
||||||
|
|
||||||
|
|
||||||
|
def search(self,item):
|
||||||
|
''' this method is different from linked list '''
|
||||||
|
current = self.head
|
||||||
|
found = False
|
||||||
|
stop = False
|
||||||
|
while current != None and not found and not stop:
|
||||||
|
if current.getData() == item:
|
||||||
|
found = True
|
||||||
|
else:
|
||||||
|
if current.getData() > item:
|
||||||
|
stop = True
|
||||||
|
else:
|
||||||
|
current = current.getNext()
|
||||||
|
return found
|
||||||
|
|
||||||
|
|
||||||
|
def remove(self,item):
|
||||||
|
current = self.head
|
||||||
|
previous = None
|
||||||
|
found = False
|
||||||
|
while not found:
|
||||||
|
if current.getData() == item:
|
||||||
|
found = True
|
||||||
|
else:
|
||||||
|
previous = current
|
||||||
|
current = current.getNext()
|
||||||
|
if previous == None:
|
||||||
|
self.head = current.getNext()
|
||||||
|
else:
|
||||||
|
previous.setNext(current.getNext())
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_OrderedList(module_name='this module'):
|
||||||
|
olist = OrderedList()
|
||||||
|
olist.add(31)
|
||||||
|
olist.add(22)
|
||||||
|
olist.add(10)
|
||||||
|
assert(olist.search(22) == True)
|
||||||
|
olist.remove(22)
|
||||||
|
assert(olist.search(22) == False)
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_OrderedList()
|
||||||
|
|
||||||
|
|
0
src/examples_in_my_book/adt/queues/__init__.py
Normal file
0
src/examples_in_my_book/adt/queues/__init__.py
Normal file
46
src/examples_in_my_book/adt/queues/deque.py
Normal file
46
src/examples_in_my_book/adt/queues/deque.py
Normal file
@ -0,0 +1,46 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class Deque(object):
|
||||||
|
''' a class for a double ended queue '''
|
||||||
|
def __init__(self):
|
||||||
|
self.items = []
|
||||||
|
|
||||||
|
def is_empty(self):
|
||||||
|
return self.items == []
|
||||||
|
|
||||||
|
def add_front(self, item):
|
||||||
|
self.items.append(item)
|
||||||
|
|
||||||
|
def add_rear(self, item):
|
||||||
|
self.items.insert(0, item)
|
||||||
|
|
||||||
|
def remove_front(self):
|
||||||
|
return self.items.pop()
|
||||||
|
|
||||||
|
def remove_rear(self):
|
||||||
|
return self.items.pop(0)
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
return len(self.items)
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
return '{}'.format(self.items)
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
dq = Deque()
|
||||||
|
dq.add_front(1)
|
||||||
|
dq.add_front(2)
|
||||||
|
dq.add_front(3)
|
||||||
|
dq.add_rear(40)
|
||||||
|
dq.add_rear(50)
|
||||||
|
print(dq.size())
|
||||||
|
print(dq)
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
46
src/examples_in_my_book/adt/queues/deque.py~
Normal file
46
src/examples_in_my_book/adt/queues/deque.py~
Normal file
@ -0,0 +1,46 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class Deque(object):
|
||||||
|
''' a class for a double ended queue '''
|
||||||
|
def __init__(self):
|
||||||
|
self.items = []
|
||||||
|
|
||||||
|
def is_empty(self):
|
||||||
|
return self.items == []
|
||||||
|
|
||||||
|
def add_front(self, item):
|
||||||
|
self.items.append(item)
|
||||||
|
|
||||||
|
def add_rear(self, item):
|
||||||
|
self.items.insert(0, item)
|
||||||
|
|
||||||
|
def remove_front(self):
|
||||||
|
return self.items.pop()
|
||||||
|
|
||||||
|
def remove_rear(self):
|
||||||
|
return self.items.pop(0)
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
return len(self.items)
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
return '{}'.format(self.items)
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
dq = Deque()
|
||||||
|
dq.add_front(1)
|
||||||
|
dq.add_front(2)
|
||||||
|
dq.add_front(3)
|
||||||
|
dq.add_rear(40)
|
||||||
|
dq.add_rear(50)
|
||||||
|
assert(dq.size() == 5)
|
||||||
|
assert(dq == [50, 40, 1, 2, 3])
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
61
src/examples_in_my_book/adt/queues/linked_queue.py
Normal file
61
src/examples_in_my_book/adt/queues/linked_queue.py
Normal file
@ -0,0 +1,61 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class Node(object):
|
||||||
|
def __init__(self, value):
|
||||||
|
self.value = value
|
||||||
|
self.next = None
|
||||||
|
|
||||||
|
|
||||||
|
class LinkedQueue(object):
|
||||||
|
''' Queue acts as a container for nodes (objects) that are inserted and removed according FIFO'''
|
||||||
|
def __init__(self):
|
||||||
|
self.front = None
|
||||||
|
self.back = None
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return bool(self.front)
|
||||||
|
|
||||||
|
def dequeue(self):
|
||||||
|
if self.front:
|
||||||
|
value = self.front.value
|
||||||
|
self.front = self.front.next
|
||||||
|
return value
|
||||||
|
raise Exception('Queue is empty, cannot dequeue.')
|
||||||
|
|
||||||
|
def enqueue(self, value):
|
||||||
|
node = Node(value)
|
||||||
|
if self.front:
|
||||||
|
self.back.next = node
|
||||||
|
self.back = node
|
||||||
|
else:
|
||||||
|
self.front = node
|
||||||
|
self.back = node
|
||||||
|
return True
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
node = self.front
|
||||||
|
num_nodes = 1
|
||||||
|
while node.next:
|
||||||
|
num_nodes += 1
|
||||||
|
node = node.next
|
||||||
|
return num_nodes
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
return self.front.value
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
queue = LinkedQueue()
|
||||||
|
queue.enqueue(1)
|
||||||
|
queue.enqueue(2)
|
||||||
|
queue.enqueue(3)
|
||||||
|
print(queue.size())
|
||||||
|
print(queue.peek())
|
||||||
|
print(queue.dequeue())
|
||||||
|
print(queue.peek())
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
61
src/examples_in_my_book/adt/queues/linked_queue.py~
Normal file
61
src/examples_in_my_book/adt/queues/linked_queue.py~
Normal file
@ -0,0 +1,61 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class Node(object):
|
||||||
|
def __init__(self, value):
|
||||||
|
self.value = value
|
||||||
|
self.next = None
|
||||||
|
|
||||||
|
|
||||||
|
class LinkedQueue(object):
|
||||||
|
''' Queue acts as a container for nodes (objects) that are inserted and removed according FIFO'''
|
||||||
|
def __init__(self):
|
||||||
|
self.front = None
|
||||||
|
self.back = None
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return bool(self.front)
|
||||||
|
|
||||||
|
def dequeue(self):
|
||||||
|
if self.front:
|
||||||
|
value = self.front.value
|
||||||
|
self.front = self.front.next
|
||||||
|
return value
|
||||||
|
raise Exception('Queue is empty, cannot dequeue.')
|
||||||
|
|
||||||
|
def enqueue(self, value):
|
||||||
|
node = Node(value)
|
||||||
|
if self.front:
|
||||||
|
self.back.next = node
|
||||||
|
self.back = node
|
||||||
|
else:
|
||||||
|
self.front = node
|
||||||
|
self.back = node
|
||||||
|
return True
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
node = self.front
|
||||||
|
num_nodes = 1
|
||||||
|
while node.next:
|
||||||
|
num_nodes += 1
|
||||||
|
node = node.next
|
||||||
|
return num_nodes
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
return self.front.value[-1]
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
queue = LinkedQueue()
|
||||||
|
queue.enqueue(1)
|
||||||
|
queue.enqueue(2)
|
||||||
|
queue.enqueue(3)
|
||||||
|
print(queue.size())
|
||||||
|
print(queue.peek())
|
||||||
|
print(queue.dequeue())
|
||||||
|
print(queue.peek())
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
@ -0,0 +1,34 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import sys
|
||||||
|
import string
|
||||||
|
import collections
|
||||||
|
|
||||||
|
def palindrome_checker_with_deque(str1):
|
||||||
|
d = collections.deque()
|
||||||
|
eq = True
|
||||||
|
strip = string.whitespace + string.punctuation + "\"'"
|
||||||
|
for s in str1.lower():
|
||||||
|
if s not in strip: d.append(s)
|
||||||
|
while len(d) > 1 and eq:
|
||||||
|
first = d.pop()
|
||||||
|
last = d.popleft()
|
||||||
|
if first != last:
|
||||||
|
eq = False
|
||||||
|
return eq
|
||||||
|
|
||||||
|
|
||||||
|
def test_palindrome_checker_with_deque():
|
||||||
|
str1 = 'Madam Im Adam'
|
||||||
|
str2 = 'Buffy is a Slayer'
|
||||||
|
assert(palindrome_checker_with_deque(str1) == True)
|
||||||
|
assert(palindrome_checker_with_deque(str2) == False)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_palindrome_checker_with_deque()
|
||||||
|
|
||||||
|
|
39
src/examples_in_my_book/adt/queues/queue.py
Normal file
39
src/examples_in_my_book/adt/queues/queue.py
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
class Queue(object):
|
||||||
|
''' a class for a queue '''
|
||||||
|
def __init__(self):
|
||||||
|
self.items = []
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return self.items == []
|
||||||
|
|
||||||
|
def enqueue(self, item):
|
||||||
|
self.items.insert(0, item)
|
||||||
|
|
||||||
|
def dequeue(self):
|
||||||
|
return self.items.pop()
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
return len(self.items)
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
return self.items[-1]
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
queue = Queue()
|
||||||
|
queue.enqueue(1)
|
||||||
|
queue.enqueue(2)
|
||||||
|
queue.enqueue(3)
|
||||||
|
print(queue.size())
|
||||||
|
print(queue.peek())
|
||||||
|
print(queue.dequeue())
|
||||||
|
print(queue.peek())
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
39
src/examples_in_my_book/adt/queues/queue.py~
Normal file
39
src/examples_in_my_book/adt/queues/queue.py~
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
class Queue(object):
|
||||||
|
''' a class for a queue '''
|
||||||
|
def __init__(self):
|
||||||
|
self.items = []
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return self.items == []
|
||||||
|
|
||||||
|
def enqueue(self, item):
|
||||||
|
self.items.insert(0, item)
|
||||||
|
|
||||||
|
def dequeue(self):
|
||||||
|
return self.items.pop()
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
return len(self.items)
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
return self.items[-1]
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
queue = Queue()
|
||||||
|
queue.enqueue(1)
|
||||||
|
queue.enqueue(2)
|
||||||
|
queue.enqueue(3)
|
||||||
|
print(queue.size())
|
||||||
|
print(queue.peek())
|
||||||
|
print(queue.dequeue())
|
||||||
|
print(queue.peek())
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
48
src/examples_in_my_book/adt/queues/queue_from_two_stacks.py
Normal file
48
src/examples_in_my_book/adt/queues/queue_from_two_stacks.py
Normal file
@ -0,0 +1,48 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
class Queue(object):
|
||||||
|
''' an example of a queue implemented from 2 stacks '''
|
||||||
|
def __init__(self):
|
||||||
|
self.in_stack = []
|
||||||
|
self.out_stack = []
|
||||||
|
|
||||||
|
def enqueue(self, item):
|
||||||
|
return self.in_stack.append(item)
|
||||||
|
|
||||||
|
def dequeue(self):
|
||||||
|
if self.out_stack:
|
||||||
|
return self.out_stack.pop()
|
||||||
|
while self.in_stack:
|
||||||
|
self.out_stack.append(self.in_stack.pop())
|
||||||
|
if not self.out_stack:
|
||||||
|
return "Queue empty!"
|
||||||
|
return self.out_stack.pop()
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
return len(self.in_stack) + len(self.out_stack)
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
if self.out_stack:
|
||||||
|
return self.out_stack[-1]
|
||||||
|
while self.in_stack:
|
||||||
|
self.out_stack.append(self.in_stack.pop())
|
||||||
|
return self.out_stack[-1]
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
queue = Queue()
|
||||||
|
queue.enqueue(1)
|
||||||
|
queue.enqueue(2)
|
||||||
|
queue.enqueue(3)
|
||||||
|
print(queue.size())
|
||||||
|
print(queue.peek())
|
||||||
|
print(queue.dequeue())
|
||||||
|
print(queue.peek())
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
48
src/examples_in_my_book/adt/queues/queue_from_two_stacks.py~
Normal file
48
src/examples_in_my_book/adt/queues/queue_from_two_stacks.py~
Normal file
@ -0,0 +1,48 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
class Queue(object):
|
||||||
|
''' an example of a queue implemented from 2 stacks '''
|
||||||
|
def __init__(self):
|
||||||
|
self.in_stack = []
|
||||||
|
self.out_stack = []
|
||||||
|
|
||||||
|
def enqueue(self, item):
|
||||||
|
return self.in_stack.append(item)
|
||||||
|
|
||||||
|
def dequeue(self):
|
||||||
|
if self.out_stack:
|
||||||
|
return self.out_stack.pop()
|
||||||
|
while self.in_stack:
|
||||||
|
self.out_stack.append(self.in_stack.pop())
|
||||||
|
if not self.out_stack:
|
||||||
|
return "Queue empty!"
|
||||||
|
return self.out_stack.pop()
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
return len(self.in_stack) + len(self.out_stack)
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
if self.out_stack:
|
||||||
|
return self.out_stack[-1]
|
||||||
|
while self.in_stack:
|
||||||
|
self.out_stack.append(self.in_stack.pop())
|
||||||
|
return self.out_stack[-1]
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
queue = Queue()
|
||||||
|
queue.add(1)
|
||||||
|
queue.add(2)
|
||||||
|
queue.add(3)
|
||||||
|
print(queue.size())
|
||||||
|
print(queue.peek())
|
||||||
|
print(queue.remove())
|
||||||
|
print(queue.peek())
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
47
src/examples_in_my_book/adt/queues/queue_with_nodes.py~
Normal file
47
src/examples_in_my_book/adt/queues/queue_with_nodes.py~
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class Node:
|
||||||
|
def __init__(self, value):
|
||||||
|
self.value = value
|
||||||
|
self.next = None
|
||||||
|
|
||||||
|
|
||||||
|
class Queue:
|
||||||
|
''' Queue acts as a container for nodes (objects) that are inserted and removed according FIFO'''
|
||||||
|
def __init__(self):
|
||||||
|
self.first = None
|
||||||
|
self.last = None
|
||||||
|
|
||||||
|
def dequeue(self):
|
||||||
|
if self.front:
|
||||||
|
value = self.first.value
|
||||||
|
self.first = self.first.next
|
||||||
|
return value
|
||||||
|
raise Exception('Queue is empty, cannot dequeue.')
|
||||||
|
|
||||||
|
def enqueue(self, value):
|
||||||
|
node = Node(value)
|
||||||
|
if self.first:
|
||||||
|
self.last.next = node
|
||||||
|
self.last = node
|
||||||
|
else:
|
||||||
|
self.first = node
|
||||||
|
self.last = node
|
||||||
|
return True
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return bool(self.first)
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
node = self.first
|
||||||
|
num_nodes = 0
|
||||||
|
while node.next:
|
||||||
|
num_nodes += 1
|
||||||
|
node = node.next
|
||||||
|
return num_nodes
|
||||||
|
|
||||||
|
|
27
src/examples_in_my_book/adt/queues/rotating_array.py
Normal file
27
src/examples_in_my_book/adt/queues/rotating_array.py
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def rotating_array(seq, N):
|
||||||
|
''' rotate an array from right to left for a given number'''
|
||||||
|
myqueue = []
|
||||||
|
for i in range(N):
|
||||||
|
myqueue.append(seq.pop())
|
||||||
|
myqueue.reverse()
|
||||||
|
return myqueue + seq
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_rotating_array(module_name='this module'):
|
||||||
|
seq = [1, 2, 3, 4, 5, 6, 7]
|
||||||
|
N = 4
|
||||||
|
assert(rotating_array(seq, N) == [4, 5, 6, 7, 1, 2, 3])
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_rotating_array()
|
||||||
|
|
0
src/examples_in_my_book/adt/stacks/__init__.py
Normal file
0
src/examples_in_my_book/adt/stacks/__init__.py
Normal file
@ -0,0 +1,40 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from stack import Stack
|
||||||
|
|
||||||
|
def balance_par_str_with_stack(symbolString):
|
||||||
|
''' use a stack to balance the parenteses of a string '''
|
||||||
|
s = Stack()
|
||||||
|
balanced = True
|
||||||
|
index = 0
|
||||||
|
while index < len(symbolString) and balanced:
|
||||||
|
symbol = symbolString[index]
|
||||||
|
if symbol == "(":
|
||||||
|
s.push(symbol)
|
||||||
|
else:
|
||||||
|
if s.isEmpty():
|
||||||
|
balanced = False
|
||||||
|
else:
|
||||||
|
s.pop()
|
||||||
|
index = index + 1
|
||||||
|
|
||||||
|
if balanced and s.isEmpty():
|
||||||
|
return True
|
||||||
|
else:
|
||||||
|
return False
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_balance_par_str_with_stack(module_name='this module'):
|
||||||
|
print(balance_par_str_with_stack('((()))'))
|
||||||
|
print(balance_par_str_with_stack('(()'))
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_balance_par_str_with_stack()
|
28
src/examples_in_my_book/adt/stacks/dec2bin_with_stack.py
Normal file
28
src/examples_in_my_book/adt/stacks/dec2bin_with_stack.py
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from stack import Stack
|
||||||
|
|
||||||
|
def dec2bin_with_stack(decnum):
|
||||||
|
'''transform a decimal number to a binary number with a stack '''
|
||||||
|
s = Stack()
|
||||||
|
str_aux = ''
|
||||||
|
while decnum > 0:
|
||||||
|
dig = decnum % 2
|
||||||
|
decnum = decnum//2
|
||||||
|
s.push(dig)
|
||||||
|
while not s.isEmpty():
|
||||||
|
str_aux += str(s.pop())
|
||||||
|
return str_aux
|
||||||
|
|
||||||
|
|
||||||
|
def test_dec2bin_with_stack(module_name='this module'):
|
||||||
|
decnum = 9
|
||||||
|
assert(dec2bin_with_stack(decnum) == '1001')
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_dec2bin_with_stack()
|
52
src/examples_in_my_book/adt/stacks/linked_stack.py
Normal file
52
src/examples_in_my_book/adt/stacks/linked_stack.py
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class Node:
|
||||||
|
def __init__(self, value=None):
|
||||||
|
self.value = value
|
||||||
|
self.next = None
|
||||||
|
|
||||||
|
class StackwithNodes:
|
||||||
|
''' Define a Stack with nodes'''
|
||||||
|
def __init__(self):
|
||||||
|
self.top = None
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return bool(self.top)
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
node = self.top
|
||||||
|
self.top = node.next
|
||||||
|
return node.value
|
||||||
|
|
||||||
|
def push(self, value):
|
||||||
|
node = Node(value)
|
||||||
|
node.next = self.top
|
||||||
|
self.top = node
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
node = self.top
|
||||||
|
if node not None: num_nodes = 1
|
||||||
|
else: return 0
|
||||||
|
while node.next:
|
||||||
|
num_nodes += 1
|
||||||
|
node = node.next
|
||||||
|
return num_nodes
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
return self.top.value
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
stack = StackwithNodes()
|
||||||
|
stack.push(1)
|
||||||
|
stack.push(2)
|
||||||
|
stack.push(3)
|
||||||
|
print(stack.size())
|
||||||
|
print(stack.peek())
|
||||||
|
print(stack.pop())
|
||||||
|
print(stack.peek())
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
51
src/examples_in_my_book/adt/stacks/linked_stack.py~
Normal file
51
src/examples_in_my_book/adt/stacks/linked_stack.py~
Normal file
@ -0,0 +1,51 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class Node:
|
||||||
|
def __init__(self, value=None):
|
||||||
|
self.value = value
|
||||||
|
self.next = None
|
||||||
|
|
||||||
|
class StackwithNodes:
|
||||||
|
''' Define a Stack with nodes'''
|
||||||
|
def __init__(self):
|
||||||
|
self.top = None
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return bool(self.top)
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
node = self.top
|
||||||
|
self.top = node.next
|
||||||
|
return node.value
|
||||||
|
|
||||||
|
def push(self, value):
|
||||||
|
node = Node(value)
|
||||||
|
node.next = self.top
|
||||||
|
self.top = node
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
node = self.top
|
||||||
|
num_nodes = 1
|
||||||
|
while node.next:
|
||||||
|
num_nodes += 1
|
||||||
|
node = node.next
|
||||||
|
return num_nodes
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
return self.top.value
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
stack = StackwithNodes()
|
||||||
|
stack.push(1)
|
||||||
|
stack.push(2)
|
||||||
|
stack.push(3)
|
||||||
|
print(stack.size())
|
||||||
|
print(stack.peek())
|
||||||
|
print(stack.pop())
|
||||||
|
print(stack.peek())
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
@ -0,0 +1,30 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import sys
|
||||||
|
import stack
|
||||||
|
|
||||||
|
def reverse_string_with_stack(str1):
|
||||||
|
''' Uses a stack to reverse a string '''
|
||||||
|
s = stack.Stack()
|
||||||
|
revStr = ''
|
||||||
|
for c in str1:
|
||||||
|
s.push(c)
|
||||||
|
while not s.isEmpty():
|
||||||
|
revStr += s.pop()
|
||||||
|
return revStr
|
||||||
|
|
||||||
|
|
||||||
|
def test_reverse_string_with_stack():
|
||||||
|
str1 = 'Buffy is a Slayer!'
|
||||||
|
assert(reverse_string_with_stack(str1) == '!reyalS a si yffuB')
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_reverse_string_with_stack()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,30 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import sys
|
||||||
|
import stack
|
||||||
|
|
||||||
|
def reverse_string_with_stack(str1):
|
||||||
|
''' Uses a stack to reverse a string '''
|
||||||
|
s = stack.Stack()
|
||||||
|
revStr = ''
|
||||||
|
for c in str1:
|
||||||
|
s.push(c)
|
||||||
|
while not s.isEmpty():
|
||||||
|
revStr += s.pop()
|
||||||
|
return revStr
|
||||||
|
|
||||||
|
|
||||||
|
def test_reverse_string_with_stack():
|
||||||
|
str1 = 'Buffy is a Slayer!'
|
||||||
|
assert(reverse_string_with_stack(str1) == '!reyalS a si yffuB')
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_reverse_string_with_stack()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
47
src/examples_in_my_book/adt/stacks/set_of_stacks.py
Normal file
47
src/examples_in_my_book/adt/stacks/set_of_stacks.py
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class SetOfStacks(list):
|
||||||
|
def __init__(self, capacity=4):
|
||||||
|
self.stacks = []
|
||||||
|
self.last_stack = []
|
||||||
|
self.capacity = capacity
|
||||||
|
self.stacks.append(self.last_stack)
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
return str(self.stacks)
|
||||||
|
|
||||||
|
def push(self, value):
|
||||||
|
last_stack = self.last_stack
|
||||||
|
if len(last_stack) is self.capacity:
|
||||||
|
last_stack = []
|
||||||
|
self.last_stack = last_stack
|
||||||
|
self.stacks.append(last_stack)
|
||||||
|
last_stack.append(value)
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
last_stack = self.last_stack
|
||||||
|
value = last_stack.pop()
|
||||||
|
if len(last_stack) is 0:
|
||||||
|
self.stacks.pop()
|
||||||
|
self.last_stack = self.stacks[-1]
|
||||||
|
return value
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
stack = SetOfStacks()
|
||||||
|
stack.push(1)
|
||||||
|
stack.push(2)
|
||||||
|
stack.push(3)
|
||||||
|
stack.push(4)
|
||||||
|
stack.push(5)
|
||||||
|
stack.push(6)
|
||||||
|
print(stack)
|
||||||
|
stack.pop()
|
||||||
|
stack.pop()
|
||||||
|
stack.pop()
|
||||||
|
print(stack)
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
48
src/examples_in_my_book/adt/stacks/set_of_stacks.py~
Normal file
48
src/examples_in_my_book/adt/stacks/set_of_stacks.py~
Normal file
@ -0,0 +1,48 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class SetOfStacks(list):
|
||||||
|
|
||||||
|
def __init__(self, capacity=4):
|
||||||
|
self.stacks = []
|
||||||
|
self.last_stack = []
|
||||||
|
self.capacity = capacity
|
||||||
|
self.stacks.append(self.last_stack)
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
return str(self.stacks)
|
||||||
|
|
||||||
|
def push(self, value):
|
||||||
|
last_stack = self.last_stack
|
||||||
|
if len(last_stack) is self.capacity:
|
||||||
|
last_stack = []
|
||||||
|
self.last_stack = last_stack
|
||||||
|
self.stacks.append(last_stack)
|
||||||
|
last_stack.append(value)
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
last_stack = self.last_stack
|
||||||
|
value = last_stack.pop()
|
||||||
|
if len(last_stack) is 0:
|
||||||
|
self.stacks.pop()
|
||||||
|
self.last_stack = self.stacks[-1]
|
||||||
|
return value
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
stack = SetOfStacks()
|
||||||
|
stack.push(1)
|
||||||
|
stack.push(2)
|
||||||
|
stack.push(3)
|
||||||
|
stack.push(4)
|
||||||
|
stack.push(5)
|
||||||
|
stack.push(6)
|
||||||
|
print(stack)
|
||||||
|
stack.pop()
|
||||||
|
stack.pop()
|
||||||
|
stack.pop()
|
||||||
|
print(stack)
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
40
src/examples_in_my_book/adt/stacks/stack.py
Normal file
40
src/examples_in_my_book/adt/stacks/stack.py
Normal file
@ -0,0 +1,40 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class Stack(object):
|
||||||
|
''' define the stack class '''
|
||||||
|
def __init__(self):
|
||||||
|
self.items = []
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return self.items == []
|
||||||
|
|
||||||
|
def push(self, items):
|
||||||
|
self.items.append(items)
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
return self.items.pop()
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
return self.items[-1]
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
return len(self.items)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
stack = Stack()
|
||||||
|
stack.push(1)
|
||||||
|
stack.push(2)
|
||||||
|
stack.push(3)
|
||||||
|
print(stack.size())
|
||||||
|
print(stack.peek())
|
||||||
|
print(stack.pop())
|
||||||
|
print(stack.peek())
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
24
src/examples_in_my_book/adt/stacks/stack.py~
Normal file
24
src/examples_in_my_book/adt/stacks/stack.py~
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class Stack(object):
|
||||||
|
''' define the stack class '''
|
||||||
|
def __init__(self):
|
||||||
|
self.items = []
|
||||||
|
|
||||||
|
def isEmpty(self):
|
||||||
|
return self.items == []
|
||||||
|
|
||||||
|
def push(self, items):
|
||||||
|
self.items.append(items)
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
return self.items.pop()
|
||||||
|
|
||||||
|
def peek(self):
|
||||||
|
return self.items[-1]
|
||||||
|
|
||||||
|
def size(self):
|
||||||
|
return len(self.items)
|
||||||
|
|
55
src/examples_in_my_book/adt/stacks/stack_with_min.py
Normal file
55
src/examples_in_my_book/adt/stacks/stack_with_min.py
Normal file
@ -0,0 +1,55 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
class Stack(list):
|
||||||
|
def push(self, value):
|
||||||
|
if len(self) > 0:
|
||||||
|
last = self[-1]
|
||||||
|
minimum = self._find_minimum(value, last)
|
||||||
|
else:
|
||||||
|
minimum = value
|
||||||
|
self.minimum = minimum
|
||||||
|
self.append(NodeWithMin(value, minimum))
|
||||||
|
|
||||||
|
def _find_minimum(self, value, last_value):
|
||||||
|
if value < last_value.minimum:
|
||||||
|
return value
|
||||||
|
return last_value.minimum
|
||||||
|
|
||||||
|
def min(self):
|
||||||
|
return self.minimum
|
||||||
|
|
||||||
|
|
||||||
|
class NodeWithMin(object):
|
||||||
|
def __init__(self, value, minimum):
|
||||||
|
self.value = value
|
||||||
|
self.minimum = minimum
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
return str(self.value)
|
||||||
|
|
||||||
|
def min(self):
|
||||||
|
return self.minimum
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def main():
|
||||||
|
stack = Stack()
|
||||||
|
stack.push(1)
|
||||||
|
stack.push(2)
|
||||||
|
stack.push(3)
|
||||||
|
node = stack.pop()
|
||||||
|
print(node.minimum)
|
||||||
|
stack.push(0)
|
||||||
|
stack.push(4)
|
||||||
|
node = stack.pop()
|
||||||
|
print(node.min())
|
||||||
|
print(stack.min())
|
||||||
|
print(stack)
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
main()
|
||||||
|
|
||||||
|
|
54
src/examples_in_my_book/adt/stacks/stack_with_min.py~
Normal file
54
src/examples_in_my_book/adt/stacks/stack_with_min.py~
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from linked_stack import StackwithNodes
|
||||||
|
from node import Node
|
||||||
|
|
||||||
|
|
||||||
|
class StackWithMins(Stack):
|
||||||
|
mins = StackwithNodes()
|
||||||
|
|
||||||
|
def push(self, item):
|
||||||
|
node = Node(item)
|
||||||
|
node.next = self.top
|
||||||
|
self.top = node
|
||||||
|
if self.mins.top is not None:
|
||||||
|
if self.mins.top.data > item:
|
||||||
|
self.mins.push(item)
|
||||||
|
else:
|
||||||
|
self.mins.push(item)
|
||||||
|
|
||||||
|
def pop(self):
|
||||||
|
if self.top is not None:
|
||||||
|
if self.peek() == self.mins.peek():
|
||||||
|
self.mins.pop()
|
||||||
|
node = self.top
|
||||||
|
self.top = self.top.next
|
||||||
|
return node
|
||||||
|
return None
|
||||||
|
|
||||||
|
def min(self):
|
||||||
|
return self.mins.peek()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_():
|
||||||
|
stack = StackWithMins()
|
||||||
|
stack.push(9)
|
||||||
|
stack.push(5)
|
||||||
|
stack.push(7)
|
||||||
|
stack.push(4)
|
||||||
|
stack.push(3)
|
||||||
|
stack.push(6)
|
||||||
|
stack.push(5)
|
||||||
|
stack.push(2)
|
||||||
|
stack.push(1)
|
||||||
|
stack.print_stack()
|
||||||
|
stack.mins.print_stack()
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_()
|
||||||
|
|
||||||
|
|
16
src/examples_in_my_book/dynamic_programming/do_benchmark.py~
Normal file
16
src/examples_in_my_book/dynamic_programming/do_benchmark.py~
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import random
|
||||||
|
|
||||||
|
def benchmark(func):
|
||||||
|
import time
|
||||||
|
def wrapper(*args, **kwargs):
|
||||||
|
t = time.clock()
|
||||||
|
res = func(*args, **kwargs)
|
||||||
|
print("\t%s" % func.__name__, time.clock()-t)
|
||||||
|
return res
|
||||||
|
return wrapper
|
||||||
|
|
||||||
|
|
42
src/examples_in_my_book/dynamic_programming/memo.py
Normal file
42
src/examples_in_my_book/dynamic_programming/memo.py
Normal file
@ -0,0 +1,42 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
from functools import wraps
|
||||||
|
from do_benchmark import benchmark
|
||||||
|
|
||||||
|
def memo(func):
|
||||||
|
''' an example of dynamic programming using a memoizing decorator '''
|
||||||
|
cache = {}
|
||||||
|
@wraps(func)
|
||||||
|
def wrap(*args):
|
||||||
|
if args not in cache:
|
||||||
|
cache[args] = func(*args)
|
||||||
|
return cache[args]
|
||||||
|
return wrap
|
||||||
|
|
||||||
|
@memo
|
||||||
|
def find_fibonacci_seq_rec(n):
|
||||||
|
''' implements the nth fibonacci value in a recursive exponential runtime '''
|
||||||
|
if n < 2: return n
|
||||||
|
return find_fibonacci_seq_rec(n - 1) + find_fibonacci_seq_rec(n - 2)
|
||||||
|
|
||||||
|
def test_memo():
|
||||||
|
n = 50
|
||||||
|
# find_fibonacci_seq_rec = memo(find_fibonacci_seq_rec)
|
||||||
|
# @benchmark
|
||||||
|
print(find_fibonacci_seq_rec(n))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_memo()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,86 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
from itertools import combinations
|
||||||
|
from bisect import bisect
|
||||||
|
from memo import memo
|
||||||
|
from do_benchmark import benchmark
|
||||||
|
|
||||||
|
def naive_longest_inc_subseq(seq):
|
||||||
|
''' naive (exponential) solution to the longest increasing subsequence problem '''
|
||||||
|
for length in range(len(seq), 0, -1):
|
||||||
|
for sub in combinations(seq, length):
|
||||||
|
if list(sub) == sorted(sub):
|
||||||
|
return len(sub)
|
||||||
|
|
||||||
|
|
||||||
|
def longest_inc_subseq1(seq):
|
||||||
|
''' an iterative algorithm for the longest increasing subsequence problem '''
|
||||||
|
end = []
|
||||||
|
for val in seq:
|
||||||
|
idx = bisect(end, val)
|
||||||
|
if idx == len(end): end.append(val)
|
||||||
|
else: end[idx] = val
|
||||||
|
return len(end)
|
||||||
|
|
||||||
|
|
||||||
|
def longest_inc_subseq2(seq):
|
||||||
|
''' another iterative algorithm for the longest increasing subsequence problem '''
|
||||||
|
L = [1] * len(seq)
|
||||||
|
for cur, val in enumerate(seq):
|
||||||
|
for pre in range(cur):
|
||||||
|
if seq[pre] <= val:
|
||||||
|
L[cur] = max(L[cur], 1 + L[pre])
|
||||||
|
return max(L)
|
||||||
|
|
||||||
|
|
||||||
|
def memoized_longest_inc_subseq(seq):
|
||||||
|
''' a memoized recursive solution to find the longest increasing subsequence problem '''
|
||||||
|
@memo
|
||||||
|
def L(cur):
|
||||||
|
res = 1
|
||||||
|
for pre in range(cur):
|
||||||
|
if seq[pre] <= seq[cur]:
|
||||||
|
res = max(res, 1 + L(pre))
|
||||||
|
return res
|
||||||
|
return max(L(i) for i in range(len(seq)))
|
||||||
|
|
||||||
|
|
||||||
|
@benchmark
|
||||||
|
def test_naive_longest_inc_subseq():
|
||||||
|
print(naive_longest_inc_subseq(s1))
|
||||||
|
|
||||||
|
benchmark
|
||||||
|
def test_longest_inc_subseq1():
|
||||||
|
print(longest_inc_subseq1(s1))
|
||||||
|
|
||||||
|
@benchmark
|
||||||
|
def test_longest_inc_subseq2():
|
||||||
|
print(longest_inc_subseq2(s1))
|
||||||
|
|
||||||
|
@benchmark
|
||||||
|
def test_memoized_longest_inc_subseq():
|
||||||
|
print(memoized_longest_inc_subseq(s1))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
from random import randrange
|
||||||
|
s1 = [randrange(100) for i in range(25)]
|
||||||
|
print(s1)
|
||||||
|
test_naive_longest_inc_subseq()
|
||||||
|
test_longest_inc_subseq1()
|
||||||
|
test_longest_inc_subseq2()
|
||||||
|
test_memoized_longest_inc_subseq()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,33 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from collections import Counter
|
||||||
|
|
||||||
|
def Counter_example():
|
||||||
|
''' show some examples for Counter '''
|
||||||
|
''' it is a dictionary that maps the items to the number of occurences '''
|
||||||
|
seq1 = [1, 2, 3, 5, 1, 2, 5, 5, 2, 5, 1, 4]
|
||||||
|
seq_counts = Counter(seq1)
|
||||||
|
print(seq_counts)
|
||||||
|
|
||||||
|
''' we can increment manually or use the update() method '''
|
||||||
|
seq2 = [1, 2, 3]
|
||||||
|
seq_counts.update(seq2)
|
||||||
|
print(seq_counts)
|
||||||
|
|
||||||
|
seq3 = [1, 4, 3]
|
||||||
|
for key in seq3:
|
||||||
|
seq_counts[key] += 1
|
||||||
|
print(seq_counts)
|
||||||
|
|
||||||
|
''' also, we can use set operations such as a-b or a+b '''
|
||||||
|
seq_counts_2 = Counter(seq3)
|
||||||
|
print(seq_counts_2)
|
||||||
|
print(seq_counts + seq_counts_2)
|
||||||
|
print(seq_counts - seq_counts_2)
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
Counter_example()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,31 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from collections import OrderedDict
|
||||||
|
|
||||||
|
def OrderedDict_example():
|
||||||
|
''' show some examples for OrderedDict '''
|
||||||
|
''' keep the order of insertion.
|
||||||
|
maintains a doubly linked list, so size is more than twice than normal dict'''
|
||||||
|
|
||||||
|
|
||||||
|
pairs = [('a', 1), ('b',2), ('c',3)]
|
||||||
|
|
||||||
|
d1 = {}
|
||||||
|
for key, value in pairs:
|
||||||
|
if key not in d1:
|
||||||
|
d1[key] = []
|
||||||
|
d1[key].append(value)
|
||||||
|
for key in d1:
|
||||||
|
print(key, d1[key])
|
||||||
|
|
||||||
|
d2 = OrderedDict(pairs)
|
||||||
|
for key in d2:
|
||||||
|
print(key, d2[key])
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
OrderedDict_example()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,21 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import collections
|
||||||
|
import string
|
||||||
|
import sys
|
||||||
|
|
||||||
|
def count_unique_word():
|
||||||
|
words = collections.defaultdict(int)
|
||||||
|
strip = string.whitespace + string.punctuation + string.digits + "\"'"
|
||||||
|
for filename in sys.argv[1:]:
|
||||||
|
with open(filename) as file:
|
||||||
|
for line in file:
|
||||||
|
for word in line.lower().split():
|
||||||
|
word = word.strip(strip)
|
||||||
|
if len(word) > 2:
|
||||||
|
words[word] = +1
|
||||||
|
for word in sorted(words):
|
||||||
|
print("'{0}' occurs {1} times.".format(word, words[word]))
|
||||||
|
|
@ -0,0 +1,27 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from collections import defaultdict
|
||||||
|
|
||||||
|
def defaultdict_example():
|
||||||
|
''' show some examples for defaultdicts '''
|
||||||
|
pairs = {('a', 1), ('b',2), ('c',3)}
|
||||||
|
|
||||||
|
d1 = {}
|
||||||
|
for key, value in pairs:
|
||||||
|
if key not in d1:
|
||||||
|
d1[key] = []
|
||||||
|
d1[key].append(value)
|
||||||
|
print(d1)
|
||||||
|
|
||||||
|
d2 = defaultdict(list)
|
||||||
|
for key, value in pairs:
|
||||||
|
d2[key].append(value)
|
||||||
|
print(d2)
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
defaultdict_example()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,32 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import string
|
||||||
|
|
||||||
|
def delete_unique_word(str1):
|
||||||
|
''' find and delete all the duplicate characters in a string '''
|
||||||
|
|
||||||
|
# create ordered dict
|
||||||
|
table_c = { key : 0 for key in string.ascii_lowercase}
|
||||||
|
|
||||||
|
# fill the table with the chars in the string
|
||||||
|
for i in str1:
|
||||||
|
table_c[i] += 1
|
||||||
|
|
||||||
|
# scan the table to find times chars > 1
|
||||||
|
for key, value in table_c.items():
|
||||||
|
if value > 1:
|
||||||
|
str1 = str1.replace(key, "")
|
||||||
|
|
||||||
|
return str1
|
||||||
|
|
||||||
|
|
||||||
|
def test_delete_unique_word():
|
||||||
|
str1 = "google"
|
||||||
|
assert(delete_unique_word(str1) == 'le')
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_delete_unique_word()
|
||||||
|
|
@ -0,0 +1,34 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def hash_func(astring, tablesize):
|
||||||
|
sum = 0
|
||||||
|
for pos in range(len(astring)):
|
||||||
|
sum = sum + ord(astring[pos])
|
||||||
|
return sum%tablesize
|
||||||
|
|
||||||
|
|
||||||
|
def find_anagram_hash_function(word1, word2):
|
||||||
|
''' verify if words are anagrams by comparying hash functions'''
|
||||||
|
tablesize = 11
|
||||||
|
return hash_func(word1, tablesize) == hash_func(word2, tablesize)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_anagram_hash_function(module_name='this module'):
|
||||||
|
word1 = 'buffy'
|
||||||
|
word2 = 'bffyu'
|
||||||
|
word3 = 'bffya'
|
||||||
|
assert(find_anagram_hash_function(word1, word2) == True)
|
||||||
|
assert(find_anagram_hash_function(word1, word3) == False)
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_anagram_hash_function()
|
||||||
|
|
@ -0,0 +1,33 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from collections import Counter, defaultdict
|
||||||
|
|
||||||
|
def find_dice_probabilities(S, n_faces=6):
|
||||||
|
''' given 2 dice, determine number of ways to sum S if all dice are rolled '''
|
||||||
|
|
||||||
|
if S > 2*n_faces or S < 2: return None
|
||||||
|
|
||||||
|
cdict = Counter()
|
||||||
|
ddict = defaultdict(list)
|
||||||
|
|
||||||
|
for dice1 in range(1, n_faces+1):
|
||||||
|
for dice2 in range(1, n_faces+1):
|
||||||
|
t = [dice1, dice2]
|
||||||
|
cdict[dice1+dice2] += 1
|
||||||
|
ddict[dice1+dice2].append( t)
|
||||||
|
|
||||||
|
return [cdict[S], ddict[S]]
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_dice_probabilities(module_name='this module'):
|
||||||
|
n_faces = 6
|
||||||
|
S = 5
|
||||||
|
results = find_dice_probabilities(S, n_faces)
|
||||||
|
print(results)
|
||||||
|
assert(results[0] == len(results[1]))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_dice_probabilities()
|
@ -0,0 +1,31 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from collections import Counter
|
||||||
|
|
||||||
|
def find_top_N_recurring_words(seq, N):
|
||||||
|
''' find the top N recurring words in a file:
|
||||||
|
1) use a hash table to find counts
|
||||||
|
2) sort the list on base of the maximum counts
|
||||||
|
3) return the last N words '''
|
||||||
|
|
||||||
|
dcounter = Counter()
|
||||||
|
for word in seq.split():
|
||||||
|
dcounter[word] += 1
|
||||||
|
return dcounter.most_common(N)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_top_N_recurring_words(module_name='this module'):
|
||||||
|
seq = 'buffy angel monster xander a willow gg buffy the monster super buffy angel'
|
||||||
|
N = 3
|
||||||
|
assert(find_top_N_recurring_words(seq, N) == [('buffy', 3), ('monster', 2), ('angel', 2)])
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_top_N_recurring_words()
|
||||||
|
|
@ -0,0 +1,51 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
'''To use timeit you create a Timer object whose parameters are two Python statements. The first parameter is a Python statement that you want to time; the second parameter is a statement that will run once to set up the test. The timeit module will then time how long it takes to execute the statement some number of times. By default timeit will try to run the statement one million times. When its done it returns the time as a floating point value representing the total number of seconds. However, since it executes the statement a million times you can read the result as the number of microseconds to execute the test one time. You can also pass timeit a named parameter called number that allows you to specify how many times the test statement is executed. The following session shows how long it takes to run each of our test functions 1000 times. '''
|
||||||
|
|
||||||
|
|
||||||
|
import timeit
|
||||||
|
import random
|
||||||
|
|
||||||
|
for i in range(10000,1000001,20000):
|
||||||
|
''' this experiment confirm that the contains operator for lists is O(n) and for dict is O(1) '''
|
||||||
|
t = timeit.Timer("random.randrange(%d) in x"%i, "from __main__ import random,x")
|
||||||
|
x = list(range(i))
|
||||||
|
lst_time = t.timeit(number=1000)
|
||||||
|
x = {j:None for j in range(i)}
|
||||||
|
d_time = t.timeit(number=1000)
|
||||||
|
print("%d,%10.3f,%10.3f" % (i, lst_time, d_time))
|
||||||
|
|
||||||
|
|
||||||
|
""" There rersults are:
|
||||||
|
10000, 0.192, 0.002
|
||||||
|
30000, 0.600, 0.002
|
||||||
|
50000, 1.000, 0.002
|
||||||
|
70000, 1.348, 0.002
|
||||||
|
90000, 1.755, 0.002
|
||||||
|
110000, 2.194, 0.002
|
||||||
|
130000, 2.635, 0.002
|
||||||
|
150000, 2.951, 0.002
|
||||||
|
170000, 3.405, 0.002
|
||||||
|
190000, 3.743, 0.002
|
||||||
|
210000, 4.142, 0.002
|
||||||
|
230000, 4.577, 0.002
|
||||||
|
250000, 4.797, 0.002
|
||||||
|
270000, 5.371, 0.002
|
||||||
|
290000, 5.690, 0.002
|
||||||
|
310000, 5.977, 0.002
|
||||||
|
|
||||||
|
so we can see the linear tile for lists, and constant for dict!
|
||||||
|
|
||||||
|
Big-O Efficiency of Python Dictionary Operations
|
||||||
|
Operation Big-O Efficiency
|
||||||
|
copy O(n)
|
||||||
|
get item O(1)
|
||||||
|
set item O(1)
|
||||||
|
delete item O(1)
|
||||||
|
contains (in) O(1)
|
||||||
|
iteration O(n)
|
||||||
|
"""
|
||||||
|
|
@ -0,0 +1,38 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def usual_dict(dict_data):
|
||||||
|
newdata = {}
|
||||||
|
for k, v in dict_data:
|
||||||
|
if k in newdata:
|
||||||
|
newdata[k].append(v)
|
||||||
|
else:
|
||||||
|
newdata[k] = [v]
|
||||||
|
return newdata
|
||||||
|
|
||||||
|
|
||||||
|
def setdefault_dict(dict_data):
|
||||||
|
newdata = {}
|
||||||
|
for k, v in dict_data:
|
||||||
|
newdata.setdefault(k, []).append(v)
|
||||||
|
return newdata
|
||||||
|
|
||||||
|
|
||||||
|
def test_setdef(module_name='this module'):
|
||||||
|
dict_data = (('key1', 'value1'),
|
||||||
|
('key1', 'value2'),
|
||||||
|
('key2', 'value3'),
|
||||||
|
('key2', 'value4'),
|
||||||
|
('key2', 'value5'),)
|
||||||
|
print(usual_dict(dict_data))
|
||||||
|
print(setdefault_dict(dict_data))
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_setdef()
|
||||||
|
|
@ -0,0 +1,45 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import string
|
||||||
|
|
||||||
|
|
||||||
|
def verify_two_strings_are_anagrams(str1, str2):
|
||||||
|
""" find whether two words are anagrams. Since sets do not count occurency, and sorting is O(nlogn)
|
||||||
|
we will use hash tables. We scan the first string and add all the character occurences. Then we
|
||||||
|
scan the second tring and decrease all the caracther occurences. If all the counts are zero, it is
|
||||||
|
an anagram"""
|
||||||
|
|
||||||
|
# create the hash table
|
||||||
|
ana_table = {key:0 for key in string.ascii_lowercase}
|
||||||
|
|
||||||
|
# scan first string
|
||||||
|
for i in str1:
|
||||||
|
ana_table[i] += 1
|
||||||
|
|
||||||
|
# scan second string
|
||||||
|
for i in str2:
|
||||||
|
ana_table[i] -= 1
|
||||||
|
|
||||||
|
# verify whether all the entries are 0
|
||||||
|
if len(set(ana_table.values())) < 2: return True
|
||||||
|
else: return False
|
||||||
|
|
||||||
|
|
||||||
|
def test_verify_two_strings_are_anagrams():
|
||||||
|
str1 = 'marina'
|
||||||
|
str2 = 'aniram'
|
||||||
|
assert(verify_two_strings_are_anagrams(str1, str2) == True)
|
||||||
|
str1 = 'google'
|
||||||
|
str2 = 'gouglo'
|
||||||
|
assert(verify_two_strings_are_anagrams(str1, str2) == False)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_verify_two_strings_are_anagrams()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,47 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def find_closest_num_seq_unsorted(seq):
|
||||||
|
''' Find the Closest two Numbers in a Sequence. If we do this without sorting
|
||||||
|
first, the runtime will be O(n^2) '''
|
||||||
|
dd = float("inf")
|
||||||
|
for x in seq:
|
||||||
|
for y in seq:
|
||||||
|
if x == y: continue
|
||||||
|
d = abs(x - y)
|
||||||
|
if d < dd:
|
||||||
|
xx, yy, dd = x, y, d
|
||||||
|
return xx, yy
|
||||||
|
|
||||||
|
|
||||||
|
def find_closest_num_seq_sorted(seq):
|
||||||
|
''' However, if we sort first, we can achieve it with runtime O(n log n): '''
|
||||||
|
seq.sort()
|
||||||
|
print(seq)
|
||||||
|
dd = float("inf")
|
||||||
|
for i in range(len(seq) - 1):
|
||||||
|
x, y = seq[i], seq[i+1]
|
||||||
|
if x == y: continue
|
||||||
|
d = abs(x-y)
|
||||||
|
if d < dd:
|
||||||
|
xx, yy, dd = x, y, d
|
||||||
|
return xx, yy
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_closest_num_seq(module_name='this module'):
|
||||||
|
import random
|
||||||
|
seq = [random.randrange(100) for i in range(20)]
|
||||||
|
print(seq)
|
||||||
|
print(find_closest_num_seq_sorted(seq))
|
||||||
|
print(find_closest_num_seq_unsorted(seq))
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_closest_num_seq()
|
||||||
|
|
@ -0,0 +1,44 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
def find_duplicate_num_array(l1):
|
||||||
|
""" an array contains n numbers ranging from 0 to n-1. there are some numbers duplicated, but it is
|
||||||
|
not clear how many. this code find a duplicate number in the array. """
|
||||||
|
|
||||||
|
""" A naive solution is to sort the input array, costing O(nlogn). Another solution is the utilization of a hash set. When the number is scanned, it is either in or not. It costs O(n) auxiliary memory to accomodate a hash set. A third solution, that only costs O(1) is consider that indexes in an array with length n are in the range n-1. If there were no duplication in the n numbers from 0 to n-1, we could rearange them sorted, so that each i has its ith number. Since there are duplicates, some locations are occupied by multiple numbers, other are vacant. So every number is scanned one by one, if it the number is not in the right i, it is compared to that from i, and the duplicate can be found, or we swap. Continue until a duplicate is found."""
|
||||||
|
|
||||||
|
for i in range(len(l1)):
|
||||||
|
if l1[i] == i: continue
|
||||||
|
elif l1[i] < 0 or l1[i] > len(l1)-1:
|
||||||
|
return None
|
||||||
|
elif l1[i] == l1[l1[i]]:
|
||||||
|
return True
|
||||||
|
else:
|
||||||
|
aux = l1[l1[i]]
|
||||||
|
l1[l1[i]] = l1[i]
|
||||||
|
l1[i] = aux
|
||||||
|
else:
|
||||||
|
return False
|
||||||
|
|
||||||
|
def test_find_duplicate_num_array():
|
||||||
|
a = [1,3,5,2,4,0]
|
||||||
|
b = [1,3,5,2,1,0,4]
|
||||||
|
c = [0,0]
|
||||||
|
assert(find_duplicate_num_array(b) == True)
|
||||||
|
assert(find_duplicate_num_array(a) == False)
|
||||||
|
assert(find_duplicate_num_array(c) == True)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_duplicate_num_array()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,30 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
def find_long_con_inc(seq):
|
||||||
|
''' find the longest continuous increasing subsequence'''
|
||||||
|
one_seq = []
|
||||||
|
result = []
|
||||||
|
|
||||||
|
for i in range(0, len(seq)-1):
|
||||||
|
pivot = seq[i]
|
||||||
|
if pivot <= seq[i+1]:
|
||||||
|
one_seq.append(pivot)
|
||||||
|
else:
|
||||||
|
one_seq.append(pivot)
|
||||||
|
if len(one_seq) > len(result):
|
||||||
|
result = one_seq
|
||||||
|
one_seq = []
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_long_con_inc(module_name='this module'):
|
||||||
|
seq = [1, -2, 3, 5, 1, -1, 4, -1, 6]
|
||||||
|
long_con_inc = [-2,3,5]
|
||||||
|
|
||||||
|
assert(find_long_con_inc(seq) == long_con_inc )
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_long_con_inc()
|
||||||
|
|
@ -0,0 +1,31 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
def find_long_con_inc(seq):
|
||||||
|
''' find the longest continuous increasing subsequence'''
|
||||||
|
one_seq = []
|
||||||
|
result = []
|
||||||
|
|
||||||
|
for i in range(0, len(seq)-1):
|
||||||
|
pivot = seq[i]
|
||||||
|
if pivot <= seq[i+1]:
|
||||||
|
one_seq.append(pivot)
|
||||||
|
else:
|
||||||
|
one_seq.append(pivot)
|
||||||
|
if len(one_seq) > len(result):
|
||||||
|
result = one_seq
|
||||||
|
one_seq = []
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_long_con_inc(module_name='this module'):
|
||||||
|
seq = [1, -2, 3, 5, 1, -1, 4, -1, 6]
|
||||||
|
long_con_inc = [-2,3,5]
|
||||||
|
|
||||||
|
assert(find_long_con_inc(seq) == long_con_inc )
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_long_con_inc()
|
||||||
|
|
@ -0,0 +1,58 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
def find_majority_in_seq(seq):
|
||||||
|
''' find value which occurrence is greater than the total occurrence of all other elements '''
|
||||||
|
times = 1
|
||||||
|
result = seq[0]
|
||||||
|
for i in range(len(seq)):
|
||||||
|
if times == 0:
|
||||||
|
result = seq[i]
|
||||||
|
times = 1
|
||||||
|
elif seq[i] == result:
|
||||||
|
times +=1
|
||||||
|
else:
|
||||||
|
times -=1
|
||||||
|
|
||||||
|
if times == 0: return None
|
||||||
|
else:
|
||||||
|
count = 0
|
||||||
|
for i, c in enumerate(seq):
|
||||||
|
if c == result:
|
||||||
|
count += 1
|
||||||
|
return result, count
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_majority_in_seq():
|
||||||
|
seq = [1, 1, 2, 3, 3, 3, 4, 4, 4, 4, 5, 6]
|
||||||
|
seq2 = [1, 2, 3]
|
||||||
|
assert(find_majority_in_seq(seq) == (4, 4))
|
||||||
|
assert(find_majority_in_seq(seq2) == None)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_majority_in_seq()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
"""
|
||||||
|
>>> A = [1, 2, 3, 2, 2, 4, 2, 5, 2]
|
||||||
|
>>> find_majority(A)
|
||||||
|
(2, 5)
|
||||||
|
>>> A = [1]
|
||||||
|
>>> find_majority(A)
|
||||||
|
(1, 1)
|
||||||
|
>>> A = [1, 2, 3, 2, 5, 6, 7]
|
||||||
|
>>> find_majority(A)
|
||||||
|
No Majority Element.
|
||||||
|
"""
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,44 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def find_max_profit_On(seq):
|
||||||
|
''' find the most profit from a seq with O(n) '''
|
||||||
|
max_profit = 0
|
||||||
|
min_value = seq[0]
|
||||||
|
for i in range(1, len(seq)):
|
||||||
|
profit_here = seq[i]- min_value
|
||||||
|
if profit_here > max_profit:
|
||||||
|
max_profit = profit_here
|
||||||
|
else:
|
||||||
|
if min_value > seq[i]:
|
||||||
|
min_value = seq[i]
|
||||||
|
|
||||||
|
return max_profit
|
||||||
|
|
||||||
|
|
||||||
|
def find_max_profit_On2(seq):
|
||||||
|
''' find the most profit from a seq with O(n2) '''
|
||||||
|
max_profit = 0
|
||||||
|
for i in range(len(seq)-1):
|
||||||
|
for j in range (i, len(seq)-1):
|
||||||
|
if seq[j] - seq[i] > max_profit:
|
||||||
|
max_profit = seq[j] - seq[i]
|
||||||
|
return max_profit
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_max_profit():
|
||||||
|
seq = [9,11,5,7,16,1]
|
||||||
|
assert(find_max_profit_On(seq) == 11)
|
||||||
|
assert(find_max_profit_On2(seq) == 11)
|
||||||
|
seq = [1,15,2,3,4,3]
|
||||||
|
assert(find_max_profit_On(seq) == 14)
|
||||||
|
assert(find_max_profit_On2(seq) == 14)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_max_profit()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,44 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
def find_max_subarray1(l1):
|
||||||
|
''' calculate the greatest sum of subarrays from an array.
|
||||||
|
An array with n elements has n(n+1)/2 subarrays so force brute cost O(n^2).
|
||||||
|
What we can do is to check when a sum becomes a negative number or zero, and then discard, since
|
||||||
|
this will not "add" anything to the new event... When the sum decreases, it gets the previous sum. '''
|
||||||
|
sum_new, result = 0, 0
|
||||||
|
for c in l1:
|
||||||
|
result = max(result, sum_new)
|
||||||
|
sum_new += c
|
||||||
|
if sum_new <= 0: sum_new = 0
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def find_max_subarray2(l1):
|
||||||
|
''' find the contiguous subarray which has the largest sum (Kadane's algorithm in O(n))
|
||||||
|
with extra O(n) space '''
|
||||||
|
sum_old = [l1[0]]
|
||||||
|
for c in l1:
|
||||||
|
sum_old.append(max(c, sum_old [-1] + c))
|
||||||
|
return max(sum_old)
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_max_subarray():
|
||||||
|
l1 = [-2, 1, -3, 4, -1, 2, 1, -5, 4]
|
||||||
|
l2 = [-1, 3, -5, 4, 6, -1, 2, -7, 13, -3]
|
||||||
|
assert(find_max_subarray1(l1)) == 6)
|
||||||
|
assert(find_max_subarray1(l2)) == 17)
|
||||||
|
assert(find_max_subarray2(l1) == 6)
|
||||||
|
assert(find_max_subarray2(l2) == 17)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_max_subarray()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,44 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
def find_max_subarray1(l1):
|
||||||
|
''' calculate the greatest sum of subarrays from an array.
|
||||||
|
An array with n elements has n(n+1)/2 subarrays so force brute cost O(n^2).
|
||||||
|
What we can do is to check when a sum becomes a negative number or zero, and then discard, since
|
||||||
|
this will not "add" anything to the new event... When the sum decreases, it gets the previous sum. '''
|
||||||
|
sum_new, result = 0, 0
|
||||||
|
for c in l1:
|
||||||
|
result = max(result, sum_new)
|
||||||
|
sum_new += c
|
||||||
|
if sum_new <= 0: sum_new = 0
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def find_max_subarray2(l1):
|
||||||
|
''' find the contiguous subarray which has the largest sum (Kadane's algorithm in O(n))
|
||||||
|
with extra O(n) space '''
|
||||||
|
sum_old = [l1[0]]
|
||||||
|
for c in l1:
|
||||||
|
sum_old.append(max(c, sum_old [-1] + c))
|
||||||
|
return max(sum_old)
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_max_subarray():
|
||||||
|
l1 = [-2, 1, -3, 4, -1, 2, 1, -5, 4]
|
||||||
|
l2 = [-1, 3, -5, 4, 6, -1, 2, -7, 13, -3]
|
||||||
|
assert(find_max_subarray1(l1)) == 6)
|
||||||
|
assert(find_max_subarray1(l2)) == 17)
|
||||||
|
assert(find_max_subarray2(l1) == 6)
|
||||||
|
assert(find_max_subarray2(l2) == 17)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_max_subarray()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,33 @@
|
|||||||
|
def find_product_without_division(seq):
|
||||||
|
'''Given an array of numbers, replace each number with the product of all the numbers in the array except the number itself *without* using division '''
|
||||||
|
forw = []
|
||||||
|
bacw = []
|
||||||
|
|
||||||
|
for i in range(len(seq)):
|
||||||
|
prod_f = 1
|
||||||
|
prod_b = 1
|
||||||
|
for next in range(i+1, len(seq)):
|
||||||
|
prod_f *= seq[next]
|
||||||
|
for before in range(0, i):
|
||||||
|
prod_b *= seq[before]
|
||||||
|
forw.append(prod_f)
|
||||||
|
bacw.append(prod_b)
|
||||||
|
|
||||||
|
print(bacw)
|
||||||
|
print(forw)
|
||||||
|
for i in range(len(seq)):
|
||||||
|
seq[i] = forw[i]*bacw[i]
|
||||||
|
|
||||||
|
return seq
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_product_without_division():
|
||||||
|
seq = [2,3,4]
|
||||||
|
result = [12, 8, 6]
|
||||||
|
print(find_product_without_division(seq))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_product_without_division()
|
@ -0,0 +1,55 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
import math
|
||||||
|
|
||||||
|
def find_two_missing_numbers(l1):
|
||||||
|
""" Two numbers out of n numbers from 1 to n are missing. The remaining n-2 numbers are in the
|
||||||
|
array but not sorted. Find the missing numbers The sum1 is the sum of all the elements in n. The
|
||||||
|
sum2 is the sum of all the elements in n-2. sum1 - sum2 = num1 + num2 = s. The prod1 is the prod of
|
||||||
|
all the elements in n. The prod2 is the prod of all the elements in n-2. prod1/prod2 = num1*num2 =
|
||||||
|
p. Runtime is O(n), because it scan 3 times. Space is O(1)
|
||||||
|
|
||||||
|
- In case of finding one integer, Let the missing number be M. We know that the sum of first N
|
||||||
|
natural numbers is N*(N+1)/2. Traverse through the array once and calculate the sum. This is the
|
||||||
|
sum of first N natural numbers – M or S=N*(N+1)/2 – M. Therefore M = N*(N+1)/2 – S.
|
||||||
|
"""
|
||||||
|
|
||||||
|
n_min_2 = len(l1)
|
||||||
|
n = n_min_2 + 2
|
||||||
|
sum1, sum2, prod1, prod2 = 0,0,1,1
|
||||||
|
sum2 = sum(l1[:])
|
||||||
|
sum1 = sum(range(1,n+1))
|
||||||
|
s = sum1 - sum2
|
||||||
|
|
||||||
|
for i in range(1, n-1):
|
||||||
|
prod1 = prod1*i
|
||||||
|
prod2 = prod2*l1[i-1]
|
||||||
|
|
||||||
|
prod1 = prod1*n*(n-1)
|
||||||
|
p = prod1/prod2
|
||||||
|
num1 = (s + math.sqrt(s*s - 4*p))/2
|
||||||
|
num2 = (s - math.sqrt(s*s - 4*p))/2
|
||||||
|
|
||||||
|
return num1, num2
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_two_missing_numbers():
|
||||||
|
l1 = [1, 3, 5]
|
||||||
|
result = find_two_missing_numbers(l1)
|
||||||
|
assert(result[0] == 2.0 or result[0] == 4.0)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_two_missing_numbers()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,27 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def greatest_sum_sub_array(l1):
|
||||||
|
sum_new = 0
|
||||||
|
results = []
|
||||||
|
for i, c in enumerate(l1):
|
||||||
|
sum_old = sum_new
|
||||||
|
sum_new = sum_old + c
|
||||||
|
if sum_new <= 0 or sum_new < sum_old:
|
||||||
|
sum_new = 0
|
||||||
|
results.append(sum_old)
|
||||||
|
continue
|
||||||
|
results.append(sum_new)
|
||||||
|
results.sort()
|
||||||
|
return results.pop()
|
||||||
|
|
||||||
|
def test_greatest_sum_sub_array():
|
||||||
|
l1 = [1, -4, 20, -4, 5, 15, 3]
|
||||||
|
assert(greatest_sum_sub_array(l1) == 23)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_greatest_sum_sub_array()
|
||||||
|
|
@ -0,0 +1,47 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def find_closest_num_seq_unsorted(seq):
|
||||||
|
''' Find the Closest two Numbers in a Sequence. If we do this without sorting
|
||||||
|
first, the runtime will be O(n^2) '''
|
||||||
|
dd = float("inf")
|
||||||
|
for x in seq:
|
||||||
|
for y in seq:
|
||||||
|
if x == y: continue
|
||||||
|
d = abs(x - y)
|
||||||
|
if d < dd:
|
||||||
|
xx, yy, dd = x, y, d
|
||||||
|
return xx, yy
|
||||||
|
|
||||||
|
|
||||||
|
def find_closest_num_seq_sorted(seq):
|
||||||
|
''' However, if we sort first, we can achieve it with runtime O(n log n): '''
|
||||||
|
seq.sort()
|
||||||
|
print(seq)
|
||||||
|
dd = float("inf")
|
||||||
|
for i in range(len(seq) - 1):
|
||||||
|
x, y = seq[i], seq[i+1]
|
||||||
|
if x == y: continue
|
||||||
|
d = abs(x-y)
|
||||||
|
if d < dd:
|
||||||
|
xx, yy, dd = x, y, d
|
||||||
|
return xx, yy
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_closest_num_seq(module_name='this module'):
|
||||||
|
import random
|
||||||
|
seq = [random.randrange(100) for i in range(20)]
|
||||||
|
print(seq)
|
||||||
|
print(find_closest_num_seq_sorted(seq))
|
||||||
|
print(find_closest_num_seq_unsorted(seq))
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_closest_num_seq()
|
||||||
|
|
@ -0,0 +1,38 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
def merge_two_sorted_arrays(a1, a2):
|
||||||
|
""" merge two sorted arrays, keeping the final sorted """
|
||||||
|
if len(a1) >= len(a2):
|
||||||
|
biga = a1
|
||||||
|
smalla = a2
|
||||||
|
else:
|
||||||
|
biga = a2
|
||||||
|
smalla = a1
|
||||||
|
final = []
|
||||||
|
count = 0
|
||||||
|
for i in range(len(biga)):
|
||||||
|
if count < len(smalla) and smalla[count] < biga[i]:
|
||||||
|
final.append(smalla[count])
|
||||||
|
count+=1
|
||||||
|
final.append(biga[i])
|
||||||
|
return final
|
||||||
|
|
||||||
|
def test_merge_two_sorted_arrays():
|
||||||
|
a1 = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
|
||||||
|
a2 = [3, 6, 7]
|
||||||
|
assert(merge_two_sorted_arrays(a1, a2) == [0, 1, 2, 3, 3, 4, 5, 6, 6, 7, 7, 8, 9, 10])
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_merge_two_sorted_arrays()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,39 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def print_all_seq_with_cont_num(s):
|
||||||
|
''' print all sequences with cont. numbers (2 at least) whose sum is a given s '''
|
||||||
|
if s < 3: return s
|
||||||
|
small = 1
|
||||||
|
big = 2
|
||||||
|
sum_here = big + small
|
||||||
|
result = []
|
||||||
|
|
||||||
|
while small < (1+s)/2:
|
||||||
|
sum_here = sum(range(small, big))
|
||||||
|
if sum_here < s:
|
||||||
|
big += 1
|
||||||
|
elif sum_here > s:
|
||||||
|
small +=1
|
||||||
|
else:
|
||||||
|
result.append(list(range(small, big)))
|
||||||
|
big += 1
|
||||||
|
|
||||||
|
return result
|
||||||
|
|
||||||
|
def test_print_all_seq_with_cont_num():
|
||||||
|
s = 15
|
||||||
|
sum_set_for_s = [[1,2,3,4,5], [4,5,6], [7,8]]
|
||||||
|
assert(print_all_seq_with_cont_num(s) == sum_set_for_s)
|
||||||
|
s = 1
|
||||||
|
assert(print_all_seq_with_cont_num(s)== 1)
|
||||||
|
s = 0
|
||||||
|
assert(print_all_seq_with_cont_num(s) == 0)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_print_all_seq_with_cont_num()
|
||||||
|
|
@ -0,0 +1,37 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def removing_duplicates_seq(seq):
|
||||||
|
''' if the values are hashable, we can use set and generators to remove duplicates
|
||||||
|
in a sequence '''
|
||||||
|
seen = set()
|
||||||
|
for item in seq:
|
||||||
|
if item not in seen:
|
||||||
|
yield item
|
||||||
|
seen.add(item)
|
||||||
|
|
||||||
|
def removing_duplicates_seq_not_hash(seq, key= None):
|
||||||
|
''' if the item is not hashable, such as dictionaries '''
|
||||||
|
seen = set()
|
||||||
|
for item in seq:
|
||||||
|
val = item if key is None else key[item]
|
||||||
|
if item not in seen:
|
||||||
|
yield item
|
||||||
|
seen.add(val)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_removing_duplicates_seq():
|
||||||
|
seq = [1, 2, 2, 2, 3, 3, 4, 4, 4]
|
||||||
|
dict = {'a':1, 'b':2, 'a':2, 'a':1}
|
||||||
|
assert(list(removing_duplicates_seq(seq)) == [1,2,3,4])
|
||||||
|
assert(list(removing_duplicates_seq_not_hash(dict)) == ['a', 'b'])
|
||||||
|
print('Tests passed!'.center(20, '*'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_removing_duplicates_seq()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,67 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
'''To use timeit you create a Timer object whose parameters are two Python statements. The first parameter is a Python statement that you want to time; the second parameter is a statement that will run once to set up the test. The timeit module will then time how long it takes to execute the statement some number of times. By default timeit will try to run the statement one million times. When its done it returns the time as a floating point value representing the total number of seconds. However, since it executes the statement a million times you can read the result as the number of microseconds to execute the test one time. You can also pass timeit a named parameter called number that allows you to specify how many times the test statement is executed. The following session shows how long it takes to run each of our test functions 1000 times. '''
|
||||||
|
|
||||||
|
|
||||||
|
def test1():
|
||||||
|
l = []
|
||||||
|
for i in range(1000):
|
||||||
|
l = l + [i]
|
||||||
|
|
||||||
|
def test2():
|
||||||
|
l = []
|
||||||
|
for i in range(1000):
|
||||||
|
l.append(i)
|
||||||
|
|
||||||
|
def test3():
|
||||||
|
l = [i for i in range(1000)]
|
||||||
|
|
||||||
|
def test4():
|
||||||
|
l = list(range(1000))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
import timeit
|
||||||
|
t1 = timeit.Timer("test1()", "from __main__ import test1")
|
||||||
|
print("concat ",t1.timeit(number=1000), "milliseconds")
|
||||||
|
t2 = timeit.Timer("test2()", "from __main__ import test2")
|
||||||
|
print("append ",t2.timeit(number=1000), "milliseconds")
|
||||||
|
t3 = timeit.Timer("test3()", "from __main__ import test3")
|
||||||
|
print("comprehension ",t3.timeit(number=1000), "milliseconds")
|
||||||
|
t4 = timeit.Timer("test4()", "from __main__ import test4")
|
||||||
|
print("list range ",t4.timeit(number=1000), "milliseconds")
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
""" The results are:
|
||||||
|
('concat ', 2.366791009902954, 'milliseconds')
|
||||||
|
('append ', 0.16743111610412598, 'milliseconds')
|
||||||
|
('comprehension ', 0.06446194648742676, 'milliseconds')
|
||||||
|
('list range ', 0.021029949188232422, 'milliseconds')
|
||||||
|
|
||||||
|
|
||||||
|
So we see the following pattern for lists:
|
||||||
|
|
||||||
|
Operation Big-O Efficiency
|
||||||
|
index [] O(1)
|
||||||
|
index assignment O(1)
|
||||||
|
append O(1)
|
||||||
|
pop() O(1)
|
||||||
|
pop(i) O(n)
|
||||||
|
insert(i,item) O(n)
|
||||||
|
del operator O(n)
|
||||||
|
iteration O(n)
|
||||||
|
contains (in) O(n)
|
||||||
|
get slice [x:y] O(k)
|
||||||
|
del slice O(n)
|
||||||
|
set slice O(n+k)
|
||||||
|
reverse O(n)
|
||||||
|
concatenate O(k)
|
||||||
|
sort O(n log n)
|
||||||
|
multiply O(nk)
|
||||||
|
"""
|
||||||
|
|
@ -0,0 +1,36 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def sum_two_numbers_sequence(seq, s):
|
||||||
|
""" given an increasing sorted array and an integer s, find if there is a pair of two numbers in the array whose sum is s. It takes O(n). """
|
||||||
|
l1 = seq[:]
|
||||||
|
l2 = seq[:]
|
||||||
|
l2.reverse()
|
||||||
|
n1 = l1.pop()
|
||||||
|
n2 = l2.pop()
|
||||||
|
while l2 and l1:
|
||||||
|
sum_here = n1 + n2
|
||||||
|
if sum_here > s:
|
||||||
|
n1 = l1.pop()
|
||||||
|
elif sum_here < s:
|
||||||
|
n2 = l2.pop()
|
||||||
|
else:
|
||||||
|
return True
|
||||||
|
return False
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_sum_two_numbers_sequence():
|
||||||
|
l1 = [1,2,3,4,5,6,7,8]
|
||||||
|
s = 7
|
||||||
|
assert(sum_two_numbers_sequence(l1, s) == True)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_sum_two_numbers_sequence()
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,28 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
import shutil
|
||||||
|
|
||||||
|
def change_file_ext():
|
||||||
|
""" read a file and an extension from the command line and produces a copy with its extension changed"""
|
||||||
|
if len(sys.argv) < 2:
|
||||||
|
print("Usage: change_ext.py filename.old_ext 'new_ext'")
|
||||||
|
sys.exit()
|
||||||
|
|
||||||
|
name = os.path.splitext(sys.argv[1])[0] + "." + sys.argv[2]
|
||||||
|
print (name)
|
||||||
|
|
||||||
|
try:
|
||||||
|
shutil.copyfile(sys.argv[1], name)
|
||||||
|
except OSError as err:
|
||||||
|
print (err)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
change_file_ext()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,33 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import pickle
|
||||||
|
|
||||||
|
def export_pickle(data, filename='test.dat', compress=False):
|
||||||
|
""" simple example of how to use pickle to export files """
|
||||||
|
fh = None
|
||||||
|
try:
|
||||||
|
if compress:
|
||||||
|
fh = gzip.open(filename, "wb") # write binary
|
||||||
|
else:
|
||||||
|
fh = open(filename, "wb") # compact binary pickle format
|
||||||
|
pickle.dump(data, fh, pickle.HIGHEST_PROTOCOL)
|
||||||
|
|
||||||
|
except(EnvironmentError, pickle.PickingError) as err:
|
||||||
|
print("{0}: export error: {1}".format(os.path.basename(sys.argv[0], err)))
|
||||||
|
return False
|
||||||
|
|
||||||
|
finally:
|
||||||
|
if fh is not None:
|
||||||
|
fh.close()
|
||||||
|
|
||||||
|
|
||||||
|
def test_export_pickle():
|
||||||
|
mydict = {'a': 1, 'b': 2, 'c': 3}
|
||||||
|
export_pickle(mydict)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_export_pickle()
|
@ -0,0 +1,18 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def fib_generator():
|
||||||
|
a, b = 0, 1
|
||||||
|
while True:
|
||||||
|
yield b
|
||||||
|
a, b = b, a+b
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
fib = fib_generator()
|
||||||
|
print(next(fib))
|
||||||
|
print(next(fib))
|
||||||
|
print(next(fib))
|
||||||
|
print(next(fib))
|
@ -0,0 +1,26 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import sys
|
||||||
|
|
||||||
|
def grep_word_from_files():
|
||||||
|
''' using iterator enumerate to create a grep command '''
|
||||||
|
word = sys.argv[1]
|
||||||
|
for filename in sys.argv[2:]:
|
||||||
|
with open(filename) as file:
|
||||||
|
for lino, line in enumerate(file, start=1):
|
||||||
|
if word in line:
|
||||||
|
print("{0}:{1}:{2:.40}".format(filename, lino, line.rstrip()))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
if len(sys.argv) < 2:
|
||||||
|
print("Usage: grep_word_from_files.py word infile1 [infile2...]")
|
||||||
|
sys.exit()
|
||||||
|
else:
|
||||||
|
grep_word_from_files()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,31 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import pickle
|
||||||
|
|
||||||
|
def import_pickle(filename):
|
||||||
|
""" an example of using pickle for importing data from files """
|
||||||
|
fh = None
|
||||||
|
try:
|
||||||
|
fh = open(filename, "rb")
|
||||||
|
mydict2 = pickle.load(fh)
|
||||||
|
return mydict2
|
||||||
|
|
||||||
|
except (EnvironmentError) as err:
|
||||||
|
print ("{0}: import error: {0}".format(os.path.basename(sys.arg[0]), err))
|
||||||
|
return false
|
||||||
|
|
||||||
|
finally:
|
||||||
|
if fh is not None:
|
||||||
|
fh.close()
|
||||||
|
|
||||||
|
|
||||||
|
def test_import_pickle():
|
||||||
|
pkl_file = 'test.dat'
|
||||||
|
mydict = import_pickle(pkl_file)
|
||||||
|
print(mydict)
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_import_pickle()
|
@ -0,0 +1,18 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
import sys
|
||||||
|
|
||||||
|
def main():
|
||||||
|
''' print command line arguments '''
|
||||||
|
for arg in sys.argv[1:]:
|
||||||
|
print arg
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
main()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,53 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
|
||||||
|
def read_data(filename):
|
||||||
|
lines = []
|
||||||
|
fh = None
|
||||||
|
try:
|
||||||
|
fh = open(filename)
|
||||||
|
for line in fh:
|
||||||
|
if line.strip():
|
||||||
|
lines.append(line)
|
||||||
|
except (IOError, OSError) as err:
|
||||||
|
print(err)
|
||||||
|
finally:
|
||||||
|
if fh is not None:
|
||||||
|
fh.close()
|
||||||
|
return lines
|
||||||
|
|
||||||
|
|
||||||
|
def write_data(lines, filename):
|
||||||
|
fh = None
|
||||||
|
try:
|
||||||
|
fh = open(filename, "w")
|
||||||
|
for line in lines:
|
||||||
|
fh.write(line)
|
||||||
|
except (EnvironmentError) as err:
|
||||||
|
print(err)
|
||||||
|
finally:
|
||||||
|
if fh is not None:
|
||||||
|
fh.close()
|
||||||
|
|
||||||
|
|
||||||
|
def remove_blank_lines():
|
||||||
|
""" read a list of filenames on the command line and for each one produces another file with the same content but with no blank lines """
|
||||||
|
|
||||||
|
if len(sys.argv) < 2:
|
||||||
|
print ("Usage: noblank.py infile1 [infile2...]")
|
||||||
|
|
||||||
|
for filename in sys.argv[1:]:
|
||||||
|
lines = read_data(filename)
|
||||||
|
if lines:
|
||||||
|
write_data(lines, filename)
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
remove_blank_lines()
|
||||||
|
|
@ -0,0 +1,23 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import time
|
||||||
|
|
||||||
|
def sumOfN2(n):
|
||||||
|
''' a simple example of how to time a function '''
|
||||||
|
start = time.time()
|
||||||
|
theSum = 0
|
||||||
|
for i in range(1,n+1):
|
||||||
|
theSum = theSum + i
|
||||||
|
end = time.time()
|
||||||
|
return theSum,end-start
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
n = 5
|
||||||
|
print("Sum is %d and required %10.7f seconds"%sumOfN2(n))
|
||||||
|
n = 200
|
||||||
|
print("Sum is %d and required %10.7f seconds"%sumOfN2(n))
|
||||||
|
|
@ -0,0 +1,27 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def convert_dec_to_any_base_rec(number, base):
|
||||||
|
''' convert an integer to a string in any base'''
|
||||||
|
convertString = '012345679ABCDEF'
|
||||||
|
if number < base: return convertString[number]
|
||||||
|
else:
|
||||||
|
return convert_dec_to_any_base_rec(number//base, base) + convertString[number%base]
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_convert_dec_to_any_base_rec(module_name='this module'):
|
||||||
|
number = 9
|
||||||
|
base = 2
|
||||||
|
assert(convert_dec_to_any_base_rec(number, base) == '1001')
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_convert_dec_to_any_base_rec()
|
||||||
|
|
@ -0,0 +1,24 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
def convert_from_decimal(number, base):
|
||||||
|
''' convert any decimal number to another base. '''
|
||||||
|
multiplier, result = 1, 0
|
||||||
|
while number > 0:
|
||||||
|
result += number%base*multiplier
|
||||||
|
multiplier *= 10
|
||||||
|
number = number//base
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
def test_convert_from_decimal():
|
||||||
|
number, base = 9, 2
|
||||||
|
assert(convert_from_decimal(number, base) == 1001)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_convert_from_decimal()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,24 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def convert_from_decimal_larger_bases(number, base):
|
||||||
|
''' convert any decimal number to a number in a base up to 20'''
|
||||||
|
strings = "0123456789ABCDEFGHIJ"
|
||||||
|
result = ""
|
||||||
|
while number > 0:
|
||||||
|
digit = number%base
|
||||||
|
result = strings[digit] + result
|
||||||
|
number = number//base
|
||||||
|
return result
|
||||||
|
|
||||||
|
def test_convert_from_decimal_larger_bases():
|
||||||
|
number, base = 31, 16
|
||||||
|
assert(convert_from_decimal_larger_bases(number, base) == '1F')
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_convert_from_decimal_larger_bases()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,25 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def convert_to_decimal(number, base):
|
||||||
|
''' convert any number in another base to the decimal base'''
|
||||||
|
multiplier, result = 1, 0
|
||||||
|
while number > 0:
|
||||||
|
result += number%10*multiplier
|
||||||
|
multiplier *= base
|
||||||
|
number = number//10
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
def test_convert_to_decimal():
|
||||||
|
number, base = 1001, 2
|
||||||
|
assert(convert_to_decimal(number, base) == 9)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_convert_to_decimal()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,44 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import math
|
||||||
|
|
||||||
|
def find_fibonacci_seq_rec(n):
|
||||||
|
''' implements the nth fibonacci value in a recursive exponential runtime '''
|
||||||
|
if n < 2: return n
|
||||||
|
return find_fibonacci_seq_rec(n - 1) + find_fibonacci_seq_rec(n - 2)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def find_fibonacci_seq_iter(n):
|
||||||
|
''' return the nth fibonacci value in a iterative O(n^2) runtime '''
|
||||||
|
if n < 2: return n
|
||||||
|
a, b = 0, 1
|
||||||
|
for i in range(n):
|
||||||
|
a, b = b, a + b
|
||||||
|
return a
|
||||||
|
|
||||||
|
|
||||||
|
def find_fibonacci_seq_form(n):
|
||||||
|
''' return the nth fibonacci value implemented by the formula, nearly constant-time algorithm,
|
||||||
|
but, it has a poor precise (after 72 it starts to become wrong) '''
|
||||||
|
sq5 = math.sqrt(5)
|
||||||
|
phi = (1 + sq5) / 2
|
||||||
|
return int(math.floor(phi ** n / sq5))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_fib():
|
||||||
|
n = 10
|
||||||
|
assert(find_fibonacci_seq_rec(n) == 55)
|
||||||
|
assert(find_fibonacci_seq_iter(n) == 55)
|
||||||
|
assert(find_fibonacci_seq_form(n) == 55)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_fib()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,28 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
def finding_gcd(a, b):
|
||||||
|
''' implements the greatest common divider algorithm '''
|
||||||
|
while(b != 0):
|
||||||
|
result = b
|
||||||
|
a, b = b, a % b
|
||||||
|
return result
|
||||||
|
|
||||||
|
|
||||||
|
def test_finding_gcd():
|
||||||
|
number1 = 21
|
||||||
|
number2 = 12
|
||||||
|
assert(finding_gcd(number1, number2) == 3)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_finding_gcd()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,59 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import math
|
||||||
|
import random
|
||||||
|
|
||||||
|
def finding_prime(number):
|
||||||
|
''' find whether a number is prime in a simple way'''
|
||||||
|
num = abs(number)
|
||||||
|
if num < 4 : return True
|
||||||
|
for x in range(2, num):
|
||||||
|
if num % x == 0:
|
||||||
|
return False
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
|
def finding_prime_sqrt(number):
|
||||||
|
''' find whether a number is prime as soon as it rejects all candidates up to sqrt(n) '''
|
||||||
|
num = abs(number)
|
||||||
|
if num < 4 : return True
|
||||||
|
for x in range(2, int(math.sqrt(num)) + 1):
|
||||||
|
if number % x == 0:
|
||||||
|
return False
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
|
def finding_prime_fermat(number):
|
||||||
|
''' find whether a number is prime with Fermat's theorem, using probabilistic tests '''
|
||||||
|
if number <= 102:
|
||||||
|
for a in range(2, number):
|
||||||
|
if pow(a, number- 1, number) != 1:
|
||||||
|
return False
|
||||||
|
return True
|
||||||
|
else:
|
||||||
|
for i in range(100):
|
||||||
|
a = random.randint(2, number - 1)
|
||||||
|
if pow(a, number - 1, number) != 1:
|
||||||
|
return False
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_finding_prime():
|
||||||
|
number1 = 17
|
||||||
|
number2 = 20
|
||||||
|
assert(finding_prime(number1) == True)
|
||||||
|
assert(finding_prime(number2) == False)
|
||||||
|
assert(finding_prime_sqrt(number1) == True)
|
||||||
|
assert(finding_prime_sqrt(number2) == False)
|
||||||
|
assert(finding_prime_fermat(number1) == True)
|
||||||
|
assert(finding_prime_fermat(number2) == False)
|
||||||
|
print('Tests passed!')
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_finding_prime()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,35 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import math
|
||||||
|
import random
|
||||||
|
import sys
|
||||||
|
from finding_prime import finding_prime_sqrt
|
||||||
|
|
||||||
|
|
||||||
|
def generate_prime(number=3):
|
||||||
|
''' return a n-bit prime '''
|
||||||
|
while 1:
|
||||||
|
p = random.randint(pow(2, number-2), pow(2, number-1)-1)
|
||||||
|
p = 2 * p + 1
|
||||||
|
if finding_prime_sqrt(p):
|
||||||
|
return p
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
if len(sys.argv) < 2:
|
||||||
|
print ("Usage: generate_prime.py number")
|
||||||
|
sys.exit()
|
||||||
|
else:
|
||||||
|
number = int(sys.argv[1])
|
||||||
|
print(generate_prime(number))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -0,0 +1,40 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def find_elem_matrix_bool(m1, value):
|
||||||
|
''' Search an Entry in a Matrix where the Rows and columns are Sorted
|
||||||
|
In this 2D matrix, every row is increasingly sorted from left to right,
|
||||||
|
and every column is increasingly sorted from top to bottom.
|
||||||
|
The runtime is O(m+n). '''
|
||||||
|
found = False
|
||||||
|
row = 0
|
||||||
|
col = len(m1[0]) - 1
|
||||||
|
while row < len(m1) and col >= 0:
|
||||||
|
if m1[row][col] == value:
|
||||||
|
found = True
|
||||||
|
break
|
||||||
|
elif m1[row][col] > value:
|
||||||
|
col-=1
|
||||||
|
else:
|
||||||
|
row+=1
|
||||||
|
return found
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_find_elem_matrix_bool(module_name='this module'):
|
||||||
|
m1 = [[1,2,8,9], [2,4,9,12], [4,7,10,13], [6,8,11,15]]
|
||||||
|
assert(find_elem_matrix_bool(m1,8) == True)
|
||||||
|
assert(find_elem_matrix_bool(m1,3) == False)
|
||||||
|
m2 = [[0]]
|
||||||
|
assert(find_elem_matrix_bool(m2,0) == True)
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_find_elem_matrix_bool()
|
||||||
|
|
@ -0,0 +1,45 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
from fractions import Fraction
|
||||||
|
|
||||||
|
def rounding_floats(number1, places):
|
||||||
|
''' some operations with float()'''
|
||||||
|
return round(number1, places)
|
||||||
|
|
||||||
|
|
||||||
|
def float_to_fractions(number):
|
||||||
|
return Fraction(*number.as_integer_ratio())
|
||||||
|
|
||||||
|
|
||||||
|
def get_denominator(number1, number2):
|
||||||
|
a = Fraction(number1, number2)
|
||||||
|
return a.denominator
|
||||||
|
|
||||||
|
|
||||||
|
def get_numerator(number1, number2):
|
||||||
|
a = Fraction(number1, number2)
|
||||||
|
return a.numerator
|
||||||
|
|
||||||
|
|
||||||
|
def test_testing_floats(module_name='this module'):
|
||||||
|
number1 = 1.25
|
||||||
|
number2 = 1
|
||||||
|
number3 = -1
|
||||||
|
number4 = 5/4
|
||||||
|
number6 = 6
|
||||||
|
assert(rounding_floats(number1, number2) == 1.2)
|
||||||
|
assert(rounding_floats(number1*10, number3) == 10)
|
||||||
|
assert(float_to_fractions(number1) == number4)
|
||||||
|
assert(get_denominator(number2, number6) == number6)
|
||||||
|
assert(get_numerator(number2, number6) == number2)
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_testing_floats()
|
||||||
|
|
||||||
|
|
@ -0,0 +1,32 @@
|
|||||||
|
#!/usr/bin/python
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import numpy as np
|
||||||
|
|
||||||
|
def testing_numpy():
|
||||||
|
''' tests many features of numpy '''
|
||||||
|
ax = np.array([1,2,3])
|
||||||
|
ay = np.array([3,4,5])
|
||||||
|
print(ax)
|
||||||
|
print(ax*2)
|
||||||
|
print(ax+10)
|
||||||
|
print(np.sqrt(ax))
|
||||||
|
print(np.cos(ax))
|
||||||
|
print(ax-ay)
|
||||||
|
print(np.where(ax<2, ax, 10))
|
||||||
|
|
||||||
|
m = np.matrix([ax, ay, ax])
|
||||||
|
print(m)
|
||||||
|
print(m.T)
|
||||||
|
|
||||||
|
grid1 = np.zeros(shape=(10,10), dtype=float)
|
||||||
|
grid2 = np.ones(shape=(10,10), dtype=float)
|
||||||
|
print(grid1)
|
||||||
|
print(grid2)
|
||||||
|
print(grid1[1]+10)
|
||||||
|
print(grid2[:,2]*2)
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
testing_numpy()
|
||||||
|
|
@ -0,0 +1,32 @@
|
|||||||
|
#!/usr/bin/python
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import numpy
|
||||||
|
import time
|
||||||
|
|
||||||
|
def trad_version():
|
||||||
|
t1 = time.time()
|
||||||
|
X = range(10000000)
|
||||||
|
Y = range(10000000)
|
||||||
|
Z = []
|
||||||
|
for i in range(len(X)):
|
||||||
|
Z.append(X[i] + Y[i])
|
||||||
|
return time.time() - t1
|
||||||
|
|
||||||
|
def numpy_version():
|
||||||
|
t1 = time.time()
|
||||||
|
X = numpy.arange(10000000)
|
||||||
|
Y = numpy.arange(10000000)
|
||||||
|
Z = X + Y
|
||||||
|
return time.time() - t1
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
print(trad_version())
|
||||||
|
print(numpy_version())
|
||||||
|
|
||||||
|
|
||||||
|
'''
|
||||||
|
3.23564291
|
||||||
|
0.0714290142059
|
||||||
|
'''
|
@ -0,0 +1,27 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
import random
|
||||||
|
|
||||||
|
def testing_random():
|
||||||
|
''' testing the module random'''
|
||||||
|
values = [1, 2, 3, 4]
|
||||||
|
print(random.choice(values))
|
||||||
|
print(random.choice(values))
|
||||||
|
print(random.choice(values))
|
||||||
|
print(random.sample(values, 2))
|
||||||
|
print(random.sample(values, 3))
|
||||||
|
|
||||||
|
''' shuffle in place '''
|
||||||
|
random.shuffle(values)
|
||||||
|
print(values)
|
||||||
|
|
||||||
|
''' create random integers '''
|
||||||
|
print(random.randint(0,10))
|
||||||
|
print(random.randint(0,10))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
testing_random()
|
||||||
|
|
81
src/examples_in_my_book/general_problems/oop/HashTable.py
Normal file
81
src/examples_in_my_book/general_problems/oop/HashTable.py
Normal file
@ -0,0 +1,81 @@
|
|||||||
|
#!/usr/bin/python3
|
||||||
|
# mari von steinkirch @2013
|
||||||
|
# steinkirch at gmail
|
||||||
|
|
||||||
|
|
||||||
|
class HashTable:
|
||||||
|
''' HashTable class that implements the Map abstract data type with 2 lists'''
|
||||||
|
def __init__(self):
|
||||||
|
self.size = 11
|
||||||
|
self.slots = [None] * self.size
|
||||||
|
self.data = [None] * self.size
|
||||||
|
|
||||||
|
def put(self,key,data):
|
||||||
|
hashvalue = self.hashfunction(key,len(self.slots))
|
||||||
|
|
||||||
|
if self.slots[hashvalue] == None:
|
||||||
|
self.slots[hashvalue] = key
|
||||||
|
self.data[hashvalue] = data
|
||||||
|
else:
|
||||||
|
if self.slots[hashvalue] == key:
|
||||||
|
self.data[hashvalue] = data
|
||||||
|
else:
|
||||||
|
nextslot = self.rehash(hashvalue,len(self.slots))
|
||||||
|
while self.slots[nextslot] != None and \
|
||||||
|
self.slots[nextslot] != key:
|
||||||
|
nextslot = self.rehash(nextslot,len(self.slots))
|
||||||
|
|
||||||
|
if self.slots[nextslot] == None:
|
||||||
|
self.slots[nextslot]=key
|
||||||
|
self.data[nextslot]=data
|
||||||
|
else:
|
||||||
|
self.data[nextslot] = data
|
||||||
|
|
||||||
|
def hashfunction(self,key,size):
|
||||||
|
return key%size
|
||||||
|
|
||||||
|
def rehash(self,oldhash,size):
|
||||||
|
return (oldhash+1)%size
|
||||||
|
|
||||||
|
def get(self,key):
|
||||||
|
startslot = self.hashfunction(key,len(self.slots))
|
||||||
|
|
||||||
|
data = None
|
||||||
|
stop = False
|
||||||
|
found = False
|
||||||
|
position = startslot
|
||||||
|
while self.slots[position] != None and \
|
||||||
|
not found and not stop:
|
||||||
|
if self.slots[position] == key:
|
||||||
|
found = True
|
||||||
|
data = self.data[position]
|
||||||
|
else:
|
||||||
|
position=self.rehash(position,len(self.slots))
|
||||||
|
if position == startslot:
|
||||||
|
stop = True
|
||||||
|
return data
|
||||||
|
|
||||||
|
|
||||||
|
def __getitem__(self,key):
|
||||||
|
return self.get(key)
|
||||||
|
|
||||||
|
def __setitem__(self,key,data):
|
||||||
|
self.put(key,data)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def test_HashTable(module_name='this module'):
|
||||||
|
H = HashTable()
|
||||||
|
H[54]="buffy"
|
||||||
|
H[26]="xander"
|
||||||
|
H[17]="giles"
|
||||||
|
print(H.slots)
|
||||||
|
print(H.data)
|
||||||
|
|
||||||
|
s = 'Tests in {name} have {con}!'
|
||||||
|
print(s.format(name=module_name, con='passed'))
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
test_HashTable()
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user