diff --git a/.gitignore b/.gitignore
index ea5bb31..e5095d8 100644
--- a/.gitignore
+++ b/.gitignore
@@ -34,3 +34,6 @@ nosetests.xml
 .mr.developer.cfg
 .project
 .pydevproject
+
+# PyCharm
+.idea
\ No newline at end of file
diff --git a/.travis.yml b/.travis.yml
new file mode 100644
index 0000000..252e9db
--- /dev/null
+++ b/.travis.yml
@@ -0,0 +1,9 @@
+language: python
+python:
+  - "2.7"
+# command to install dependencies
+install: "pip install -r requirements.txt"
+# command to run tests
+script: nosetests
+notifications:
+  email: false
diff --git a/README.md b/README.md
index e8ab6be..9c798a5 100644
--- a/README.md
+++ b/README.md
@@ -1,10 +1,60 @@
-Python and Algorithms
-======================
+#  Algorithms & Data Structures in Python
 
-This repository contains a comprehensive study of Algorithms and Python, including an "ebook" that I wrote. 
+An introduction to Algorithms & Data Structures in Python, including an ["e-book" I wrote](https://github.com/bt3gl/Python-and-Algorithms-and-Data-Structures/blob/master/book/book_second_edition.pdf).
 
+
 
-In the folder /src/examples_in_my_book/, I made available all the examples and cases I used in my ebook. 
+
+---
+## Source Code:
+
+src/
+
+└── abstract_structures
+
+    ├── heap
+
+    ├── linked_lists
+
+    ├── queues
+
+    └── stacks
+
+└── builtin_structures
+
+    ├── dicts
+
+    ├── lists_and_strings
+
+    ├── numbers
+
+    ├── sets
+
+    └── tuples
+
+└── trees
+
+└── bitwise
+
+└── searching_and_sorting
+
+└── USEFUL
+
+
+----
+## Installation:
+
+The snippets are designed to be used individually. However, If you want  to install all fo the libraries in your [virtualenv](https://coderwall.com/p/8-aeka), do this:
+
+```
+$ pip install -r requirements.txt
+```
+
+----
+## License
+
+
+
+This work is licensed under a [Creative Commons Attribution-ShareAlike 4.0 International License](http://creativecommons.org/licenses/by-sa/4.0/)
 
 
-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.
diff --git a/python_and_algorithms.pdf b/book/book_second_edition.pdf
similarity index 76%
rename from python_and_algorithms.pdf
rename to book/book_second_edition.pdf
index 49bc67f..60ca209 100644
Binary files a/python_and_algorithms.pdf and b/book/book_second_edition.pdf differ
diff --git a/requirements.txt b/requirements.txt
new file mode 100644
index 0000000..7d93487
--- /dev/null
+++ b/requirements.txt
@@ -0,0 +1,13 @@
+Flask==0.10.1
+SQLAlchemy==0.9.7
+bpython==0.13.1
+coverage==3.7.1
+curtsies==0.0.34
+graphviz==0.4.2
+ipython==0.13.2
+matplotlib==1.3.1
+nose==1.3.0
+numpy==1.8.2
+scapy==2.2.0
+scikit-learn==0.14.1
+scipy==0.12.1
\ No newline at end of file
diff --git a/short_phone_interview_problems/balanced.py b/short_phone_interview_problems/balanced.py
new file mode 100644
index 0000000..760316d
--- /dev/null
+++ b/short_phone_interview_problems/balanced.py
@@ -0,0 +1,22 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def balance_par_str_with_stack(str1):
+    i, stack = 0, []
+
+    while i < len(str1):
+        symbol = str1[i]
+        if symbol == "(":
+            stack.append(symbol)
+        elif symbol == ")":
+            stack.pop()
+        i += 1
+    return not stack
+
+
+
+if __name__ == '__main__':
+    print(balance_par_str_with_stack('((()))'))
+    print(balance_par_str_with_stack('(()'))
\ No newline at end of file
diff --git a/short_phone_interview_problems/binary_search.py b/short_phone_interview_problems/binary_search.py
new file mode 100644
index 0000000..c9f7705
--- /dev/null
+++ b/short_phone_interview_problems/binary_search.py
@@ -0,0 +1,50 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+def binary_search(array, value):   
+    last, first = len(array), 0
+    
+    while first < last:
+        mid = (last - first)//2
+        item = array[mid]
+        
+        if item == value:
+            return True
+        
+        elif item < value:
+            last = mid
+        
+        else:
+            first = mid 
+    
+    return False
+
+def binary_search_rec(array, value, first=0, last=None):
+    last = last or len(array)
+    if len(array[first:last]) < 1:
+        return False
+    
+    mid = (last - first)//2
+    if array[mid] == value:
+        return True
+    elif array[mid] < value:
+        return binary_search_rec(array, value, first=first, last=mid)
+    else:
+        return binary_search_rec(array, value, first=mid, last=last)
+
+    
+if __name__ == '__main__':    
+    array = [3, 4, 6, 7, 10, 11, 34, 67, 84]
+    value = 6
+    assert(binary_search(array, value) == True)   
+    assert(binary_search_rec(array, value) == True)  
+    value = 8
+    assert(binary_search(array, value) == False)
+    assert(binary_search_rec(array, value) == False)  
+    array = [8]
+    assert(binary_search(array, value) == True)
+    assert(binary_search_rec(array, value) == True)  
+    array = []
+    assert(binary_search(array, value) == False)
+    assert(binary_search_rec(array, value) == False)  
\ No newline at end of file
diff --git a/short_phone_interview_problems/bst.py b/short_phone_interview_problems/bst.py
new file mode 100644
index 0000000..f908e10
--- /dev/null
+++ b/short_phone_interview_problems/bst.py
@@ -0,0 +1,165 @@
+#!/usr/bin/python
+
+__author__ = "bt3"
+
+from collections import deque
+
+class Node(object):
+
+    def __init__(self, item=None):
+
+        self.item = item
+        self.left = None
+        self.right = None
+
+
+    def _add(self, value):
+        new_node = Node(value)
+        if not self.item:
+            self.item = new_node
+        else:
+            if value > self.item:
+                self.right = self.right and self.right._add(value) or new_node
+            elif value < self.item:
+                self.left = self.left and self.left._add(value) or new_node
+            else:
+                print("BSTs do not support repeated items.")
+        return self 
+
+
+    def _search(self, value):
+        if self.item == value:
+            return True 
+        elif self.left and value < self.item:
+                return self.left._search(value)
+        elif self.right and value > self.item:
+                return self.right._search(value)
+        else:
+            return False
+
+
+    def _isLeaf(self):
+        return not self.right and not self.left
+
+
+    def _printPreorder(self):
+        print self.item
+
+        if self.left:
+            self.left._printPreorder()
+
+        if self.right:
+            self.right._printPreorder()
+
+            
+    def _preorder_array(self):
+        nodes = []
+        if self.item:
+            nodes.append(self.item)
+        if self.left:
+            nodes.extend(self.left._preorder_array())
+        if self.right:
+            nodes.extend(self.right._preorder_array())
+        return nodes
+
+
+
+class BST(object):
+
+    def __init__(self):
+        self.root = None
+
+    def add(self, value):
+        if not self.root:
+            self.root = Node(value)
+        else:
+            self.root._add(value)
+
+    def printPreorder(self):
+        if self.root:
+            self.root._printPreorder()
+
+    def search(self, value):
+        if self.root:
+            return self.root._search(value)
+
+    def preorder_array(self):
+        if self.root:
+            return self.root._preorder_array()
+        else:
+            return 'Tree is empty.'
+
+
+
+
+def BFT(tree):
+    current = tree.root
+    nodes = []
+    queue = deque()
+    queue.append(current)
+
+    while queue:
+        current = queue.popleft()
+        nodes.append(current.item)
+        if current.left:
+            queue.append(current.left)
+        if current.right:
+            queue.append(current.right)
+
+    return nodes
+
+
+def preorder(tree, nodes=None):
+    nodes = nodes or []
+    if tree:
+        nodes.append(tree.item)
+        if tree.left:
+            preorder(tree.left, nodes)
+        if tree.right:
+            preorder(tree.right, nodes)
+    return nodes
+
+
+def postorder(tree, nodes=None):
+    nodes = nodes or []
+    if tree:
+        if tree.left:
+            nodes = postorder(tree.left, nodes)
+        if tree.right:
+            nodes = postorder(tree.right, nodes)
+        nodes.append(tree.item)
+
+    return nodes
+
+
+def inorder(tree, nodes=None):
+    nodes = nodes or []
+    if tree:
+        if tree.left:
+            nodes = inorder(tree.left, nodes)
+        nodes.append(tree.item)
+        if tree.right:
+            nodes = inorder(tree.right, nodes)
+    return nodes
+
+
+        
+        
+if __name__ == '__main__':
+    bst = BST()
+    l = [10, 5, 6, 3, 8, 2, 1, 11, 9, 4]
+    for i in l:
+        bst.add(i)
+
+    print
+    print "Searching for nodes 16 and 6:"
+    print bst.search(16)
+    print bst.search(6)
+
+    print
+    print 'Traversals:'
+    print 'Original:    ', l
+    print 'Preorder:    ', preorder(bst.root)
+    print 'Postorder:   ', postorder(bst.root)
+    print 'Inorder:     ', inorder(bst.root)
+    print 'BSF:         ', BFT(bst)
\ No newline at end of file
diff --git a/short_phone_interview_problems/check_anagram.py b/short_phone_interview_problems/check_anagram.py
new file mode 100644
index 0000000..f6bf749
--- /dev/null
+++ b/short_phone_interview_problems/check_anagram.py
@@ -0,0 +1,38 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+from collections import Counter
+
+def check_if_anagram(word1, word2):
+    counter = Counter()
+    
+    for c in word1:
+        counter[c] += 1
+    
+    for c in word2:
+        counter[c] -= 1
+        
+    for values in counter.values():
+        if values != 0:
+            return False
+
+    return True
+    
+    
+    
+if __name__ == '__main__':
+    word1 = 'abc'
+    word2 = 'bca'
+    assert(check_if_anagram(word1, word2) == True)
+    
+    word2 = 'bcd'
+    assert(check_if_anagram(word1, word2) == False)
+    
+    word1 = ''
+    word2 = ''
+    assert(check_if_anagram(word1, word2) == True)
+    
+    word1 = 'a'
+    word2 = 'a'
+    assert(check_if_anagram(word1, word2) == True)
\ No newline at end of file
diff --git a/short_phone_interview_problems/combination.py b/short_phone_interview_problems/combination.py
new file mode 100644
index 0000000..cdf3ba8
--- /dev/null
+++ b/short_phone_interview_problems/combination.py
@@ -0,0 +1,32 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+def combination(array):
+    if len(array) < 2:
+        return set(array)
+    
+    result = set()
+    for index, item in enumerate(array):
+        new_array = array[:index] + array[index+1:]
+        result.add(item)
+        for perm in combination(new_array):
+            new_item = ''.join(sorted(item + perm))
+            result.add(new_item)
+    
+    return result
+    
+    
+    
+if __name__ == '__main__':
+    array = ['a', 'b', 'c']
+    result = set(['a', 'ac', 'ab', 'abc', 'bc', 'c', 'b']) 
+    assert(combination(array) == result)
+    
+    array = ['']
+    result = set([''])
+    assert(combination(array) == result)
+    
+    array = ['a']
+    result = set(['a'])
+    assert(combination(array) == result)
\ No newline at end of file
diff --git a/short_phone_interview_problems/hash_table.py b/short_phone_interview_problems/hash_table.py
new file mode 100644
index 0000000..70ff62d
--- /dev/null
+++ b/short_phone_interview_problems/hash_table.py
@@ -0,0 +1,45 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+class HashTable(object):
+    def __init__(self, slots=10):
+        self.slots = slots
+        self.table = []
+        self.create_table()
+
+    # Get the slot
+    def hash_key(self, value):
+        return hash(value)%self.slots
+
+    # When creating the table, add list struct 
+    # to each slot
+    def create_table(self):
+        for i in range(self.slots):
+            self.table.append([])
+
+    # Method to add a item in the right slot
+    def add_item(self, value):
+        key = self.hash_key(value)
+        self.table[key].append(value)
+
+    # Aux: print table
+    def print_table(self):
+        for key in range(self.slots):
+            print "Key is {0}, value is {1}.".format(key, self.table[key])
+
+    # Aux: find item
+    def find_item(self, item):
+        item_hash = self.hash_key(item)
+        return item in self.table[item_hash]
+        
+
+if __name__ == '__main__':
+    dic = HashTable(5)
+    for i in range(1, 40, 2):
+        dic.add_item(i)
+
+    dic.print_table()
+    assert(dic.find_item(20) == False)
+    assert(dic.find_item(21) == True)
\ No newline at end of file
diff --git a/short_phone_interview_problems/linked_list.py b/short_phone_interview_problems/linked_list.py
new file mode 100644
index 0000000..0abf3e6
--- /dev/null
+++ b/short_phone_interview_problems/linked_list.py
@@ -0,0 +1,60 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+class Node(object):
+    def __init__(self, value, next=None):
+        self.value = value
+        self.next = next
+        
+
+class LinkedList(object):
+    def __init__(self):
+        self.head = None
+  
+      def _add(self, value):
+        self.head = Node(value, self.head)
+            
+    def _printList(self):
+        node = self.head
+        while node:
+            print node.value
+            node = node.next
+            
+    def _find(self, index):
+        prev = None
+        node = self.head
+        i = 0
+        while node and i < index:
+            prev = node
+            node = node.next
+            i += 1
+        return node, prev, i
+
+    def _delete(self, prev, node):
+        if not prev:
+            self.head = node.next
+        else:
+            prev.next = node.next
+    
+    def deleteNode(self, index):
+        node, prev, i = self._find(index)
+        if index == i:
+            self._delete(prev, node)
+        else:
+            print('Node with index {} not found'.format(index))
+
+    
+
+if __name__ == '__main__':
+    ll = LinkedList()
+    for i in range(1, 5):
+        ll._add(i)
+        
+    print('The list is:')
+    ll._printList()
+     
+    print('The list after deleting node with index 2:')
+    ll.deleteNode(2)
+    ll._printList()
\ No newline at end of file
diff --git a/short_phone_interview_problems/longest_common_prefix.py b/short_phone_interview_problems/longest_common_prefix.py
new file mode 100644
index 0000000..c339ad3
--- /dev/null
+++ b/short_phone_interview_problems/longest_common_prefix.py
@@ -0,0 +1,32 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def longest_common_substring(s1, s2):
+    p1 = 0
+    aux, lcp = '', ''
+    string1 = max(s1, s2)
+    string2 = min(s1, s2)
+
+    while p1 < len(string1):
+        p2 = 0
+        while  p2 < len(string2) and p1+p2 < len(string1):
+            if string1[p1+p2] == string2[p2]:
+                aux += string1[p1+p2]
+            else:
+                if len(lcp) < len(aux):
+                    lcp = aux
+                aux = ''
+            p2 += 1
+        p1 += 1
+
+    return lcp
+             
+    
+    
+if __name__ == '__main__':
+    str1 = 'hasfgeaae'
+    str2 = 'bafgekk'
+    result = 'fge'
+    assert(longest_common_substring(str1, str2) == result)
\ No newline at end of file
diff --git a/short_phone_interview_problems/longest_increasing_subsequence.py b/short_phone_interview_problems/longest_increasing_subsequence.py
new file mode 100644
index 0000000..ca1c2e9
--- /dev/null
+++ b/short_phone_interview_problems/longest_increasing_subsequence.py
@@ -0,0 +1,31 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def longest_increasing_subsequence(seq):
+    result, aux = [], []
+    seq.append(-float('infinity'))
+    
+    for i, value in enumerate(seq[:-1]):
+        aux.append(value)
+        if value > seq[i+1]:
+            if len(result) < len(aux):
+                result = aux[:]
+            aux = []
+    return result
+             
+    
+    
+if __name__ == '__main__':
+    seq = [10, -12, 2, 3, -3, 5, -1, 2, -10]
+    result = [-12, 2, 3]
+    assert(longest_increasing_subsequence(seq) == result)
+    
+    seq = [2]
+    result = [2]
+    assert(longest_increasing_subsequence(seq) == result)
+
+    seq = []
+    result = []
+    assert(longest_increasing_subsequence(seq) == result)
\ No newline at end of file
diff --git a/short_phone_interview_problems/merge_sort.py b/short_phone_interview_problems/merge_sort.py
new file mode 100644
index 0000000..40c3691
--- /dev/null
+++ b/short_phone_interview_problems/merge_sort.py
@@ -0,0 +1,47 @@
+#!/usr/bin/env python
+# AKA: do you believe in magic?
+
+__author__ = "bt3"
+
+def merge_sort(array):
+    if len(array) < 2:
+        return array
+    
+    # divide
+    mid = len(array)//2
+    left = merge_sort(array[:mid])
+    right = merge_sort(array[mid:])
+    
+    # merge
+    result = []
+    i, j = 0, 0
+    
+    while i < len(left) and j < len(right):
+        if left[i] < right[j]:
+            result.append(left[i])
+            i += 1
+        else:
+            result.append(right[j])
+            j+= 1
+    
+    # make sure nothing is left behind
+    if left[i:]:
+        result.extend(left[i:])
+    if right[j:]:
+        result.extend(right[j:])
+    
+    return result
+    
+    
+    
+    
+if __name__ == '__main__':
+    array = [3, 1, 6, 0, 7, 19, 7, 2, 22]
+    sorted = [0, 1, 2, 3, 6, 7, 7, 19, 22]
+    assert(merge_sort(array) == sorted)
+    
+    array = []
+    assert(merge_sort(array) == array)
+
+    array = [1]
+    assert(merge_sort(array) == array)
\ No newline at end of file
diff --git a/short_phone_interview_problems/palindome.py b/short_phone_interview_problems/palindome.py
new file mode 100644
index 0000000..a274417
--- /dev/null
+++ b/short_phone_interview_problems/palindome.py
@@ -0,0 +1,58 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+import string
+
+def sanitize(sentence):
+        array = sentence.lower()
+        array = array.strip()
+        array = array.strip(string.punctuation)
+        return array
+
+def check_if_palindrome(array):
+        if len(array) < 2:
+            return True
+        
+        if array[0] == array[-1]:
+                return check_if_palindrome(array[1:-1])
+        else:
+            return False
+
+def check_if_palindrome_iter(array):        
+    i, j = 0, len(array)-1
+    
+    while i <= j:
+        if array[i] != array[j]:
+            return False
+        i += 1
+        j -= 1
+        
+    return True
+    
+    
+if __name__ == '__main__':
+    sentence = 'hello there'
+    array = sanitize(sentence)
+    assert(check_if_palindrome(array) == False)
+    assert(check_if_palindrome_iter(array) == False)
+    
+    sentence = ''
+    array = sanitize(sentence)
+    assert(check_if_palindrome(array) == True)
+    assert(check_if_palindrome_iter(array) == True)
+    
+    sentence = 'h'
+    array = sanitize(sentence)
+    assert(check_if_palindrome(array) == True)
+    assert(check_if_palindrome_iter(array) == True)
+    
+    sentence = 'Noel sees Leon'
+    array = sanitize(sentence)
+    assert(check_if_palindrome(array) == True)
+    assert(check_if_palindrome_iter(array) == True)
+        
+    sentence = 'Noel sees Leon!'
+    array = sanitize(sentence)
+    assert(check_if_palindrome(array) == True)
+    assert(check_if_palindrome_iter(array) == True)
\ No newline at end of file
diff --git a/short_phone_interview_problems/permutation.py b/short_phone_interview_problems/permutation.py
new file mode 100644
index 0000000..0287c2b
--- /dev/null
+++ b/short_phone_interview_problems/permutation.py
@@ -0,0 +1,31 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def permutation(array):
+    if len(array) < 2:
+        return [array]
+    
+    result = []
+    for index, letter in enumerate(array):
+        new_array = array[:index] + array[index+1:]
+        for perm in permutation(new_array):
+            result.append(letter + perm)
+    
+    return result
+    
+    
+    
+if __name__ == '__main__':
+    word = 'abc'
+    result = ['abc', 'acb', 'bac', 'bca', 'cab', 'cba']
+    assert(permutation(word) == result)
+    
+    word = ''
+    result = ['']
+    assert(permutation(word) == result)
+    
+    word = 'a'
+    result = ['a']
+    assert(permutation(word) == result)
\ No newline at end of file
diff --git a/short_phone_interview_problems/queue.py b/short_phone_interview_problems/queue.py
new file mode 100644
index 0000000..c2ec415
--- /dev/null
+++ b/short_phone_interview_problems/queue.py
@@ -0,0 +1,47 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+class Queue(object):
+    def __init__(self):
+        self.enq = []
+        self.deq = []
+
+    def enqueue(self, item):
+        return self.enq.append(item)
+
+    def deque(self):
+        if not self.deq:
+            while self.enq:
+                self.deq.append(self.enq.pop())
+        return self.deq.pop()
+
+    def peak(self):
+        if not self.deq:
+            while self.enq:
+                self.deq.append(self.enq.pop())
+        if self.deq:
+            return self.deq[-1]
+
+    def size(self):
+        return len(self.enq) + len(self.deq)
+
+    def isempty(self):
+        return not (self.enq + self.deq)
+
+    
+if __name__ == '__main__':
+    q = Queue()
+    for i in range(1,11):
+        q.enqueue(i)
+    print 'Size:',  q.size()
+    print 'Is empty?', q.isempty()
+    print 'Peak: ', q.peak()
+    print
+    print 'Dequeuing...'
+    for i in range(10):
+        print q.deque()
+    print 'Size:',  q.size()
+    print 'Is empty?', q.isempty()
+    print 'Peak: ', q.peak()
\ No newline at end of file
diff --git a/short_phone_interview_problems/quick_sort.py b/short_phone_interview_problems/quick_sort.py
new file mode 100644
index 0000000..2986b57
--- /dev/null
+++ b/short_phone_interview_problems/quick_sort.py
@@ -0,0 +1,31 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+def quick_sort(array):
+    if len(array) < 2:
+        return array
+
+    # partition
+    ipivot = len(array)//2
+    pivot = array[ipivot]
+    new_array = array[:ipivot] + array[ipivot+1:]
+    
+    left = [x for x in new_array if x <= pivot]
+    right = [x for x in new_array if x > pivot]
+
+    return quick_sort(left) + [pivot] + quick_sort(right)
+    
+    
+    
+    
+if __name__ == '__main__':
+    array = [3, 1, 6, 0, 7, 19, 7, 2, 22]
+    sorted = [0, 1, 2, 3, 6, 7, 7, 19, 22]
+    assert(quick_sort(array) == sorted)
+    
+    array = []
+    assert(quick_sort(array) == array)
+
+    array = [1]
+    assert(quick_sort(array) == array)
\ No newline at end of file
diff --git a/short_phone_interview_problems/reverse_str.py b/short_phone_interview_problems/reverse_str.py
new file mode 100644
index 0000000..3109951
--- /dev/null
+++ b/short_phone_interview_problems/reverse_str.py
@@ -0,0 +1,40 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+def reverse_str_inplace(_str):
+    if len(_str) < 2:
+        return _str
+    return _str[-1] + reverse_str(_str[1:-1]) + _str[0]
+    
+
+def reverse_str(_str):
+    result = ''
+    j = len(_str) - 1
+
+    while j >= 0:
+        result += _str[j]
+    
+    return result
+    
+    
+if __name__ == '__main__':
+    _str = ''
+    result = ''
+    assert(reverse_str(_str) == result)
+    assert(reverse_str_inplace(_str) == result)
+
+    _str = 'a'
+    result = 'a'
+    assert(reverse_str(_str) == result)
+    assert(reverse_str_inplace(_str) == result)
+
+    _str = 'abcde'
+    result = 'edcba'
+    assert(reverse_str(_str) == result)
+    assert(reverse_str_inplace(_str) == result)
+
+    _str = 'abcdef'
+    result = 'fedcba'
+    assert(reverse_str(_str) == result)
+    assert(reverse_str_inplace(_str) == result)
\ No newline at end of file
diff --git a/short_phone_interview_problems/stack.py b/short_phone_interview_problems/stack.py
new file mode 100644
index 0000000..07e9e06
--- /dev/null
+++ b/short_phone_interview_problems/stack.py
@@ -0,0 +1,40 @@
+
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+class Stack(object):
+    def __init__(self):
+        self.content = []
+
+    def push(self, value):
+        self.content.append(value)
+
+    def pop(self):
+        if self.content:
+            return self.content.pop()
+        else:
+            return 'Empty List. '
+
+    def size(self):
+        return len(self.content)
+
+    def isEmpty(self):
+        return not bool(self.content)
+
+    def peek(self):
+        if self.content:
+            return self.content[-1]
+        else:
+            print('Stack is empty.')
+
+
+
+if __name__ == '__main__':
+    q = Stack()
+
+    for i in range(10):
+        q.push(i)
+    for i in range(11):
+        print q.pop()
\ No newline at end of file
diff --git a/src/USEFUL/advanced/lru_cache.py b/src/USEFUL/advanced/lru_cache.py
new file mode 100644
index 0000000..11b451e
--- /dev/null
+++ b/src/USEFUL/advanced/lru_cache.py
@@ -0,0 +1,18 @@
+#!/usr/bin/env python3
+
+__author__ = "bt3"
+
+
+from functools import lru_cache
+
+
+@lru_cache(maxsize=20)
+def fib(n):
+    if n < 2:
+        return n
+    return fib(n-1) + fib(n-2)
+
+
+if __name__ == '__main__':
+    print([fib(n) for n in range(10)])
+    print(fib.cache_info())
diff --git a/src/examples_in_my_book/general_problems/dicts/OrderedDict_example.py b/src/USEFUL/basic_examples/example_OrderedDict.py
similarity index 75%
rename from src/examples_in_my_book/general_problems/dicts/OrderedDict_example.py
rename to src/USEFUL/basic_examples/example_OrderedDict.py
index b7dbef1..89d3291 100644
--- a/src/examples_in_my_book/general_problems/dicts/OrderedDict_example.py
+++ b/src/USEFUL/basic_examples/example_OrderedDict.py
@@ -1,17 +1,17 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 from collections import OrderedDict
 
 def  OrderedDict_example():
-    ''' show some examples for OrderedDict ''' 
-    ''' keep the order of insertion. 
+    ''' 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:
diff --git a/src/USEFUL/basic_examples/example_args.py b/src/USEFUL/basic_examples/example_args.py
new file mode 100755
index 0000000..299035b
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_args.py
@@ -0,0 +1,17 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+def simple2(a, *args):
+    print args
+
+def simple(*args):
+    print args
+
+def simple3(**kwargs):
+    print kwargs
+
+
+simple(1, 2, 3)
+simple2(1, 2, 3)
+simple3(x=1, y=2)
diff --git a/src/examples_in_my_book/general_problems/oop/do_benchmark.py b/src/USEFUL/basic_examples/example_benchmark_decorator.py
similarity index 80%
rename from src/examples_in_my_book/general_problems/oop/do_benchmark.py
rename to src/USEFUL/basic_examples/example_benchmark_decorator.py
index bfe97a5..749e403 100644
--- a/src/examples_in_my_book/general_problems/oop/do_benchmark.py
+++ b/src/USEFUL/basic_examples/example_benchmark_decorator.py
@@ -1,8 +1,10 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 import random
+
 def benchmark(func):
     import time
     def wrapper(*args, **kwargs):
@@ -11,15 +13,16 @@ def wrapper(*args, **kwargs):
         print("\t%s" % func.__name__, time.clock()-t)
         return res
     return wrapper
-    
+
+
 @benchmark
 def random_tree(n):
     temp = [n for n in range(n)]
     for i in range(n+1):
         temp[random.choice(temp)] = random.choice(temp)
     return temp
-    
+
 
 if __name__ == '__main__':
-    random_tree(10000)  
+    random_tree(10000)
 
diff --git a/src/USEFUL/basic_examples/example_comp_lists.py b/src/USEFUL/basic_examples/example_comp_lists.py
new file mode 100644
index 0000000..f5c641c
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_comp_lists.py
@@ -0,0 +1,37 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+a = [3, 4, 5, 6, 7]
+
+
+# Filter elements greater than 4
+
+# Bad:
+
+b = []
+for i in a:
+    if i > 4:
+        b.append(i)
+print b
+
+# Good:
+print [i for i in a if i > 4]
+
+# Or:
+print filter(lambda x: x > 4, a)
+
+
+# Add three to all list members:
+
+# Bad
+b = []
+for i in range(len(a)):
+    b.append(a[i] + 3)
+print b
+
+# Good:
+print [i + 3 for i in a]
+
+# Or:
+print map(lambda i: i + 3, a)
\ No newline at end of file
diff --git a/src/examples_in_my_book/general_problems/dicts/Counter_example.py b/src/USEFUL/basic_examples/example_counter.py
similarity index 74%
rename from src/examples_in_my_book/general_problems/dicts/Counter_example.py
rename to src/USEFUL/basic_examples/example_counter.py
index b0f3284..bd233e3 100644
--- a/src/examples_in_my_book/general_problems/dicts/Counter_example.py
+++ b/src/USEFUL/basic_examples/example_counter.py
@@ -1,32 +1,31 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 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 '''
+    ''' it is a dictionary that maps the items to the number of occurrences '''
     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_2)
+    print(seq_counts + seq_counts_2)
     print(seq_counts - seq_counts_2)
-    
+
 if __name__ == '__main__':
     Counter_example()
 
diff --git a/src/USEFUL/basic_examples/example_decorators.py b/src/USEFUL/basic_examples/example_decorators.py
new file mode 100755
index 0000000..a64b299
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_decorators.py
@@ -0,0 +1,42 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+def logger(func):
+    def inner(*args): #1
+        print "Arguments were: {0}".format(args)
+        return func(*args)
+    return inner
+
+@logger
+def foo(x, y):
+    return x+y
+
+print foo(1, 2)
+
+
+def sum(func):
+    s = 0
+    for i in func():
+        s += i
+    return s
+
+@sum
+def interate():
+    a = []
+    for i in range(10):
+        a.append(i)
+    return a
+
+print interate
+
+# which is the same as
+def interate():
+    a = []
+    for i in range(10):
+        a.append(i)
+    return a
+
+print sum(interate)
\ No newline at end of file
diff --git a/src/examples_in_my_book/general_problems/dicts/defaultdict_example.py b/src/USEFUL/basic_examples/example_defaultdict.py
similarity index 68%
rename from src/examples_in_my_book/general_problems/dicts/defaultdict_example.py
rename to src/USEFUL/basic_examples/example_defaultdict.py
index cea9d1c..6db52b7 100644
--- a/src/examples_in_my_book/general_problems/dicts/defaultdict_example.py
+++ b/src/USEFUL/basic_examples/example_defaultdict.py
@@ -1,13 +1,13 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 from collections import defaultdict
 
 def  defaultdict_example():
-    ''' show some examples for defaultdicts ''' 
-    pairs = {('a', 1), ('b',2), ('c',3)}   
-    
+    ''' show some examples for defaultdicts '''
+    pairs = {('a', 1), ('b',2), ('c',3)}
+
     d1 = {}
     for key, value in pairs:
         if key not in d1:
diff --git a/src/USEFUL/basic_examples/example_doctest.py b/src/USEFUL/basic_examples/example_doctest.py
new file mode 100644
index 0000000..3c379bc
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_doctest.py
@@ -0,0 +1,15 @@
+#!/usr/bin/python
+
+__author__ = "bt3"
+
+'''
+The doctest module automatically runs any statement beginning with >>>
+and compares the following line with the output from the interpreter.
+
+>>> 1 == 1
+False
+'''
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/examples_in_my_book/general_problems/numbers/testing_floats.py b/src/USEFUL/basic_examples/example_fractions.py
similarity index 88%
rename from src/examples_in_my_book/general_problems/numbers/testing_floats.py
rename to src/USEFUL/basic_examples/example_fractions.py
index 5734170..9bbff22 100644
--- a/src/examples_in_my_book/general_problems/numbers/testing_floats.py
+++ b/src/USEFUL/basic_examples/example_fractions.py
@@ -1,22 +1,22 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 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)
@@ -34,7 +34,7 @@ def test_testing_floats(module_name='this module'):
     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'))
 
diff --git a/src/USEFUL/basic_examples/example_generator.py b/src/USEFUL/basic_examples/example_generator.py
new file mode 100644
index 0000000..8256b90
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_generator.py
@@ -0,0 +1,27 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def interate(x):
+    for i in range(x):
+        yield i
+
+def gen1():
+    a =  interate(10)
+    print a.next()
+    print a.next()
+    print a.next()
+
+
+def reverse(data):
+    for i in range(len(data)-1, -1, -1):
+        yield data[i]
+
+def gen2():
+    for c in reverse('awesome'):
+        print c
+
+if __name__ == '__main__':
+    gen1()
+    gen2()
diff --git a/src/USEFUL/basic_examples/example_lambda.py b/src/USEFUL/basic_examples/example_lambda.py
new file mode 100644
index 0000000..34ddec3
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_lambda.py
@@ -0,0 +1,7 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+test = lambda x: x**2
+print test(3)
\ No newline at end of file
diff --git a/src/USEFUL/basic_examples/example_logging.py b/src/USEFUL/basic_examples/example_logging.py
new file mode 100644
index 0000000..5d483fe
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_logging.py
@@ -0,0 +1,21 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+import logging
+
+LOG_FILENAME = 'logging_example.out'
+logging.basicConfig(filename=LOG_FILENAME,
+                    level=logging.DEBUG,
+                    )
+
+logging.debug('This message should go to the log file')
+
+f = open(LOG_FILENAME, 'rt')
+try:
+    body = f.read()
+finally:
+    f.close()
+
+print 'FILE:'
+print body
\ No newline at end of file
diff --git a/src/examples_in_my_book/general_problems/numbers/testing_numpy.py b/src/USEFUL/basic_examples/example_numpy.py
similarity index 54%
rename from src/examples_in_my_book/general_problems/numbers/testing_numpy.py
rename to src/USEFUL/basic_examples/example_numpy.py
index bbd3fae..a2a90a6 100644
--- a/src/examples_in_my_book/general_problems/numbers/testing_numpy.py
+++ b/src/USEFUL/basic_examples/example_numpy.py
@@ -1,7 +1,9 @@
-#!/usr/bin/python
-# mari von steinkirch @2013
-# steinkirch at gmail
 
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+import time
 import numpy as np
 
 def testing_numpy():
@@ -15,11 +17,11 @@ def testing_numpy():
     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)
@@ -27,6 +29,32 @@ def testing_numpy():
     print(grid1[1]+10)
     print(grid2[:,2]*2)
 
+
+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 = np.arange(10000000)
+    Y = np.arange(10000000)
+    Z = X + Y
+    return time.time() - t1
+
+
+
 if __name__ == '__main__':
     testing_numpy()
+    print(trad_version())
+    print(numpy_version())
+
 
+'''
+3.23564291
+0.0714290142059
+'''
diff --git a/src/USEFUL/basic_examples/example_open_files.py b/src/USEFUL/basic_examples/example_open_files.py
new file mode 100644
index 0000000..28d03e6
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_open_files.py
@@ -0,0 +1,10 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+filename = raw_input('Enter a file name: ')
+try:
+    f = open(filename, "r")
+except:
+    print 'There is no file named', filename
+
diff --git a/src/examples_in_my_book/general_problems/modules/export_pickle.py b/src/USEFUL/basic_examples/example_pickle.py
similarity index 51%
rename from src/examples_in_my_book/general_problems/modules/export_pickle.py
rename to src/USEFUL/basic_examples/example_pickle.py
index b26bde8..2a863ee 100644
--- a/src/examples_in_my_book/general_problems/modules/export_pickle.py
+++ b/src/USEFUL/basic_examples/example_pickle.py
@@ -1,33 +1,58 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 import pickle
 
+def import_pickle(filename):
+    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)
+
+
+
 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)	
-			
+            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()
+    test_import_pickle()
diff --git a/src/USEFUL/basic_examples/example_queue.py b/src/USEFUL/basic_examples/example_queue.py
new file mode 100755
index 0000000..b51548f
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_queue.py
@@ -0,0 +1,13 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+import Queue
+
+q = Queue.Queue()
+
+for i in range(10):
+    q.put(i)
+
+for i in range(10):
+    print q.get(i)
diff --git a/src/examples_in_my_book/general_problems/numbers/testing_random.py b/src/USEFUL/basic_examples/example_random.py
similarity index 86%
rename from src/examples_in_my_book/general_problems/numbers/testing_random.py
rename to src/USEFUL/basic_examples/example_random.py
index dae8767..e4dc921 100644
--- a/src/examples_in_my_book/general_problems/numbers/testing_random.py
+++ b/src/USEFUL/basic_examples/example_random.py
@@ -1,6 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 import random
 
@@ -12,11 +12,11 @@ def testing_random():
     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))
diff --git a/src/examples_in_my_book/general_problems/dicts/setdeault_example.py b/src/USEFUL/basic_examples/example_setdefault.py
similarity index 90%
rename from src/examples_in_my_book/general_problems/dicts/setdeault_example.py
rename to src/USEFUL/basic_examples/example_setdefault.py
index 55dbfd4..6ad5c56 100644
--- a/src/examples_in_my_book/general_problems/dicts/setdeault_example.py
+++ b/src/USEFUL/basic_examples/example_setdefault.py
@@ -1,6 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 
 def usual_dict(dict_data):
@@ -28,7 +28,7 @@ def test_setdef(module_name='this module'):
                ('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'))
 
diff --git a/src/examples_in_my_book/general_problems/sets/set_operations_with_lists.py b/src/USEFUL/basic_examples/example_sets.py
similarity index 92%
rename from src/examples_in_my_book/general_problems/sets/set_operations_with_lists.py
rename to src/USEFUL/basic_examples/example_sets.py
index f836d21..ef621d4 100644
--- a/src/examples_in_my_book/general_problems/sets/set_operations_with_lists.py
+++ b/src/USEFUL/basic_examples/example_sets.py
@@ -1,6 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 def difference(l1):
     """ return the list with duplicate elements removed """
diff --git a/src/USEFUL/basic_examples/example_socket.py b/src/USEFUL/basic_examples/example_socket.py
new file mode 100644
index 0000000..0810498
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_socket.py
@@ -0,0 +1,35 @@
+#!/usr/bin/env python
+
+
+__author__ = "bt3"
+
+
+import socket
+
+
+def netcat(hostname, port, content):
+
+    s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
+
+    s.connect((hostname, port))
+    s.sendall(content)
+
+    adata = []
+    while 1:
+        data = s.recv(1024)
+        if data == '':
+            break
+        adata.append(data)
+
+    s.close()
+    return adata
+
+
+
+if __name__ == '__main__':
+
+    PORT = 12345
+    HOSTNAME = '54.209.5.48'
+
+    message = netcat(HOSTNAME, PORT, 'Hello!')[1]
+    print message
\ No newline at end of file
diff --git a/src/USEFUL/basic_examples/example_string_format.py b/src/USEFUL/basic_examples/example_string_format.py
new file mode 100644
index 0000000..b13add5
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_string_format.py
@@ -0,0 +1,11 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+foo = 'foo'
+bar = 'bar'
+
+print '%s%s' % (foo, bar) # It is OK
+print '{0}{1}'.format(foo, bar) # It is better
+print '{foo}{bar}'.format(foo=foo, bar=bar) # It is best
\ No newline at end of file
diff --git a/src/USEFUL/basic_examples/example_subprocess.py b/src/USEFUL/basic_examples/example_subprocess.py
new file mode 100644
index 0000000..b845ca4
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_subprocess.py
@@ -0,0 +1,8 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+import subprocess,os
+
+os.system('ls')
+subprocess.call(['ls', '-1'], shell=True)
diff --git a/src/USEFUL/basic_examples/example_telnet.py b/src/USEFUL/basic_examples/example_telnet.py
new file mode 100644
index 0000000..2c46254
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_telnet.py
@@ -0,0 +1,22 @@
+#!/usr/bin/env python
+
+
+__author__ = "bt3"
+
+
+from telnetlib import Telnet
+
+
+# examples of telnet connections
+PORT = 12345
+HOST = '54.209.5.48'
+
+# creating connection
+tn = Telnet(HOST ,PORT)
+
+# reading input
+msg_in2 = tn.read_all().dec_msg()
+tn.read_until(b'psifer text: ')
+
+# writing outputs
+tn.write(msg.encode() + b'\n')
diff --git a/src/USEFUL/basic_examples/example_testing.py b/src/USEFUL/basic_examples/example_testing.py
new file mode 100644
index 0000000..5e900f2
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_testing.py
@@ -0,0 +1,46 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+def test_doctest():
+    '''
+    >>> 1 == 1
+    False
+    '''
+    pass
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
+#####
+
+import unittest
+
+class BasicsTestCase(unittest.TestCase):
+
+    def test_find_name(self):
+        self.assertTrue(1 == 1)
+        self.assertFalse(1 == 2)
+
+if __name__ == '__main__':
+    unittest.main()
+
+
+
+#####
+
+# content of test_example.py, run with $ py.test
+#
+# run tests over the directory
+# $ nosetest
+
+
+def func(x):
+    return x + 1
+
+def test_answer():
+    assert func(3) == 4
+
diff --git a/src/USEFUL/basic_examples/example_threads.py b/src/USEFUL/basic_examples/example_threads.py
new file mode 100644
index 0000000..8d44859
--- /dev/null
+++ b/src/USEFUL/basic_examples/example_threads.py
@@ -0,0 +1,16 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+import threading
+
+def worker(num):
+    """thread worker function"""
+    print 'Worker: %s' % num
+    return
+
+threads = []
+for i in range(5):
+    t = threading.Thread(target=worker, args=(i,))
+    threads.append(t)
+    t.start()
\ No newline at end of file
diff --git a/src/examples_in_my_book/general_problems/modules/using_time_module.py b/src/USEFUL/basic_examples/example_time.py
similarity index 73%
rename from src/examples_in_my_book/general_problems/modules/using_time_module.py
rename to src/USEFUL/basic_examples/example_time.py
index 027bbfe..78bada7 100644
--- a/src/examples_in_my_book/general_problems/modules/using_time_module.py
+++ b/src/USEFUL/basic_examples/example_time.py
@@ -1,11 +1,12 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/python
+
+__author__ = "bt3"
+
+''' a simple example of how to time a function '''
 
 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):
diff --git a/src/examples_in_my_book/adt/heap/__init__.py b/src/USEFUL/dynamic_programming/__init__.py
similarity index 100%
rename from src/examples_in_my_book/adt/heap/__init__.py
rename to src/USEFUL/dynamic_programming/__init__.py
diff --git a/src/examples_in_my_book/dynamic_programming/memo.py b/src/USEFUL/dynamic_programming/memo.py
similarity index 90%
rename from src/examples_in_my_book/dynamic_programming/memo.py
rename to src/USEFUL/dynamic_programming/memo.py
index 7391a6c..adff8e2 100644
--- a/src/examples_in_my_book/dynamic_programming/memo.py
+++ b/src/USEFUL/dynamic_programming/memo.py
@@ -1,6 +1,6 @@
 #!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+
+__author__ = "bt3"
 
 
 from functools import wraps
@@ -20,7 +20,7 @@ def wrap(*args):
 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)   
+    return find_fibonacci_seq_rec(n - 1) + find_fibonacci_seq_rec(n - 2)
 
 def test_memo():
     n = 50
@@ -31,9 +31,9 @@ def test_memo():
 
 if __name__ == '__main__':
     test_memo()
-    
-    
-   
+
+
+
 
 
 
diff --git a/src/examples_in_my_book/dynamic_programming/memoized_longest_inc_subseq.py b/src/USEFUL/dynamic_programming/memoized_longest_inc_subseq.py
similarity index 89%
rename from src/examples_in_my_book/dynamic_programming/memoized_longest_inc_subseq.py
rename to src/USEFUL/dynamic_programming/memoized_longest_inc_subseq.py
index 7547caa..4e6434c 100644
--- a/src/examples_in_my_book/dynamic_programming/memoized_longest_inc_subseq.py
+++ b/src/USEFUL/dynamic_programming/memoized_longest_inc_subseq.py
@@ -1,7 +1,6 @@
 #!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
 
+__author__ = "bt3"
 
 from itertools import combinations
 from bisect import bisect
@@ -14,7 +13,7 @@ def naive_longest_inc_subseq(seq):
         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 '''
@@ -24,8 +23,8 @@ def longest_inc_subseq1(seq):
         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)
@@ -51,17 +50,17 @@ def L(cur):
 @benchmark
 def test_naive_longest_inc_subseq():
     print(naive_longest_inc_subseq(s1))
-    
+
 benchmark
-def test_longest_inc_subseq1():   
+def test_longest_inc_subseq1():
     print(longest_inc_subseq1(s1))
 
 @benchmark
-def test_longest_inc_subseq2():  
+def test_longest_inc_subseq2():
     print(longest_inc_subseq2(s1))
- 
+
 @benchmark
-def test_memoized_longest_inc_subseq(): 
+def test_memoized_longest_inc_subseq():
     print(memoized_longest_inc_subseq(s1))
 
 
@@ -73,9 +72,9 @@ def test_memoized_longest_inc_subseq():
     test_longest_inc_subseq1()
     test_longest_inc_subseq2()
     test_memoized_longest_inc_subseq()
-    
-    
-   
+
+
+
 
 
 
diff --git a/src/examples_in_my_book/general_problems/oop/ShapeClass.py b/src/USEFUL/oop/ShapeClass.py
similarity index 100%
rename from src/examples_in_my_book/general_problems/oop/ShapeClass.py
rename to src/USEFUL/oop/ShapeClass.py
diff --git a/src/examples_in_my_book/adt/linked_lists/__init__.py b/src/USEFUL/oop/__init__.py
similarity index 100%
rename from src/examples_in_my_book/adt/linked_lists/__init__.py
rename to src/USEFUL/oop/__init__.py
diff --git a/src/examples_in_my_book/general_problems/modules/change_ext_file.py b/src/USEFUL/useful_with_files/change_ext_file.py
similarity index 64%
rename from src/examples_in_my_book/general_problems/modules/change_ext_file.py
rename to src/USEFUL/useful_with_files/change_ext_file.py
index e5b9d7a..f114c2e 100644
--- a/src/examples_in_my_book/general_problems/modules/change_ext_file.py
+++ b/src/USEFUL/useful_with_files/change_ext_file.py
@@ -1,6 +1,8 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+
+__author__ = "bt3"
+
 
 import os
 import sys
@@ -12,12 +14,12 @@ def change_file_ext():
         print("Usage: change_ext.py filename.old_ext 'new_ext'")
         sys.exit()
 
-    name = os.path.splitext(sys.argv[1])[0] + "." + sys.argv[2] 
+    name = os.path.splitext(sys.argv[1])[0] + "." + sys.argv[2]
     print (name)
-	
+
     try:
-        shutil.copyfile(sys.argv[1], name)			
-    except OSError as err:	
+        shutil.copyfile(sys.argv[1], name)
+    except OSError as err:
         print (err)
 
 
diff --git a/src/examples_in_my_book/general_problems/strings/count_unique_words.py b/src/USEFUL/useful_with_files/count_unique_words_files.py
old mode 100644
new mode 100755
similarity index 52%
rename from src/examples_in_my_book/general_problems/strings/count_unique_words.py
rename to src/USEFUL/useful_with_files/count_unique_words_files.py
index 9ab81a2..e1e3de0
--- a/src/examples_in_my_book/general_problems/strings/count_unique_words.py
+++ b/src/USEFUL/useful_with_files/count_unique_words_files.py
@@ -1,24 +1,28 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/python
 
+__author__ = "bt3"
+
+
+import collections
 import string
 import sys
 
-def count_unique_word():
-    ''' list every word and number of times in alphabetical order for input files ''' 
-    words = {} # create an empty dictionary
-    strip = string.whitespace + string.punctuation + string.digits + "\"'" 
+def count_unique_word_file():
+    if len(sys.argv) < 2:
+        print "Usage: python count_unique_word.py NAMEFILE"
+
+    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 line in file:
                 for word in line.lower().split():
                     word = word.strip(strip)
                     if len(word) > 2:
-                        words[word] = words.get(word,0) +1
+                        words[word] = +1
     for word in sorted(words):
         print("'{0}' occurs {1} times.".format(word, words[word]))
 
 
-count_unique_word()
-        
+if __name__ == '__main__':
+    count_unique_word_file()
\ No newline at end of file
diff --git a/src/USEFUL/useful_with_files/count_unique_words_frequency.py b/src/USEFUL/useful_with_files/count_unique_words_frequency.py
new file mode 100755
index 0000000..14162d5
--- /dev/null
+++ b/src/USEFUL/useful_with_files/count_unique_words_frequency.py
@@ -0,0 +1,15 @@
+#!/usr/bin/python
+
+__author__ = "bt3"
+
+
+import collections
+import sys
+
+def count_unique_word_freq():
+        return collections.Counter(\
+            sys.stdin.read().lower().split()).most_common(n)
+
+
+if __name__ == '__main__':
+    count_unique_word_freq()
\ No newline at end of file
diff --git a/src/examples_in_my_book/general_problems/modules/grep_word_from_files.py b/src/USEFUL/useful_with_files/grep_word_from_files.py
similarity index 87%
rename from src/examples_in_my_book/general_problems/modules/grep_word_from_files.py
rename to src/USEFUL/useful_with_files/grep_word_from_files.py
index 6ef2a81..7dfa064 100644
--- a/src/examples_in_my_book/general_problems/modules/grep_word_from_files.py
+++ b/src/USEFUL/useful_with_files/grep_word_from_files.py
@@ -1,6 +1,7 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+
+__author__ = "bt3"
 
 import sys
 
@@ -13,7 +14,7 @@ def grep_word_from_files():
                 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...]")
diff --git a/src/examples_in_my_book/general_problems/modules/remove_blank_lines.py b/src/USEFUL/useful_with_files/remove_blank_lines.py
similarity index 91%
rename from src/examples_in_my_book/general_problems/modules/remove_blank_lines.py
rename to src/USEFUL/useful_with_files/remove_blank_lines.py
index 4576434..e9bad3f 100644
--- a/src/examples_in_my_book/general_problems/modules/remove_blank_lines.py
+++ b/src/USEFUL/useful_with_files/remove_blank_lines.py
@@ -1,6 +1,7 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+
+__author__ = "bt3"
 
 
 
@@ -46,8 +47,8 @@ def remove_blank_lines():
         lines = read_data(filename)
         if lines:
             write_data(lines, filename)
-            
-            
+
+
 if __name__ == '__main__':
     remove_blank_lines()
 
diff --git a/src/abstract_structures/HashTable.py b/src/abstract_structures/HashTable.py
new file mode 100755
index 0000000..2dad275
--- /dev/null
+++ b/src/abstract_structures/HashTable.py
@@ -0,0 +1,41 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+class HashTable(object):
+    def __init__(self, slots=10):
+        self.slots = slots
+        self.table = []
+        self.create_table()
+
+    def hash_key(self, value):
+        return hash(value)%self.slots
+
+    def create_table(self):
+        for i in range(self.slots):
+            self.table.append([])
+
+    def add_item(self, value):
+        key = self.hash_key(value)
+        self.table[key].append(value)
+
+    def print_table(self):
+        for key in range(len(self.table)):
+            print "Key is %s, value is %s." %(key, self.table[key])
+
+    def find_item(self, item):
+        pos = self.hash_key(item)
+        if item in self.table[pos]:
+            return True
+        else:
+            return False
+
+if __name__ == '__main__':
+    dic = HashTable(5)
+    for i in range(1, 40, 2):
+        dic.add_item(i)
+
+    dic.print_table()
+    assert(dic.find_item(20) == False)
+    assert(dic.find_item(21) == True)
diff --git a/src/abstract_structures/Queue.py b/src/abstract_structures/Queue.py
new file mode 100755
index 0000000..eff7e91
--- /dev/null
+++ b/src/abstract_structures/Queue.py
@@ -0,0 +1,47 @@
+#!/usr/bin/env python
+# Time: 5 min
+
+__author__ = "bt3"
+
+
+class Queue(object):
+    def __init__(self):
+        self.enq = []
+        self.deq = []
+
+    def enqueue(self, item):
+        return self.enq.append(item)
+
+    def deque(self):
+        if not self.deq:
+            while self.enq:
+                self.deq.append(self.enq.pop())
+        return self.deq.pop()
+
+    def peak(self):
+        if not self.deq:
+            while self.enq:
+                self.deq.append(self.enq.pop())
+        if self.deq:
+            return self.deq[-1]
+
+    def size(self):
+        return len(self.enq) + len(self.deq)
+
+    def isempty(self):
+        return not (self.enq + self.deq)
+
+if __name__ == '__main__':
+    q = Queue()
+    for i in range(1,11):
+        q.enqueue(i)
+    print 'Size:',  q.size()
+    print 'Is empty?', q.isempty()
+    print 'Peak: ', q.peak()
+    print
+    print 'Dequeuing...'
+    for i in range(10):
+        print q.deque()
+    print 'Size:',  q.size()
+    print 'Is empty?', q.isempty()
+    print 'Peak: ', q.peak()
\ No newline at end of file
diff --git a/src/abstract_structures/Stack.py b/src/abstract_structures/Stack.py
new file mode 100755
index 0000000..ba36110
--- /dev/null
+++ b/src/abstract_structures/Stack.py
@@ -0,0 +1,63 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+class Stack(object):
+    def __init__(self):
+        self.content = []
+        self.min_array = []
+        self.min = float('inf')
+
+    def push(self, value):
+        if value < self.min:
+            self.min = value
+
+        self.content.append(value)
+        self.min_array.append(self.min)
+
+    def pop(self):
+        if self.content:
+            value = self.content.pop()
+            self.min_array.pop()
+            if self.min_array:
+                self.min = self.min_array[-1]
+            return value
+        else:
+            return 'Empty List. '
+
+    def find_min(self):
+        if self.min_array:
+            return self.min_array[-1]
+        else:
+            return 'No min value for empty list.'
+
+    def size(self):
+        return len(self.content)
+
+    def isEmpty(self):
+        return not bool(self.content)
+
+    def peek(self):
+        if self.content:
+            return self.content[-1]
+        else:
+            print('Stack is empty.')
+
+
+    def __repr__(self):
+        return '{}'.format(self.content)
+
+
+if __name__ == '__main__':
+    q = Stack()
+
+    for i in range(15,20):
+        q.push(i)
+    for i in range(10,5,-1):
+        q.push(i)
+
+
+
+    for i in range(1, 13):
+        print q.pop(), q.find_min()
\ No newline at end of file
diff --git a/src/abstract_structures/__init__.py b/src/abstract_structures/__init__.py
new file mode 100755
index 0000000..be4c726
--- /dev/null
+++ b/src/abstract_structures/__init__.py
@@ -0,0 +1 @@
+__all__=["hash_tables", "heap", "linked_list", "queues", "stacks"]
\ No newline at end of file
diff --git a/src/examples_in_my_book/adt/queues/__init__.py b/src/abstract_structures/heap/__init__.py
similarity index 100%
rename from src/examples_in_my_book/adt/queues/__init__.py
rename to src/abstract_structures/heap/__init__.py
diff --git a/src/examples_in_my_book/adt/heap/find_N_largest_smallest_items_seq.py b/src/abstract_structures/heap/find_N_largest_smallest_items_seq.py
similarity index 94%
rename from src/examples_in_my_book/adt/heap/find_N_largest_smallest_items_seq.py
rename to src/abstract_structures/heap/find_N_largest_smallest_items_seq.py
index 11bde95..18042fe 100644
--- a/src/examples_in_my_book/adt/heap/find_N_largest_smallest_items_seq.py
+++ b/src/abstract_structures/heap/find_N_largest_smallest_items_seq.py
@@ -1,13 +1,13 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 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)
@@ -18,7 +18,7 @@ def find_smallest_items_seq_heap(seq):
     ''' 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)
@@ -26,7 +26,7 @@ def find_smallest_items_seq(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:]
@@ -41,7 +41,7 @@ def test_find_N_largest_smallest_items_seq(module_name='this module'):
     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'))
 
diff --git a/src/examples_in_my_book/adt/heap/heapify.py b/src/abstract_structures/heap/heapify.py
similarity index 90%
rename from src/examples_in_my_book/adt/heap/heapify.py
rename to src/abstract_structures/heap/heapify.py
index 8c39c0e..aa1d86b 100644
--- a/src/examples_in_my_book/adt/heap/heapify.py
+++ b/src/abstract_structures/heap/heapify.py
@@ -1,13 +1,13 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 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)
 
@@ -19,12 +19,12 @@ def left_child(self, i):
 
     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) 
+        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:
@@ -44,7 +44,6 @@ 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()
diff --git a/src/examples_in_my_book/adt/heap/merge_sorted_seqs.py b/src/abstract_structures/heap/merge_sorted_seqs.py
similarity index 76%
rename from src/examples_in_my_book/adt/heap/merge_sorted_seqs.py
rename to src/abstract_structures/heap/merge_sorted_seqs.py
index 861ca07..1d211b2 100644
--- a/src/examples_in_my_book/adt/heap/merge_sorted_seqs.py
+++ b/src/abstract_structures/heap/merge_sorted_seqs.py
@@ -1,6 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 import heapq
 
@@ -19,9 +19,7 @@ def test_merge_sorted_seq(module_name='this module'):
     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__':
diff --git a/src/examples_in_my_book/adt/heap/priority_queue.py b/src/abstract_structures/heap/priority_queue.py
similarity index 86%
rename from src/examples_in_my_book/adt/heap/priority_queue.py
rename to src/abstract_structures/heap/priority_queue.py
index 605f78d..5aed910 100644
--- a/src/examples_in_my_book/adt/heap/priority_queue.py
+++ b/src/abstract_structures/heap/priority_queue.py
@@ -1,6 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 import heapq
 
@@ -9,11 +9,11 @@ class PriorityQueue(object):
     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)) 
+        heapq.heappush(self._queue, (-priority, self._index, item))
         self._index += 1
-    
+
     def pop(self):
         return heapq.heappop(self._queue)[-1]
 
@@ -32,7 +32,6 @@ def test_PriorityQueue():
     q.push(Item('test2'), 4)
     q.push(Item('test3'), 3)
     assert(str(q.pop()) == "Item('test2')")
-    print('Tests passed!'.center(20,'*'))
 
 
 if __name__ == '__main__':
diff --git a/src/examples_in_my_book/adt/stacks/__init__.py b/src/abstract_structures/linked_list/__init__.py
similarity index 100%
rename from src/examples_in_my_book/adt/stacks/__init__.py
rename to src/abstract_structures/linked_list/__init__.py
diff --git a/src/abstract_structures/linked_list/circular_ll.py b/src/abstract_structures/linked_list/circular_ll.py
new file mode 100644
index 0000000..fdeb026
--- /dev/null
+++ b/src/abstract_structures/linked_list/circular_ll.py
@@ -0,0 +1,55 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' implement a function to see whether a linked list is circular.
+    To implement this, we just need two pointers with different
+    paces (for example, one goes twice faster)'''
+
+from linked_list_fifo import LinkedListFIFO
+from node import Node
+
+
+class cicularLinkedListFIFO(LinkedListFIFO):
+    def _add(self, value):
+        self.length += 1
+        node = Node(value, self.head)
+        if self.tail:
+            self.tail.pointer = node
+        self.tail = node
+
+
+
+
+def isCircularll(ll):
+    p1 = ll.head
+    p2 = ll.head
+
+    while p2:
+        try:
+            p1 = p1.pointer
+            p2 = p2.pointer.pointer
+        except:
+            break
+
+        if p1 == p2:
+            return True
+    return False
+
+
+
+if __name__ == '__main__':
+
+    ll = LinkedListFIFO()
+    for i in range(10):
+        ll.addNode(i)
+    ll._printList()
+
+    print(isCircularll(ll))
+
+    lcirc = cicularLinkedListFIFO()
+    for i in range(10):
+        lcirc.addNode(i)
+    print(isCircularll(lcirc))
+
diff --git a/src/abstract_structures/linked_list/double_linked_list_fifo.py b/src/abstract_structures/linked_list/double_linked_list_fifo.py
new file mode 100644
index 0000000..094b283
--- /dev/null
+++ b/src/abstract_structures/linked_list/double_linked_list_fifo.py
@@ -0,0 +1,81 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' Implement a double-linked list, which is very simple, we just need inherits
+from a Linked List Class and  add an attribute for previous.'''
+
+from linked_list_fifo import LinkedListFIFO
+
+
+class dNode(object):
+    def __init__(self, value=None, pointer=None, previous=None):
+        self.value = value
+        self.pointer = pointer
+        self.previous = previous
+
+
+class dLinkList(LinkedListFIFO):
+
+    def printListInverse(self):
+        node = self.tail
+        while node:
+            print(node.value)
+            try:
+                node = node.previous
+            except:
+                break
+
+    def _add(self, value):
+        self.length += 1
+        node = dNode(value)
+        if self.tail:
+            self.tail.pointer = node
+            node.previous = self.tail
+        self.tail = node
+
+    def _delete(self, node):
+        self.length -= 1
+        node.previous.pointer = node.pointer
+        if not node.pointer:
+            self.tail = node.previous
+
+    def _find(self, index):
+        node = self.head
+        i = 0
+        while node and i < index:
+            node = node.pointer
+            i += 1
+        return node, i
+
+    # delete nodes in general
+    def deleteNode(self, index):
+        if not self.head or not self.head.pointer:
+            self._deleteFirst()
+        else:
+            node, i = self._find(index)
+            if i == index:
+                self._delete(node)
+            else:
+                print('Node with index {} not found'.format(index))
+
+
+if __name__ == '__main__':
+
+    from collections import Counter
+
+    ll = dLinkList()
+    for i in range(1, 5):
+        ll.addNode(i)
+    print('Printing the list...')
+    ll._printList()
+    print('Now, printing the list inversely...')
+    ll.printListInverse()
+    print('The list after adding node with value 15')
+    ll._add(15)
+    ll._printList()
+    print("The list after deleting everything...")
+    for i in range(ll.length-1, -1, -1):
+        ll.deleteNode(i)
+    ll._printList()
+
diff --git a/src/abstract_structures/linked_list/find_kth_from_the_end.py b/src/abstract_structures/linked_list/find_kth_from_the_end.py
new file mode 100644
index 0000000..8fd0cba
--- /dev/null
+++ b/src/abstract_structures/linked_list/find_kth_from_the_end.py
@@ -0,0 +1,42 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' Find the mth-to-last element of a linked list.
+    One option is having two pointers, separated by m. P1 start at the roots
+    (p1 = self.root) and p2 is m-behinf pointer, which is created when p1 is at m.
+    When p1 reach the end, p2 is the node. '''
+
+from linked_list_fifo import LinkedListFIFO
+from node import Node
+
+
+class LinkedListFIFO_find_kth(LinkedListFIFO):
+
+
+    def find_kth_to_last(self, k):
+        p1, p2 = self.head, self.head
+        i = 0
+        while p1:
+            if i > k:
+                try:
+                    p2 = p2.pointer
+                except:
+                    break
+            p1 = p1.pointer
+            i += 1
+        return p2.value
+
+
+
+if __name__ == '__main__':
+    ll = LinkedListFIFO_find_kth()
+    for i in range(1, 11):
+        ll.addNode(i)
+    print('The Linked List:')
+    print(ll._printList())
+    k = 3
+    k_from_last = ll.find_kth_to_last(k)
+    print("The %dth element to the last of the LL of size %d is %d" %(k, ll.length, k_from_last))
+
diff --git a/src/abstract_structures/linked_list/linked_list_fifo.py b/src/abstract_structures/linked_list/linked_list_fifo.py
new file mode 100644
index 0000000..9a983a9
--- /dev/null
+++ b/src/abstract_structures/linked_list/linked_list_fifo.py
@@ -0,0 +1,90 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' A class for a linked list that has the nodes in a FIFO order (such as a queue)'''
+
+
+from node import Node
+
+class LinkedListFIFO(object):
+
+    def __init__(self):
+        self.head = None
+        self.length = 0
+        self.tail = None # this is different from ll lifo
+
+    def _printList(self):
+        node = self.head
+        while node:
+            print(node.value)
+            node = node.pointer
+
+    def _addFirst(self, value):
+        self.length = 1
+        node = Node(value)
+        self.head = node
+        self.tail = node
+
+    def _deleteFirst(self):
+        self.length = 0
+        self.head = None
+        self.tail = None
+        print('The list is empty.')
+
+    def _add(self, value):
+        self.length += 1
+        node = Node(value)
+        if self.tail:
+            self.tail.pointer = node
+        self.tail = node
+
+    def addNode(self, value):
+        if not self.head:
+            self._addFirst(value)
+        else:
+            self._add(value)
+
+    def _find(self, index):
+        prev = None
+        node = self.head
+        i = 0
+        while node and i < index:
+            prev = node
+            node = node.pointer
+            i += 1
+        return node, prev, i
+
+    def deleteNode(self, index):
+        if not self.head or not self.head.pointer:
+            self._deleteFirst()
+        else:
+            node, prev, i = self._find(index)
+            if i == index and node:
+                self.length -= 1
+                if i == 0 or not prev :
+                    self.head = node.pointer
+                else:
+                    prev.pointer = node.pointer
+                if not self.tail == node:
+                    self.tail = prev
+            else:
+                print('Node with index {} not found'.format(index))
+
+
+if __name__ == '__main__':
+    ll = LinkedListFIFO()
+    for i in range(1, 5):
+        ll.addNode(i)
+    print('The list is:')
+    ll._printList()
+    print('The list after deleting node with index 2:')
+    ll.deleteNode(2)
+    ll._printList()
+    print('The list after adding node with value 15')
+    ll._add(15)
+    ll._printList()
+    print("The list after deleting everything...")
+    for i in range(ll.length-1, -1, -1):
+        ll.deleteNode(i)
+    ll._printList()
diff --git a/src/abstract_structures/linked_list/linked_list_lifo.py b/src/abstract_structures/linked_list/linked_list_lifo.py
new file mode 100644
index 0000000..b75b621
--- /dev/null
+++ b/src/abstract_structures/linked_list/linked_list_lifo.py
@@ -0,0 +1,90 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' Implement a unordered linked list, i.e. a LIFO linked list (like a stack) '''
+
+from node import Node
+
+class LinkedListLIFO(object):
+
+    def __init__(self):
+        self.head = None
+        self.length = 0
+
+    def _printList(self):
+        node = self.head
+        while node:
+            print(node.value)
+            node = node.pointer
+
+    def _delete(self, prev, node):
+        self.length -= 1
+        if not prev:
+            self.head = node.pointer
+        else:
+            prev.pointer = node.pointer
+
+    def _add(self, value):
+        self.length += 1
+        self.head = Node(value, self.head)
+
+    def _find(self, index):
+        prev = None
+        node = self.head
+        i = 0
+        while node and i < index:
+            prev = node
+            node = node.pointer
+            i += 1
+        return node, prev, i
+
+    def _find_by_value(self, value):
+        prev = None
+        node = self.head
+        found = 0
+        while node and not found:
+            if node.value == value:
+                found = True
+            else:
+                prev = node
+                node = node.pointer
+        return node, prev, found
+
+    def deleteNode(self, index):
+        node, prev, i = self._find(index)
+        if index == i:
+            self._delete(prev, node)
+        else:
+            print('Node with index {} not found'.format(index))
+
+    def deleteNodeByValue(self, value):
+        node, prev, found = self._find_by_value(value)
+        if found:
+            self._delete(prev, node)
+        else:
+            print('Node with value {} not found'.format(value))
+
+
+
+
+if __name__ == '__main__':
+    ll = LinkedListLIFO()
+    for i in range(1, 5):
+        ll._add(i)
+    print('The list is:')
+    ll._printList()
+    print('The list after deleting node with index 2:')
+    ll.deleteNode(2)
+    ll._printList()
+    print('The list after deleting node with value 3:')
+    ll.deleteNodeByValue(2)
+    ll._printList()
+    print('The list after adding node with value 15')
+    ll._add(15)
+    ll._printList()
+    print("The list after deleting everything...")
+    for i in range(ll.length-1, -1, -1):
+        ll.deleteNode(i)
+    ll._printList()
diff --git a/src/abstract_structures/linked_list/node.py b/src/abstract_structures/linked_list/node.py
new file mode 100644
index 0000000..0a2d459
--- /dev/null
+++ b/src/abstract_structures/linked_list/node.py
@@ -0,0 +1,33 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+class Node(object):
+    def __init__(self, value=None, pointer=None):
+        self.value = value
+        self.pointer = pointer
+
+    def getData(self):
+        return self.value
+
+    def getNext(self):
+        return self.pointer
+
+    def setData(self, newdata):
+        self.value = newdata
+
+    def setNext(self, newpointer):
+        self.pointer = newpointer
+
+
+
+if __name__ == '__main__':
+    L = Node("a", Node("b", Node("c", Node("d"))))
+    assert(L.pointer.pointer.value=='c')
+
+    print(L.getData())
+    print(L.getNext().getData())
+    L.setData('aa')
+    L.setNext(Node('e'))
+    print(L.getData())
+    print(L.getNext().getData())
diff --git a/src/abstract_structures/linked_list/part_linked_list.py b/src/abstract_structures/linked_list/part_linked_list.py
new file mode 100644
index 0000000..d178b27
--- /dev/null
+++ b/src/abstract_structures/linked_list/part_linked_list.py
@@ -0,0 +1,57 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' This function divides a linked list in a value, where everything smaller than this value
+    goes to the front, and everything large goes to the back:'''
+
+
+from linked_list_fifo import LinkedListFIFO
+from node import Node
+
+
+def partList(ll, n):
+
+    more = LinkedListFIFO()
+    less = LinkedListFIFO()
+
+    node = ll.head
+
+    while node:
+        item = node.value
+
+        if item < n:
+            less.addNode(item)
+
+        elif item > n:
+            more.addNode(item)
+
+        node = node.pointer
+
+    less.addNode(n)
+    nodemore = more.head
+
+    while nodemore:
+        less.addNode(nodemore.value)
+        nodemore = nodemore.pointer
+
+    return less
+
+
+
+
+if __name__ == '__main__':
+
+    ll = LinkedListFIFO()
+    l = [6, 7, 3, 4, 9, 5, 1, 2, 8]
+    for i in l:
+        ll.addNode(i)
+
+    print('Before Part')
+    ll._printList()
+
+    print('After Part')
+    newll = partList(ll, 6)
+    newll._printList()
+
+
diff --git a/src/abstract_structures/linked_list/sum_linked_list.py b/src/abstract_structures/linked_list/sum_linked_list.py
new file mode 100644
index 0000000..4cf14cb
--- /dev/null
+++ b/src/abstract_structures/linked_list/sum_linked_list.py
@@ -0,0 +1,85 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' Supposing two linked lists representing numbers, such that in each of their
+    nodes they carry one digit. This function sums the two numbers that these
+    two linked lists represent, returning a third list representing the sum:'''
+
+
+from linked_list_fifo import LinkedListFIFO
+from node import Node
+
+
+class LinkedListFIFOYield(LinkedListFIFO):
+
+    # print each node's value, starting from the head
+    def _printList(self):
+        node = self.head
+        while node:
+            yield(node.value)
+            node = node.pointer
+
+
+
+def sumlls(l1, l2):
+
+    lsum = LinkedListFIFOYield()
+    dig1 = l1.head
+    dig2 = l2.head
+    pointer = 0
+
+    while dig1 and dig2:
+        d1 = dig1.value
+        d2 = dig2.value
+        sum_d = d1 + d2 + pointer
+        if sum_d > 9:
+            pointer = sum_d//10
+            lsum.addNode(sum_d%10)
+
+        else:
+            lsum.addNode(sum_d)
+            pointer = 0
+
+        dig1 = dig1.pointer
+        dig2 = dig2.pointer
+
+    if dig1:
+        sum_d = pointer + dig1.value
+        if sum_d > 9:
+            lsum.addNode(sum_d%10)
+        else:
+            lsum.addNode(sum_d)
+        dig1 = dig1.pointer
+
+    if dig2:
+        sum_d = pointer + dig2.value
+        if sum_d > 9:
+            lsum.addNode(sum_d%10)
+        else:
+            lsum.addNode(sum_d)
+        dig2 = dig2.pointer
+
+    return lsum
+
+
+
+
+
+
+if __name__ == '__main__':
+    l1 = LinkedListFIFOYield() # 2671
+    l1.addNode(1)
+    l1.addNode(7)
+    l1.addNode(6)
+    l1.addNode(2)
+
+    l2 = LinkedListFIFOYield() # 455
+    l2.addNode(5)
+    l2.addNode(5)
+    l2.addNode(4)
+
+    lsum = sumlls(l1, l2)
+    l = list(lsum._printList())
+    for i in reversed(l):
+        print i
diff --git a/src/examples_in_my_book/dynamic_programming/__init__.py b/src/abstract_structures/queues/__init__.py
similarity index 100%
rename from src/examples_in_my_book/dynamic_programming/__init__.py
rename to src/abstract_structures/queues/__init__.py
diff --git a/src/abstract_structures/queues/animal_shelter.py b/src/abstract_structures/queues/animal_shelter.py
new file mode 100644
index 0000000..6208289
--- /dev/null
+++ b/src/abstract_structures/queues/animal_shelter.py
@@ -0,0 +1,109 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+""" A class for an animal shelter with two queues"""
+
+
+class Node(object):
+    def __init__(self, animalName=None, animalKind=None, pointer=None):
+        self.animalName = animalName
+        self.animalKind = animalKind
+        self.pointer = pointer
+        self.timestamp = 0
+
+
+
+class AnimalShelter(object):
+    def __init__(self):
+        self.headCat = None
+        self.headDog = None
+        self.tailCat = None
+        self.tailDog = None
+        self.animalNumber = 0
+
+
+    # Queue any animal
+
+    def enqueue(self, animalName, animalKind):
+        self.animalNumber += 1
+        newAnimal = Node(animalName, animalKind)
+        newAnimal.timestamp = self.animalNumber
+
+        if animalKind == 'cat':
+            if not self.headCat:
+                self.headCat = newAnimal
+            if self.tailCat:
+                self.tailCat.pointer = newAnimal
+            self.tailCat = newAnimal
+
+        elif animalKind == 'dog':
+            if not self.headDog:
+                self.headDog = newAnimal
+            if self.tailDog:
+                self.tailDog.pointer = newAnimal
+            self.tailDog = newAnimal
+
+
+    # Dequeue methods
+
+    def dequeueDog(self):
+        if self.headDog:
+            newAnimal = self.headDog
+            self.headDog = newAnimal.pointer
+            return str(newAnimal.animalName)
+        else:
+            return 'No Dogs!'
+
+
+    def dequeueCat(self):
+        if self.headCat:
+            newAnimal = self.headCat
+            self.headCat = newAnimal.pointer
+            return str(newAnimal.animalName)
+        else:
+            return 'No Cats!'
+
+
+    def dequeueAny(self):
+        if self.headCat and not self.headDog:
+            return self.dequeueCat()
+        elif self.headDog and not self.headCat:
+            return self.dequeueDog()
+        elif self.headDog and self.headCat:
+            if self.headDog.timestamp < self.headCat.timestamp:
+                return self.dequeueDog()
+            else:
+                return self.dequeueCat()
+        else:
+            return ('No Animals!')
+
+
+
+    def _print(self):
+        print("Cats:")
+        cats = self.headCat
+        while cats:
+            print(cats.animalName, cats.animalKind)
+            cats = cats.pointer
+        print("Dogs:")
+        dogs = self.headDog
+        while dogs:
+            print(dogs.animalName, dogs.animalKind)
+            dogs = dogs.pointer
+
+
+if __name__ == '__main__':
+
+    qs = AnimalShelter()
+    qs.enqueue('bob', 'cat')
+    qs.enqueue('mia', 'cat')
+    qs.enqueue('yoda', 'dog')
+    qs.enqueue('wolf', 'dog')
+    qs._print()
+
+    print("Deque one dog and one cat...")
+    qs.dequeueDog()
+    qs.dequeueCat()
+    qs._print()
diff --git a/src/abstract_structures/queues/deque.py b/src/abstract_structures/queues/deque.py
new file mode 100644
index 0000000..ede3e53
--- /dev/null
+++ b/src/abstract_structures/queues/deque.py
@@ -0,0 +1,39 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' a class for a double ended queue (also inefficient) '''
+
+from queue import Queue
+
+class Deque(Queue):
+
+    def enqueue_back(self, item):
+        self.items.append(item)
+
+    def dequeue_front(self):
+        return self.items.pop(0)
+
+
+
+if __name__ == '__main__':
+    queue = Deque()
+    print("Is the queue empty? ", queue.isEmpty())
+    print("Adding 0 to 10 in the queue...")
+    for i in range(10):
+        queue.enqueue(i)
+    print("Queue size: ", queue.size())
+    print("Queue peek : ", queue.peek())
+    print("Dequeue...", queue.dequeue())
+    print("Queue peek: ", queue.peek())
+    print("Is the queue empty? ", queue.isEmpty())
+    print(queue)
+
+    print("\nNow using the dequeue methods...")
+    print("Dequeue from front...", queue.dequeue_front())
+    print("Queue peek: ", queue.peek())
+    print(queue)
+    print("Queue from back...")
+    queue.enqueue_back(50)
+    print("Queue peek: ", queue.peek())
+    print(queue)
diff --git a/src/abstract_structures/queues/linked_queue.py b/src/abstract_structures/queues/linked_queue.py
new file mode 100644
index 0000000..ca2aafd
--- /dev/null
+++ b/src/abstract_structures/queues/linked_queue.py
@@ -0,0 +1,80 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' Queue acts as a container for nodes (objects) that are inserted and removed according FIFO'''
+
+
+class Node(object):
+    def __init__(self, value=None, pointer=None):
+        self.value = value
+        self.pointer = None
+
+
+class LinkedQueue(object):
+    def __init__(self):
+        self.head = None
+        self.tail = None
+
+
+    def isEmpty(self):
+        return not bool(self.head)
+
+
+    def dequeue(self):
+        if self.head:
+            value = self.head.value
+            self.head = self.head.pointer
+            return value
+        else:
+            print('Queue is empty, cannot dequeue.')
+
+
+    def enqueue(self, value):
+        node = Node(value)
+        if not self.head:
+            self.head = node
+            self.tail = node
+        else:
+            if self.tail:
+                self.tail.pointer = node
+            self.tail = node
+
+
+    def size(self):
+        node = self.head
+        num_nodes = 0
+        while node:
+                num_nodes += 1
+                node = node.pointer
+        return num_nodes
+
+
+    def peek(self):
+        return self.head.value
+
+
+    def _print(self):
+        node = self.head
+        while node:
+            print(node.value)
+            node = node.pointer
+
+
+
+
+if __name__ == '__main__':
+    queue = LinkedQueue()
+    print("Is the queue empty? ", queue.isEmpty())
+    print("Adding 0 to 10 in the queue...")
+    for i in range(10):
+        queue.enqueue(i)
+    print("Is the queue empty? ", queue.isEmpty())
+    queue._print()
+
+    print("Queue size: ", queue.size())
+    print("Queue peek : ", queue.peek())
+    print("Dequeue...", queue.dequeue())
+    print("Queue peek: ", queue.peek())
+    queue._print()
+
diff --git a/src/abstract_structures/queues/palindrome_checker_with_deque.py b/src/abstract_structures/queues/palindrome_checker_with_deque.py
new file mode 100644
index 0000000..af14321
--- /dev/null
+++ b/src/abstract_structures/queues/palindrome_checker_with_deque.py
@@ -0,0 +1,47 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+""" Using our deque class and Python's deque class """
+
+
+import string
+import collections
+
+from deque import Deque
+
+
+STRIP = string.whitespace + string.punctuation + "\"'"
+
+def palindrome_checker_with_deque(str1):
+
+    d1 = Deque()
+    d2 = collections.deque()
+
+    for s in str1.lower():
+        if s not in STRIP:
+            d2.append(s)
+            d1.enqueue(s)
+
+
+    eq1 = True
+    while d1.size() > 1 and eq1:
+        if d1.dequeue_front() != d1.dequeue():
+            eq1 = False
+
+    eq2 = True
+    while len(d2) > 1 and eq2:
+        if d2.pop() != d2.popleft():
+            eq2 = False
+
+    return eq1, eq2
+
+
+
+
+if __name__ == '__main__':
+    str1 = 'Madam Im Adam'
+    str2 = 'Buffy is a Slayer'
+    print(palindrome_checker_with_deque(str1))
+    print(palindrome_checker_with_deque(str2))
\ No newline at end of file
diff --git a/src/abstract_structures/queues/queue.py b/src/abstract_structures/queues/queue.py
new file mode 100644
index 0000000..f08c8b4
--- /dev/null
+++ b/src/abstract_structures/queues/queue.py
@@ -0,0 +1,63 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+class Queue(object):
+
+    def __init__(self):
+        self.in_stack = []
+        self.out_stack = []
+
+    def _transfer(self):
+        while self.in_stack:
+            self.out_stack.append(self.in_stack.pop())
+
+    def enqueue(self, item):
+        return self.in_stack.append(item)
+
+    def dequeue(self):
+        if not self.out_stack:
+            self._transfer()
+        if self.out_stack:
+            return self.out_stack.pop()
+        else:
+            return "Queue empty!"
+
+    def size(self):
+        return len(self.in_stack) + len(self.out_stack)
+
+    def peek(self):
+        if not self.out_stack:
+            self._transfer()
+        if self.out_stack:
+            return self.out_stack[-1]
+        else:
+            return "Queue empty!"
+
+    def __repr__(self):
+        if not self.out_stack:
+            self._transfer()
+        if self.out_stack:
+            return '{}'.format(self.out_stack)
+        else:
+            return "Queue empty!"
+
+    def isEmpty(self):
+        return not (bool(self.in_stack) or bool(self.out_stack))
+
+
+if __name__ == '__main__':
+    queue = Queue()
+    print("Is the queue empty? ", queue.isEmpty())
+    print("Adding 0 to 10 in the queue...")
+    for i in range(10):
+        queue.enqueue(i)
+    print("Queue size: ", queue.size())
+    print("Queue peek : ", queue.peek())
+    print("Dequeue...", queue.dequeue())
+    print("Queue peek: ", queue.peek())
+    print("Is the queue empty? ", queue.isEmpty())
+
+    print("Printing the queue...")
+    print(queue)
\ No newline at end of file
diff --git a/src/examples_in_my_book/general_problems/dicts/__init__.py b/src/abstract_structures/stacks/__init__.py
similarity index 100%
rename from src/examples_in_my_book/general_problems/dicts/__init__.py
rename to src/abstract_structures/stacks/__init__.py
diff --git a/src/examples_in_my_book/adt/stacks/dec2bin_with_stack.py b/src/abstract_structures/stacks/dec2bin_with_stack.py
similarity index 53%
rename from src/examples_in_my_book/adt/stacks/dec2bin_with_stack.py
rename to src/abstract_structures/stacks/dec2bin_with_stack.py
index 594ed93..31dc066 100644
--- a/src/examples_in_my_book/adt/stacks/dec2bin_with_stack.py
+++ b/src/abstract_structures/stacks/dec2bin_with_stack.py
@@ -1,28 +1,30 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+'''transform a decimal number to a binary number with a stack '''
+
 
 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
 
+    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()
+    decnum = 9
+    assert(dec2bin_with_stack(decnum) == '1001')
diff --git a/src/abstract_structures/stacks/linked_stack.py b/src/abstract_structures/stacks/linked_stack.py
new file mode 100644
index 0000000..23a4ad6
--- /dev/null
+++ b/src/abstract_structures/stacks/linked_stack.py
@@ -0,0 +1,71 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+""" A stack made of linked list"""
+
+
+class Node(object):
+    def __init__(self, value=None, pointer=None):
+        self.value = value
+        self.pointer = pointer
+
+
+class Stack(object):
+    def __init__(self):
+        self.head = None
+
+    def isEmpty(self):
+        return not bool(self.head)
+
+    def push(self, item):
+        self.head = Node(item, self.head)
+
+
+    def pop(self):
+        if self.head:
+            node = self.head
+            self.head = node.pointer
+            return node.value
+        else:
+            print('Stack is empty.')
+
+
+    def peek(self):
+        if self.head:
+            return self.head.value
+        else:
+            print('Stack is empty.')
+
+
+    def size(self):
+        node = self.head
+        count = 0
+        while node:
+            count +=1
+            node = node.pointer
+        return count
+
+
+    def _printList(self):
+        node = self.head
+        while node:
+            print(node.value)
+            node = node.pointer
+
+
+
+if __name__ == '__main__':
+    stack = Stack()
+    print("Is the stack empty? ", stack.isEmpty())
+    print("Adding 0 to 10 in the stack...")
+    for i in range(10):
+        stack.push(i)
+    stack._printList()
+    print("Stack size: ", stack.size())
+    print("Stack peek : ", stack.peek())
+    print("Pop...", stack.pop())
+    print("Stack peek: ", stack.peek())
+    print("Is the stack empty? ", stack.isEmpty())
+    stack._printList()
diff --git a/src/abstract_structures/stacks/reverse_string_with_stack.py b/src/abstract_structures/stacks/reverse_string_with_stack.py
new file mode 100644
index 0000000..014ab9b
--- /dev/null
+++ b/src/abstract_structures/stacks/reverse_string_with_stack.py
@@ -0,0 +1,31 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' Uses a stack to reverse a string '''
+
+from stack import Stack
+
+def reverse_string_with_stack(str1):
+
+  s = Stack()
+  revStr = ''
+
+  for c in str1:
+    s.push(c)
+
+  while not s.isEmpty():
+    revStr += s.pop()
+
+  return revStr
+
+
+
+if __name__ == '__main__':
+  str1 = 'Buffy is a Slayer!'
+  print(str1)
+  print(reverse_string_with_stack(str1))
+
+
+
diff --git a/src/abstract_structures/stacks/set_of_stacks.py b/src/abstract_structures/stacks/set_of_stacks.py
new file mode 100644
index 0000000..bfe5bde
--- /dev/null
+++ b/src/abstract_structures/stacks/set_of_stacks.py
@@ -0,0 +1,56 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+""" define a class for a set of stacks """
+
+from stack import Stack
+
+class SetOfStacks(Stack):
+    def __init__(self, capacity=4):
+        self.setofstacks = []
+        self.items = []
+        self.capacity = capacity
+
+
+    def push(self, value):
+        if self.size() >= self.capacity:
+            self.setofstacks.append(self.items)
+            self.items = []
+        self.items.append(value)
+
+
+    def pop(self):
+        value = self.items.pop()
+        if self.isEmpty() and self.setofstacks:
+            self.items = self.setofstacks.pop()
+        return value
+
+
+    def sizeStack(self):
+        return len(self.setofstacks)*self.capacity + self.size()
+
+
+    def __repr__(self):
+        aux = []
+        for s in self.setofstacks:
+             aux.extend(s)
+        aux.extend(self.items)
+        return '{}'.format(aux)
+
+
+
+if __name__ == '__main__':
+    capacity = 5
+    stack = SetOfStacks(capacity)
+    print("Is the stack empty? ", stack.isEmpty())
+    print("Adding 0 to 10 in the stack...")
+    for i in range(10):
+        stack.push(i)
+    print(stack)
+    print("Stack size: ", stack.sizeStack())
+    print("Stack peek : ", stack.peek())
+    print("Pop...", stack.pop())
+    print("Stack peek: ", stack.peek())
+    print("Is the stack empty? ", stack.isEmpty())
+    print(stack)
diff --git a/src/abstract_structures/stacks/stack.py b/src/abstract_structures/stacks/stack.py
new file mode 100755
index 0000000..869ecf3
--- /dev/null
+++ b/src/abstract_structures/stacks/stack.py
@@ -0,0 +1,65 @@
+#!/usr/bin/env python
+
+# copy of the class ../Stack.py
+
+__author__ = "bt3"
+
+
+class Stack(object):
+    def __init__(self):
+        self.content = []
+        self.min_array = []
+        self.min = float('inf')
+
+    def push(self, value):
+        if value < self.min:
+            self.min = value
+
+        self.content.append(value)
+        self.min_array.append(self.min)
+
+    def pop(self):
+        if self.content:
+            value = self.content.pop()
+            self.min_array.pop()
+            if self.min_array:
+                self.min = self.min_array[-1]
+            return value
+        else:
+            return 'Empty List. '
+
+    def find_min(self):
+        if self.min_array:
+            return self.min_array[-1]
+        else:
+            return 'No min value for empty list.'
+
+    def size(self):
+        return len(self.content)
+
+    def isEmpty(self):
+        return not bool(self.content)
+
+    def peek(self):
+        if self.content:
+            return self.content[-1]
+        else:
+            print('Stack is empty.')
+
+
+    def __repr__(self):
+        return '{}'.format(self.content)
+
+
+if __name__ == '__main__':
+    q = Stack()
+
+    for i in range(15,20):
+        q.push(i)
+    for i in range(10,5,-1):
+        q.push(i)
+
+
+
+    for i in range(1, 13):
+        print q.pop(), q.find_min()
\ No newline at end of file
diff --git a/src/abstract_structures/stacks/stack_with_min.py b/src/abstract_structures/stacks/stack_with_min.py
new file mode 100644
index 0000000..83a16ed
--- /dev/null
+++ b/src/abstract_structures/stacks/stack_with_min.py
@@ -0,0 +1,77 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' A stack with a minimum lookup '''
+
+from stack import Stack
+
+
+class NodeWithMin(object):
+    def __init__(self, value=None, minimum=None):
+        self.value = value
+        self.minimum = minimum
+
+
+class StackMin(Stack):
+    def __init__(self):
+        self.items = []
+        self.minimum = None
+
+
+    def push(self, value):
+        if self.isEmpty() or self.minimum > value:
+           self.minimum = value
+        self.items.append(NodeWithMin(value, self.minimum))
+
+
+    def peek(self):
+        return self.items[-1].value
+
+
+    def peekMinimum(self):
+        return self.items[-1].minimum
+
+
+    def pop(self):
+        item = self.items.pop()
+        if item:
+            if item.value == self.minimum:
+                self.minimum = self.peekMinimum()
+            return item.value
+        else:
+            print("Stack is empty.")
+
+    def __repr__(self):
+        aux = []
+        for i in self.items:
+            aux.append(i.value)
+        return '{}'.format(aux)
+
+
+
+if __name__ == '__main__':
+    stack = StackMin()
+    print("Is the stack empty? ", stack.isEmpty())
+    print("Adding 0 to 10 in the stack...")
+    for i in range(10,3, -1):
+        stack.push(i)
+    print(stack)
+
+    print("Stack size: ", stack.size())
+    print("Stack peek and peekMinimum : ", stack.peek(), stack.peekMinimum())
+    print("Pop...", stack.pop())
+    print("Stack peek and peekMinimum : ", stack.peek(), stack.peekMinimum())
+    print("Is the stack empty? ", stack.isEmpty())
+    print(stack)
+
+    for i in range(5, 1, -1):
+        stack.push(i)
+    print(stack)
+
+    print("Stack size: ", stack.size())
+    print("Stack peek and peekMinimum : ", stack.peek(), stack.peekMinimum())
+    print("Pop...", stack.pop())
+    print("Stack peek and peekMinimum : ", stack.peek(), stack.peekMinimum())
+    print("Is the stack empty? ", stack.isEmpty())
+    print(stack)
diff --git a/src/further_examples/queues_stacks/towers_of_hanoi.py b/src/abstract_structures/stacks/towers_of_hanoi.py
similarity index 73%
rename from src/further_examples/queues_stacks/towers_of_hanoi.py
rename to src/abstract_structures/stacks/towers_of_hanoi.py
index 88dc70d..f424faa 100644
--- a/src/further_examples/queues_stacks/towers_of_hanoi.py
+++ b/src/abstract_structures/stacks/towers_of_hanoi.py
@@ -1,16 +1,28 @@
-from stack import Stack, Node
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+""" Implement the 'towers of hanoi'"""
+
+from linked_stack import Stack, Node
 
 
 def moveTop(s1, s3):
+
     s3.append(s1.pop())
 
+
 def moveDisks(n, s1, s3, s2):
-    if n < 1: return    
+
+    if n < 1: return
     moveDisks(n - 1, s1, s2, s3)
     moveTop(s1, s3)
     moveDisks(n -1, s2, s3, s1)
 
 
+
 def towersOfHanoi(n):
     s1 = [x+1 for x in range(n)]
     s2 = []
@@ -18,9 +30,12 @@ def towersOfHanoi(n):
     print('The first stick is {0} and the third stick has {1}'.format(s1, s3))
 
     moveDisks(n, s1, s3, s2)
-    
+
     print('The first stick is {0} and the third stick has {1}'.format(s1, s3))
+
     return s3
-   
+
+
+
 if __name__ == '__main__':
-    towersOfHanoi(6)          
+    towersOfHanoi(6)
diff --git a/src/further_examples/bit_operations/bit_array.py b/src/bitwise/bit_array.py
old mode 100644
new mode 100755
similarity index 82%
rename from src/further_examples/bit_operations/bit_array.py
rename to src/bitwise/bit_array.py
index c5f8366..9e5aa46
--- a/src/further_examples/bit_operations/bit_array.py
+++ b/src/bitwise/bit_array.py
@@ -1,17 +1,16 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
-''' Example of how to use a bit array in python as a "counter" dict:
+__author__ = "bt3"
 
+''' Example of how to use a bit array in python as a "counter" dict'''
+
+def print_dupl_ba(l1):
+    '''
     >>> l1 = [0, 1, 2, 3, 4, 2, 6, 7, 8, 9]
     >>> print_dupl_ba(l1)
     2
-'''
-
+    '''
 
-
-def print_dupl_ba(l1):
     bs = bytearray(10)
     for i in range(len(l1)):
         if i == l1[i]:
@@ -22,9 +21,6 @@ def print_dupl_ba(l1):
     return None
 
 
-    
-    
-    
 
 if __name__ == '__main__':
     import doctest
diff --git a/src/bitwise/bitwise.txt b/src/bitwise/bitwise.txt
new file mode 100755
index 0000000..f55d9d1
--- /dev/null
+++ b/src/bitwise/bitwise.txt
@@ -0,0 +1,33 @@
+				BIT-WISE
+			----------------------
+
+1. To find a number:
+11000101 is 2^0+2^2+2^6+2^7 = 197
+
+
+2. Left shifting:
+	0010 1011 << 4  ---> 1011 000
+
+
+3. Right shifting:
+	0010 1011 >> 4	---> 0000 0010
+	or it can be filled with the copy of the first bit, instead of 0:
+	1011 0010 >> 4  ---> 1111 1011
+
+
+4. XOR can cancels out:
+15 ^ 12 ^ 15 = 12
+
+
+5. 2^x:
+	left-shift 1 by x:
+	0000 0001 << x
+
+	so if x = 2, 2^2 = 4 -> 100
+
+	0000 0001 << 2  ---> 0000 0100
+
+
+6. Is power of 2?
+	just do x&(x-1).
+	if 0 --> yes!
diff --git a/src/bitwise/clear_bits.py b/src/bitwise/clear_bits.py
new file mode 100755
index 0000000..5297b74
--- /dev/null
+++ b/src/bitwise/clear_bits.py
@@ -0,0 +1,37 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' Clear a bit in a binary number.
+    Like the reverse of set bit:
+    1) first create a number filled of 1s,
+        with 0 at i (can create 0001000 and ~)
+    2) AND the number so it clears the ith bit
+'''
+
+
+
+def clear_bit(num, i):
+    mask = ~ (1 << i)   # -0b10001
+    return bin(num & mask)
+
+
+def clear_all_bits_from_i_to_0(num, i):
+    mask = ~ ( (1 << (i+1)) - 1)
+    return bin(num & mask)
+
+
+def clear_all_bits_from_most_sig_to_1(num, i):
+    mask =  ( 1 << i) -1
+    return bin(num & mask)
+
+
+if __name__ == '__main__':
+    num = int('10010000', 2)
+    print clear_bit(num, 4)   # '0b10000000'
+
+    num = int('10010011', 2)
+    print clear_all_bits_from_i_to_0(num, 2)  # '0b10010000'
+
+    num = int('1110011', 2)
+    print clear_all_bits_from_most_sig_to_1(num, 2)  #'0b11'
diff --git a/src/further_examples/bit_operations/find_bit_len.py b/src/bitwise/find_bit_len.py
old mode 100644
new mode 100755
similarity index 63%
rename from src/further_examples/bit_operations/find_bit_len.py
rename to src/bitwise/find_bit_len.py
index d061435..81d90f0
--- a/src/further_examples/bit_operations/find_bit_len.py
+++ b/src/bitwise/find_bit_len.py
@@ -1,28 +1,25 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 ''' Find how many bits a int has:
     1) Start with a mask of 1
     2) Mask with AND
     3) if result (if true): count += 1
-    (obs: to find the int of a bin do int('1001', 2)) and to show in bin do bin(int))
-    
-    >>> for i in range(17): print(find_bit_len(i))
+    (obs: to find the int of a bin do int('1001', 2)) and to show in bin
+    do bin(int))
 '''
 
 
-
 def find_bit_len(int_num):
     lenght = 0
     while int_num:
         int_num >>= 1
         lenght += 1
     return lenght
-    
-    
 
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
 
+if __name__ == '__main__':
+    for i in range(17):
+        print(find_bit_len(i))
+        print i.bit_length()
diff --git a/src/further_examples/bit_operations/find_how_many_1_binary.py b/src/bitwise/find_how_many_1_binary.py
old mode 100644
new mode 100755
similarity index 69%
rename from src/further_examples/bit_operations/find_how_many_1_binary.py
rename to src/bitwise/find_how_many_1_binary.py
index 26a10f7..89fc44c
--- a/src/further_examples/bit_operations/find_how_many_1_binary.py
+++ b/src/bitwise/find_how_many_1_binary.py
@@ -1,21 +1,22 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 ''' Find how many 1s in the binary:
     1) Start with a mask of 1
     2) Mask with AND
     3) if result (if true): count += 1
-    (obs: to find the int of a bin do int('1001', 2)) and to show in bin do bin(int))
-    
-    >>> find_how_many_1_in_a_binary(9)
-    2
-
+    (obs: to find the int of a bin do int('1001',
+        2)) and to show in bin do bin(int))
 '''
 
 
-
 def find_how_many_1_in_a_binary(n):
+    '''
+    >>> find_how_many_1_in_a_binary(9)
+    2
+    '''
+
     counter = 0
     while n:
         if n & 1:
@@ -24,9 +25,6 @@ def find_how_many_1_in_a_binary(n):
     return counter
 
 
-    
-    
-    
 
 if __name__ == '__main__':
     import doctest
diff --git a/src/bitwise/get_bit.py b/src/bitwise/get_bit.py
new file mode 100755
index 0000000..b212316
--- /dev/null
+++ b/src/bitwise/get_bit.py
@@ -0,0 +1,27 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' Get a bit in a binary number:
+    1) Shifts 1 over by i bits
+    2) make an AND with the number
+    3) all the other than the bit at i are clean, now compare to 0
+    4) if the new value is not 0, bit i is 1
+'''
+
+
+def get_bit(num, i):
+    mask = 1 << i
+    return num & mask != 0
+
+
+if __name__ == '__main__':
+    num = int('0100100', 2)
+    get_bit(num, 0)   # 0
+    get_bit(num, 1)   # 0
+    get_bit(num, 2)   # 1
+    get_bit(num, 3)   # 0
+    get_bit(num, 4)   # 0
+    get_bit(num, 5)   # 1
+    get_bit(num, 6)   # 0
+
diff --git a/src/further_examples/bit_operations/get_float_rep_bin.py b/src/bitwise/get_float_rep_bin.py
old mode 100644
new mode 100755
similarity index 90%
rename from src/further_examples/bit_operations/get_float_rep_bin.py
rename to src/bitwise/get_float_rep_bin.py
index e8f7bd4..fb3814d
--- a/src/further_examples/bit_operations/get_float_rep_bin.py
+++ b/src/bitwise/get_float_rep_bin.py
@@ -1,20 +1,22 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 ''' Given a real number between 0 and 1 (eg: 0.72), this method print the binary
     representation. If the Number cannot be represented accurately in binary, with at
     most 32 chars, print error:
-    
+'''
+
+def get_float_rep(num):
+    '''
     >>> get_float_rep(0.72)
     ('Error 2', '.1011100001010001111010111000010')
     >>> get_float_rep(0.1)
     ('Error 2', '.0001100110011001100110011001100')
     >>> get_float_rep(0.5)
     '.1'
-'''
+    '''
 
-def get_float_rep(num):
     if num >= 1 or num <= 0: return 'Error 1'
     result = '.'
     while num:
@@ -27,7 +29,7 @@ def get_float_rep(num):
             result += '0'
             num = r
     return result
-    
+
 
 if __name__ == '__main__':
     import doctest
diff --git a/src/further_examples/bit_operations/insert_small_bin_into_big_bin.py b/src/bitwise/insert_small_bin_into_big_bin.py
old mode 100644
new mode 100755
similarity index 88%
rename from src/further_examples/bit_operations/insert_small_bin_into_big_bin.py
rename to src/bitwise/insert_small_bin_into_big_bin.py
index 03257b8..292b169
--- a/src/further_examples/bit_operations/insert_small_bin_into_big_bin.py
+++ b/src/bitwise/insert_small_bin_into_big_bin.py
@@ -1,33 +1,34 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 ''' Given two 32-bit numbers, N and M, and two bit positions, i and j, this
-    method insert M into N such that M starts at bit j and ends at bit i: 
+    method insert M into N such that M starts at bit j and ends at bit i:
     1) clear the bits j thru i in N'
     2) shift M so that it lines up with bits j thru i
     3) merge M and N
+'''
 
+def insert_small_bin_into_big_bin(M, N, i, j):
+    '''
     >>> N = 0b10000000000
     >>> M = 0b10011
     >>> j = 6
     >>> i = 2
     >>> insert_small_bin_into_big_bin(M, N, i, j)
     '0b10001001100'
-'''
+    '''
 
-def insert_small_bin_into_big_bin(M, N, i, j):
     allOnes = ~0
     left = allOnes << (j+1) # 1110000
     right = ( (1 << i) - 1) # 0000111
     mask = left | right     # 1110111
     N_cleared = N & mask
     M_shifted = M << i
-    
+
     return bin( N_cleared | M_shifted)
-    
-  
-    
+
 
 if __name__ == '__main__':
     import doctest
diff --git a/src/further_examples/bit_operations/next_with_same_num_1s.py b/src/bitwise/next_with_same_num_1s.py
old mode 100644
new mode 100755
similarity index 67%
rename from src/further_examples/bit_operations/next_with_same_num_1s.py
rename to src/bitwise/next_with_same_num_1s.py
index 47ba953..6c2617e
--- a/src/further_examples/bit_operations/next_with_same_num_1s.py
+++ b/src/bitwise/next_with_same_num_1s.py
@@ -1,27 +1,19 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 ''' Give a positive int, print the next smallest and next largest ints with
     same number of 1 bits.
     The brute force is:
     1) find number of 1 bits
     2) loop above and down until find same, checking for each
-    
-    >>> num = 0b1001
-    >>> next = '0b1010'
-    >>> prev = '0b110'
-    >>> print_prev_same_1s(num) == prev
-    True
-    >>> print_next_same_1s(num) == next
-    True
-
 '''
 
 
 
 def print_prev_same_1s(num):
-    n1s = find_num_1s(num)   
+    n1s = find_num_1s(num)
     # find prev
     i = num-1
     while True:
@@ -31,10 +23,10 @@ def print_prev_same_1s(num):
         i -= 1
         if i < 0:
             return None
- 
+
 def print_next_same_1s(num):
-    n1s = find_num_1s(num)        
-    # find next   
+    n1s = find_num_1s(num)
+    # find next
     i = num+1
     while True:
         n1s_here = find_num_1s(i)
@@ -43,8 +35,8 @@ def print_next_same_1s(num):
         i += 1
         if i < 0:
             return None
-    
-    
+
+
 
 def find_num_1s(num):
     counter = 0
@@ -54,11 +46,14 @@ def find_num_1s(num):
         num >>= 1
     return counter
 
-    
-    
-    
+
+
+
 
 if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
+    num = 0b1001
+    n = '0b1010'
+    p = '0b110'
+    print_prev_same_1s(num) == p
+    print_next_same_1s(num) == n
 
diff --git a/src/further_examples/bit_operations/num_bits_to_convert_2_nums.py b/src/bitwise/num_bits_to_convert_2_nums.py
old mode 100644
new mode 100755
similarity index 63%
rename from src/further_examples/bit_operations/num_bits_to_convert_2_nums.py
rename to src/bitwise/num_bits_to_convert_2_nums.py
index 90054de..3447d35
--- a/src/further_examples/bit_operations/num_bits_to_convert_2_nums.py
+++ b/src/bitwise/num_bits_to_convert_2_nums.py
@@ -1,18 +1,12 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 ''' This method returns the number of bits that are necessary to change to convert two
     numbers A and B:
     1) XOR
     2) count 1s
-        
-    >>> a = int('10010000', 2)
-    >>> b = int('01011010', 2)
-    >>> count_bits_swap(a, b)  
-    4
-    >>> count_bits_swap2(a, b)  
-    4
 '''
 
 def count_bits_swap2(a, b):
@@ -28,8 +22,8 @@ def count_bits_swap2(a, b):
 def count_bits_swap(a, b):
     m = a^b
     return count_1s(m)
-    
-    
+
+
 def count_1s(m):
     count = 0
     while m:
@@ -37,9 +31,10 @@ def count_1s(m):
             count +=1
         m >>= 1
     return count
-    
 
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
 
+if __name__ == '__main__':
+    a = int('10010000', 2)
+    b = int('01011010', 2)
+    print count_bits_swap(a, b)  #4
+    print count_bits_swap2(a, b)  #4
diff --git a/src/bitwise/set_bit.py b/src/bitwise/set_bit.py
new file mode 100755
index 0000000..eeb73fb
--- /dev/null
+++ b/src/bitwise/set_bit.py
@@ -0,0 +1,26 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+''' Set a bit in a binary number:
+    1) Shifts 1 over by i bits
+    2) make an OR with the number, only the value at bit i will change and all the others bit
+    of the mask are zero so will not affect the num
+'''
+
+
+def set_bit(num, i):
+    mask = 1 << i
+    return bin( num | mask )
+
+
+if __name__ == '__main__':
+    num = int('0100100', 2)
+    print set_bit(num, 0)   #'0b100101'
+    print set_bit(num, 1)   #'0b100110'
+    print set_bit(num, 2)   # nothing change '0b100100'
+    print set_bit(num, 3)   #'0b101100'
+    print set_bit(num, 4) #'0b110100'
+    print set_bit(num, 5)     # nothing change '0b100100'
diff --git a/src/bitwise/swap_in_place.py b/src/bitwise/swap_in_place.py
new file mode 100755
index 0000000..5aee66a
--- /dev/null
+++ b/src/bitwise/swap_in_place.py
@@ -0,0 +1,23 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+'''
+    swapping values in place without extra memory
+'''
+
+
+def swap_bit(a, b):
+    '''
+    >>> swap_bit(14, 73)
+    (73, 14)
+    '''
+    a = a^b
+    b = a^b
+    a = a^b
+    return a, b
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/further_examples/bit_operations/swap_odd_even.py b/src/bitwise/swap_odd_even.py
old mode 100644
new mode 100755
similarity index 87%
rename from src/further_examples/bit_operations/swap_odd_even.py
rename to src/bitwise/swap_odd_even.py
index d640262..386627d
--- a/src/further_examples/bit_operations/swap_odd_even.py
+++ b/src/bitwise/swap_odd_even.py
@@ -1,6 +1,7 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 ''' Swap odd and even bits in a smart way in a binary:
     1) first for odds, take n and move the odd:
@@ -8,17 +9,18 @@
         (b) shift by right by 1
     2) do the same to ints with 01010101
     3) merge
-    
-    >>> num = 0b11011101
-    >>> result = '0b1101110'
-    >>> swap_odd_even(num) == result
-    True
-
 '''
 
 
 
 def swap_odd_even(num):
+    '''
+    >>> num = 0b11011101
+    >>> result = '0b1101110'
+    >>> swap_odd_even(num) == result
+    True
+    '''
+
     mask_odd = 0xAA # 0b10101010
     mask_even = 0x55 # 0b1010101
     odd = num & mask_odd
@@ -28,9 +30,6 @@ def swap_odd_even(num):
     return bin(odd | even)
 
 
-    
-    
-    
 
 if __name__ == '__main__':
     import doctest
diff --git a/src/further_examples/bit_operations/update_bit.py b/src/bitwise/update_bit.py
old mode 100644
new mode 100755
similarity index 58%
rename from src/further_examples/bit_operations/update_bit.py
rename to src/bitwise/update_bit.py
index 61422c8..c31d713
--- a/src/further_examples/bit_operations/update_bit.py
+++ b/src/bitwise/update_bit.py
@@ -1,26 +1,22 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 ''' This method merges set bit and clean bit:
     1) first clear the bit at i using a mask such as 1110111
     2) then shift the intended value v by i bits
     3) this will create a number with bit i to v and all other to 0
     4) finally update the ith bit with or
-        
-    >>> num = int('10010000', 2)
-    >>> update_bit(num, 2, 1)   
-    '0b10010100'
 '''
 
 
 
 def  update_bit(num, i, v):
     mask = ~ (1 << i)
-    return bin( (num & mask) | (v << i) )    
-    
+    return bin( (num & mask) | (v << i) )
+
 
 if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
+    num = int('10010000', 2)
+    print update_bit(num, 2, 1)   # '0b10010100'
 
diff --git a/src/examples_in_my_book/general_problems/lists/__init__.py b/src/builtin_structures/__init__.py
old mode 100644
new mode 100755
similarity index 100%
rename from src/examples_in_my_book/general_problems/lists/__init__.py
rename to src/builtin_structures/__init__.py
diff --git a/src/builtin_structures/anagram.py b/src/builtin_structures/anagram.py
new file mode 100755
index 0000000..bffc085
--- /dev/null
+++ b/src/builtin_structures/anagram.py
@@ -0,0 +1,51 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+from collections import Counter
+
+def is_anagram(s1, s2):
+    '''
+    >>> is_anagram('cat', 'tac')
+    True
+    >>> is_anagram('cat', 'hat')
+    False
+    '''
+    counter = Counter()
+    for c in s1:
+        counter[c] += 1
+
+    for c in s2:
+        counter[c] -= 1
+
+    for i in counter.values():
+        if i:
+            return False
+
+    return True
+
+''' verify if words are anagrams by comparing a sum of  Unicode code
+point of the character'''
+
+def get_unicode_sum(word):
+    s = 0
+    for p in word:
+        s += ord(p)
+    return s
+
+
+def is_anagram2(word1, word2):
+    '''
+    >>> is_anagram2('cat', 'tac')
+    True
+    >>> is_anagram2('cat', 'hat')
+    False
+    '''
+    return get_unicode_sum(word1) == get_unicode_sum(word2)
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/builtin_structures/balance.txt b/src/builtin_structures/balance.txt
new file mode 100755
index 0000000..27df907
--- /dev/null
+++ b/src/builtin_structures/balance.txt
@@ -0,0 +1,9 @@
+__author__ = "bt3"
+
+
+This is the classic "you have 8 balls/coins, which are the same weight, except for one which is slightly heavier than the others. You also have an old-style balance. What is the fewest number of weighings to find the heavy coin/ball?
+
+Answer: 2! You need to use every information available:
+Weight 3 x 3 balls/coins.
+If they weight the same: weight the 2 balls/coins left outside.
+Else, measure 2 of the 3 heavier balls/coins.
\ No newline at end of file
diff --git a/src/builtin_structures/balance_symbols.py b/src/builtin_structures/balance_symbols.py
new file mode 100755
index 0000000..ff65f82
--- /dev/null
+++ b/src/builtin_structures/balance_symbols.py
@@ -0,0 +1,40 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+'''
+Given a N different open and close braces in a string "( { [ } ] )".
+How do you check whether the string has matching braces.
+'''
+
+from collections import Counter
+def check_if_balance(string):
+    '''
+    >>> check_if_balance('{[[(])}]')
+    True
+    >>> check_if_balance('{[[()}]')
+    False
+    >>> check_if_balance('')
+    True
+    '''
+    table = Counter()
+    for i in string:
+
+        index = str(ord(i))[0]
+        if i in '{[(':
+            table[index] += 1
+
+        elif i in ')}]':
+            table[index] -= 1
+
+    for i in table.values():
+        if i !=-0:
+            return False
+    return True
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/builtin_structures/check_if_2_numbers_sum_to_k.py b/src/builtin_structures/check_if_2_numbers_sum_to_k.py
new file mode 100755
index 0000000..b9d7cbf
--- /dev/null
+++ b/src/builtin_structures/check_if_2_numbers_sum_to_k.py
@@ -0,0 +1,71 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+"""
+Given an integer x and an unsorted array of integers, describe an
+algorithm to determine whether two of the numbers add up to x.
+
+1. Using hash tables.
+2. Sorting the array and keeping two pointers in the array, one in
+the beginning and one in the end. Whenever the sum of the current
+two integers is less than x, move the first pointer forwards, and
+whenever the sum is greater than x, move the second pointer
+backwards. O(nln n).
+3. Create a BST with x minus each element in the array.
+Check whether any element of the array appears in the BST.
+It takes O(nlog n) times two.
+"""
+
+from collections import defaultdict, Counter
+
+def check_sum(array, k):
+    '''
+    >>> check_sum([3, 2, 6, 7, 9, 1], 8)
+    [(6, 2), (1, 7)]
+    >>> check_sum([5, 2, 6, 7, 9, 1], 4)
+    []
+    >>>
+    '''
+
+    dict = defaultdict()
+    res = []
+
+    for i in array:
+        if k-i in dict:
+            res.append((i, k-i))
+            del dict[k-i]
+        else:
+            dict[i] = 1
+
+    return res
+
+
+def check_sum2(array, k):
+    '''
+    >>> check_sum2([1, 4, 2, 7, 1, 3, 10, 15, 3, 1], 6)
+    set([(3, 3)])
+    >>> check_sum2([1, 4, 2, 7, 1, 3, 10, 15, 3, 1], 0)
+    set([])
+    '''
+
+    dict = Counter()
+    res = set()
+
+    for i in array:
+        dict[i] += 1
+
+    for i in array:
+        if dict[k-i] > 0:
+            if i == k-i and dict[k-i] > 1:
+                    res.add((i, k-i))
+                    dict[k-i] -= 2
+            elif i == k-i:
+                res.add((i, k-i))
+                dict[k-i] -= 1
+
+    return res
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/builtin_structures/check_if_3_numbers_sum_to_zero.py b/src/builtin_structures/check_if_3_numbers_sum_to_zero.py
new file mode 100755
index 0000000..33c3e3e
--- /dev/null
+++ b/src/builtin_structures/check_if_3_numbers_sum_to_zero.py
@@ -0,0 +1,36 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' Determine if an Array of integers contains 3 numbers that sum to 0 '''
+
+from collections import defaultdict
+
+def find_3_number(array):
+    '''
+    >>> find_3_number([1,5,56,11,-3,-12])
+    1 11 -12
+    True
+    >>> find_3_number([] )
+    False
+    '''
+    hash_ = defaultdict()
+    for i in array:
+        hash_[i] = 1
+
+    for i, x in enumerate(array):
+        for y in array[i+1:]:
+            if -(x+y) in hash_:
+                print x, y, -(x+y)
+                return True
+
+    return False
+
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/builtin_structures/check_non_overlapping_intervals.py b/src/builtin_structures/check_non_overlapping_intervals.py
new file mode 100755
index 0000000..f8213ef
--- /dev/null
+++ b/src/builtin_structures/check_non_overlapping_intervals.py
@@ -0,0 +1,35 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+'''
+given an array of intervals, return max number of non-overlapping intervals
+'''
+
+from collections import defaultdict
+
+def non_overlapping(array):
+    '''
+    >>> non_overlapping([(1,2), (2,5), (1, 6)])
+    [[(1, 2), (2, 5)]]
+    >>> non_overlapping([(1,4), (2,5), (3, 6)])
+    []
+    '''
+    total = []
+
+    for i, t in enumerate(array):
+        start = t[0]
+        end = t[1]
+        for tt in array[i+1:] :
+            if end <= tt[0]:
+                total.append([(start, end), (tt[0], tt[1])])
+
+    return total
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/builtin_structures/convert_numerical_bases.py b/src/builtin_structures/convert_numerical_bases.py
new file mode 100755
index 0000000..999d40e
--- /dev/null
+++ b/src/builtin_structures/convert_numerical_bases.py
@@ -0,0 +1,64 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' convert an integer to a string in any base'''
+
+def convert_from_dec_to_any_base(number, base):
+    '''
+    >>> number, base = 9, 2
+    >>> convert_from_dec_to_any_base(number, base)
+    '1001'
+    '''
+
+    convertString = '012345679ABCDEF'
+
+    if number < base:
+        return convertString[number]
+
+    else:
+        return convert_from_dec_to_any_base(number//base, base) + \
+                                            convertString[number%base]
+
+
+
+def convert_from_decimal_to_binary(number, base):
+    '''
+    >>> number, base = 9, 2
+    >>> convert_from_decimal_to_binary(number, base)
+    1001
+    '''
+
+    multiplier, result = 1, 0
+
+    while number > 0:
+        result += number%base*multiplier
+        multiplier *= 10
+        number = number//base
+
+    return result
+
+
+
+def convert_from_decimal_larger_bases(number, base):
+    '''
+    >>> number, base = 31, 16
+    >>> convert_from_decimal_larger_bases(number, base)
+    '1F'
+    '''
+    strings = "0123456789ABCDEFGHIJ"
+    result = ""
+
+    while number > 0:
+        digit = number%base
+        result = strings[digit] + result
+        number = number//base
+
+    return result
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/further_examples/arrays_and_strings/conv_str2int.py b/src/builtin_structures/convert_str_2_int.py
old mode 100644
new mode 100755
similarity index 61%
rename from src/further_examples/arrays_and_strings/conv_str2int.py
rename to src/builtin_structures/convert_str_2_int.py
index ec7f8c3..bdf875d
--- a/src/further_examples/arrays_and_strings/conv_str2int.py
+++ b/src/builtin_structures/convert_str_2_int.py
@@ -1,9 +1,10 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
-''' two routines to convert str to int and int to str:
-    - bc: negative str, zero, exp numbers (ex. 1e5), other bases, NAN 
+__author__ = "bt3"
+
+
+def conv_int2str(int1):
+    '''
     >>> conv_str2int('367')
     367
     >>> conv_str2int('0')
@@ -12,46 +13,59 @@
     -10
     >>> conv_str2int('1e5')
     100000
-    >>> conv_int2str(0)
-    '0'
-    >>> conv_int2str(1e5)
-    '100000' 
-    >>> conv_int2str(367)
-    '367'
-    >>> conv_int2str(-10)
-    '-10'
-'''
+    '''
 
-def conv_int2str(int1):
     aux_dict = {key:value for key in range(10) for value in '0123456789'[key]}
-    if int1 == 0: return '0'    # REMEMBER TO HANDLE 0
-    if int1 < 0:                # REMEMBER TO HANDLE NEGATIVE
+
+    if int1 == 0:
+        return '0'
+    elif int1 < 0:
         sign = '-'
         int1 = int1*(-1)
     else:
         sign = ''
+
+
     aux_ls = []
+
     while int1 > 0:
         c = int1%10
         int1 = int1//10
         cadd = aux_dict[c]
         aux_ls.append(cadd)
-    aux_ls.reverse()            # REMEMBER TO REVERSE
+
+    aux_ls.reverse()
+
     return sign + ''.join(aux_ls)
-    
+
 
 
 def conv_str2int(str1):
-    if not str1: return None
+    '''
+    >>> conv_int2str(0)
+    '0'
+    >>> conv_int2str(1e5)
+    '100000'
+    >>> conv_int2str(367)
+    '367'
+    >>> conv_int2str(-10)
+    '-10'
+    '''
+    if not str1:
+        return None
+
     aux_dict = {key:value for value in range(10) for key in '0123456789'[value]}
-    if str1[0] == '-': 
+
+    if str1[0] == '-':
         sign = -1
-        str1 = str1[1:]                 # REMEMBER TO CUT THE SIGN FROM THE STR
-    else: 
+        str1 = str1[1:]
+    else:
         sign = 1
+
     dec, result = 1, 0
-    for i in range(len(str1)-1, -1, -1): # REMEMBER TO FINISH IN -1, NOT 0, AND
-        aux = str1[i]                    # AND DO THE STEPS -1
+
+    for i in range(len(str1)-1, -1, -1):
+        aux = str1[i]
         if aux == 'e':
             exp_num = conv_str2int(str1[i+1:])
             number = conv_str2int(str1[:i])
@@ -59,8 +73,9 @@ def conv_str2int(str1):
             break
         result += aux_dict[aux]*dec
         dec *= 10
+
     return result*sign
-    
+
 
 if __name__ == '__main__':
     import doctest
diff --git a/src/examples_in_my_book/general_problems/dicts/count_unique_words_.py b/src/builtin_structures/count_unique_words_On2.py
old mode 100644
new mode 100755
similarity index 81%
rename from src/examples_in_my_book/general_problems/dicts/count_unique_words_.py
rename to src/builtin_structures/count_unique_words_On2.py
index fdf66c3..7b54490
--- a/src/examples_in_my_book/general_problems/dicts/count_unique_words_.py
+++ b/src/builtin_structures/count_unique_words_On2.py
@@ -1,21 +1,26 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 import collections
 import string
 import sys
 
+
 def count_unique_word():
+
     words = collections.defaultdict(int)
-    strip = string.whitespace + string.punctuation + string.digits + "\"'" 
+
+    strip = string.whitespace + string.punctuation + string.digits + "\"'"
+
     for filename in sys.argv[1:]:
         with open(filename) as file:
-            for line in 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]))
-        
+
diff --git a/src/builtin_structures/delete_duplicate_char_str.py b/src/builtin_structures/delete_duplicate_char_str.py
new file mode 100755
index 0000000..9f8b9fc
--- /dev/null
+++ b/src/builtin_structures/delete_duplicate_char_str.py
@@ -0,0 +1,49 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+'''  find and delete all the duplicate characters in a string '''
+
+from collections import Counter
+
+def delete_unique(str1):
+    '''
+    >>> delete_unique("Trust no one")
+    'on'
+    >>> delete_unique("Mulder?")
+    ''
+    '''
+
+    str_strip = ''.join(str1.split())
+    repeat = Counter()
+
+    for c in str_strip:
+        repeat[c] += 1
+
+    result = ''
+    for c, count in repeat.items():
+        if count > 1:
+            result += c
+
+    return result
+
+
+def removing_duplicates_seq(str1):
+    '''
+    >>> delete_unique("Trust no one")
+    'on'
+    >>> delete_unique("Mulder?")
+    ''
+    '''
+    seq = str1.split()
+    result = set()
+    for item in seq:
+        if item not in result:
+            #yield item
+            result.add(item)
+    return result
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
diff --git a/src/builtin_structures/fibonacci.py b/src/builtin_structures/fibonacci.py
new file mode 100755
index 0000000..584b611
--- /dev/null
+++ b/src/builtin_structures/fibonacci.py
@@ -0,0 +1,60 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def fib_generator():
+    a, b = 0, 1
+
+    while True:
+        yield b
+        a, b = b, a+b
+
+
+def fib(n):
+    '''
+    >>> fib(2)
+    1
+    >>> fib(5)
+    5
+    >>> fib(7)
+    13
+    '''
+    if n < 3:
+        return 1
+
+    a, b = 0, 1
+    count = 1
+
+    while count < n:
+        count += 1
+        a, b = b, a+b
+
+    return b
+
+
+def fib_rec(n):
+    '''
+    >>> fib_rec(2)
+    1
+    >>> fib_rec(5)
+    5
+    >>> fib_rec(7)
+    13
+    '''
+    if n < 3:
+        return 1
+    return fib_rec(n - 1) + fib_rec(n - 2)
+
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
+    fib = fib_generator()
+    print(next(fib))
+    print(next(fib))
+    print(next(fib))
+    print(next(fib))
diff --git a/src/further_examples/arrays_and_strings/find_0_MxN_replace_cols_rows.py b/src/builtin_structures/find_0_MxN_replace_cols_rows.py
old mode 100644
new mode 100755
similarity index 89%
rename from src/further_examples/arrays_and_strings/find_0_MxN_replace_cols_rows.py
rename to src/builtin_structures/find_0_MxN_replace_cols_rows.py
index f306d83..9ab67c3
--- a/src/further_examples/arrays_and_strings/find_0_MxN_replace_cols_rows.py
+++ b/src/builtin_structures/find_0_MxN_replace_cols_rows.py
@@ -1,8 +1,8 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
-   
 def find_0_MxN(m):
     ''' find 0s in a matrix and replace the col and row to 0s:
     >>> m1 = [[1,2,3,4], [5,6,7,8], [9,10,11,12], [13,14,15,16]]
@@ -13,6 +13,7 @@ def find_0_MxN(m):
     [[0, 2, 3, 4], [0, 0, 0, 0], [0, 10, 11, 12], [0, 14, 15, 16]]
     '''
     index = []
+
     for row in range(len(m)):
         for col in range(len(m[0])):
             if m[row][col] == 0:
@@ -24,9 +25,10 @@ def find_0_MxN(m):
             m[row][i] = 0
         for i in range(len(m[0])):
             m[i][col] = 0
+
     return m
 
-                   
+
 if __name__ == '__main__':
     import doctest
     doctest.testmod()
diff --git a/src/builtin_structures/find_dice_probabilities.py b/src/builtin_structures/find_dice_probabilities.py
new file mode 100755
index 0000000..265c9b1
--- /dev/null
+++ b/src/builtin_structures/find_dice_probabilities.py
@@ -0,0 +1,32 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+'''
+given 2 dice, determine number of ways to sum S if all dice are rolled
+'''
+
+from collections import Counter, defaultdict
+
+def find_dice_probabilities(S=5, n_faces=6):
+    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]]
+
+
+
+
+
+if __name__ == '__main__':
+    results = find_dice_probabilities()
+    assert(results[0] == len(results[1]))
diff --git a/src/builtin_structures/find_edit_distance.py b/src/builtin_structures/find_edit_distance.py
new file mode 100755
index 0000000..6fc6e81
--- /dev/null
+++ b/src/builtin_structures/find_edit_distance.py
@@ -0,0 +1,43 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' computes the edit distance between two strings '''
+
+
+def find_edit_distance(str1, str2):
+    '''
+    >>> s = 'sunday'
+    >>> t = 'saturday'
+    >>> find_edit_distance(s, t)
+    3
+    '''
+
+	m = len(str1)
+	n = len(str2)
+	diff = lambda c1, c2: 0 if c1 == c2 else 1
+
+	E = [[0] * (n + 1) for i in range(m + 1)]
+
+	for i in range(m + 1):
+		E[i][0] = i
+
+    for j in range(1, n + 1):
+		E[0][j] = j
+
+    for i in range(1, m + 1):
+		for j in range(1, n + 1):
+			E[i][j] = min(E[i-1][j] + 1, E[i][j-1] + 1, E[i-1][j-1] + diff(str1[i-1], str2[j-1]))
+
+    return E[m][n]
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
+
+
+
diff --git a/src/builtin_structures/find_first_non_repetead_char.py b/src/builtin_structures/find_first_non_repetead_char.py
new file mode 100755
index 0000000..5489f7d
--- /dev/null
+++ b/src/builtin_structures/find_first_non_repetead_char.py
@@ -0,0 +1,29 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+from collections import Counter
+
+def  find_non_rep_char(s1):
+  '''
+  >>> s1 = 'aabbcceff'
+  >>> find_non_rep_char(s1)
+  e
+  >>> find_non_rep_char('ccc')
+  '''
+
+  aux_dict = Counter()
+
+  for i in s1:
+      aux_dict[i] += 1
+
+  for k, v in aux_dict.items():
+    if v < 2:
+        print k
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/examples_in_my_book/general_problems/numbers/finding_gcd.py b/src/builtin_structures/find_gcd.py
old mode 100644
new mode 100755
similarity index 73%
rename from src/examples_in_my_book/general_problems/numbers/finding_gcd.py
rename to src/builtin_structures/find_gcd.py
index dd7cb82..d9dfa4c
--- a/src/examples_in_my_book/general_problems/numbers/finding_gcd.py
+++ b/src/builtin_structures/find_gcd.py
@@ -1,13 +1,14 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 
 def finding_gcd(a, b):
     ''' implements the greatest common divider algorithm '''
     while(b != 0):
         result = b
-        a, b = b, a % b        
+        a, b = b, a % b
     return result
 
 
@@ -22,7 +23,7 @@ def test_finding_gcd():
 
 
 
-    
-    
-    
-    
+
+
+
+
diff --git a/src/builtin_structures/find_if_substr.py b/src/builtin_structures/find_if_substr.py
new file mode 100755
index 0000000..8166bda
--- /dev/null
+++ b/src/builtin_structures/find_if_substr.py
@@ -0,0 +1,36 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def find_substr(s1, s2):
+
+    if len(s1) < len(s2):
+        bs = s2
+        ss = s1
+    else:
+        bs = s1
+        ss = s2
+
+    ps = 0
+
+    for c in bs:
+
+        if ss[ps] == c:
+            ps += 1
+        else:
+            ps = 0
+
+        if ps == len(ss)-1:
+            return True
+
+    return False
+
+
+
+if __name__ == '__main__':
+    s1 = 'buffy is a vampire slayer'
+    s2 = 'vampire'
+    s3 = 'angel'
+    assert(find_substr(s2, s1) == True)
+    assert(find_substr(s3, s1) == False)
\ No newline at end of file
diff --git a/src/builtin_structures/find_if_unique_char.py b/src/builtin_structures/find_if_unique_char.py
new file mode 100755
index 0000000..3e88c46
--- /dev/null
+++ b/src/builtin_structures/find_if_unique_char.py
@@ -0,0 +1,32 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+import collections
+
+def find_if_unique_chars(word):
+    """
+    >>> find_if_unique_chars('abcde')
+    True
+    >>> find_if_unique_chars('abcae')
+    False
+    """
+
+    unique = True
+
+    counter = collections.Counter()
+
+    for c in word:
+        if not counter[c]:
+            counter[c] += 1
+        else:
+            unique = False
+
+    return unique
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/builtin_structures/find_largest_sum.py b/src/builtin_structures/find_largest_sum.py
new file mode 100755
index 0000000..9b79ac8
--- /dev/null
+++ b/src/builtin_structures/find_largest_sum.py
@@ -0,0 +1,42 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+'''
+   You are given an array of integers (both positive and negative).
+   Find the contiguous sequence with the largest sum.
+'''
+
+
+def find_largest_sum(array):
+    '''
+    >>> find_largest_sum([-1, 2, -3, 5, 3, 1, -16, 7, 1, -13, 1])
+    9
+    >>> find_largest_sum([])
+    0
+    >>> find_largest_sum([1])
+    1
+    '''
+
+    sum_ = 0
+    sum_here = 0
+
+    for i in array:
+
+        sum_here +=  i
+
+        if sum_here < 0:
+            sum_here = 0
+
+        if sum_ < sum_here:
+            sum_ = sum_here
+
+    return sum_
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/builtin_structures/find_longest_inc_subseq.py b/src/builtin_structures/find_longest_inc_subseq.py
new file mode 100755
index 0000000..38e3b9b
--- /dev/null
+++ b/src/builtin_structures/find_longest_inc_subseq.py
@@ -0,0 +1,34 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+''' find the longest continuous increasing subsequence'''
+
+
+def find_long_con_inc(seq):
+    '''
+    >>> find_long_con_inc([1, -2, 3, 5, 1, -1, 4, -1, 6])
+    [-2, 3, 5]
+    >>> find_long_con_inc([1, 3, -2, 3, 5, 6])
+    [-2, 3, 5, 6]
+    >>> find_long_con_inc([1, 3, 4, -13, 2, 5, 8, -1, 2,-17])
+    [-13, 2, 5, 8]
+    '''
+
+    res, aux = [], []
+    seq.append(-float('infinity'))
+
+    for i, n in enumerate(seq[:-1]):
+        aux.append(n)
+        if n > seq[i+1]:
+            if len(res) < len(aux):
+                res = aux[:]
+            aux = []
+
+    return res
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
diff --git a/src/builtin_structures/find_longest_str_unique_chars.py b/src/builtin_structures/find_longest_str_unique_chars.py
new file mode 100755
index 0000000..a73144e
--- /dev/null
+++ b/src/builtin_structures/find_longest_str_unique_chars.py
@@ -0,0 +1,38 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+'''
+given a string, find longest string with unique characters
+'''
+
+def find_longest(string):
+    '''
+    >>> find_longest('abfgrhgtrdsandwejfhdasjcbdsjvrejwghireeej')
+    'wejfhdas'
+    >>> find_longest('abcabcabcabcdefabcccc')
+    'defabc'
+    '''
+    maxs = ''
+    result = ''
+
+    for c in string:
+        if c in result:
+            if len(maxs) < len(result):
+                maxs = result
+            result = ''
+        else:
+            result += c
+
+    if result and len(maxs) < len(result):
+        maxs = result
+
+    return maxs
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/builtin_structures/find_non_repeating_number.py b/src/builtin_structures/find_non_repeating_number.py
new file mode 100755
index 0000000..8d1dc14
--- /dev/null
+++ b/src/builtin_structures/find_non_repeating_number.py
@@ -0,0 +1,33 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+from collections import defaultdict
+
+
+def find_unique_number(array):
+    '''
+    >>> find_unique_number([1, 3, 6, 1, 5, 6, 9, 3, 7])
+    [1, 6, 3]
+    >>> find_unique_number([1, 3, 5, 6, 9, 7])
+    []
+    '''
+
+    table = defaultdict()
+    total = []
+
+    for i in array:
+        if i in table:
+            total.append(i)
+        else:
+            table[i] = 1
+
+    return total
+
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/builtin_structures/find_product_without_division.py b/src/builtin_structures/find_product_without_division.py
new file mode 100755
index 0000000..611842e
--- /dev/null
+++ b/src/builtin_structures/find_product_without_division.py
@@ -0,0 +1,42 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+'''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
+'''
+
+
+def find_product_without_division(seq):
+    '''
+    >>> seq = [2,3,4]
+    >>> find_product_without_division(seq)
+    [12, 8, 6]
+    '''
+
+    forw = []
+    bacw = []
+
+    for i in range(len(seq)):
+
+        prod_f, prod_b = 1, 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)
+
+    for i in range(len(seq)):
+        seq[i] = forw[i] * bacw[i]
+
+    return seq
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/examples_in_my_book/general_problems/dicts/find_top_N_recurring_words.py b/src/builtin_structures/find_top_N_recurring_words.py
old mode 100644
new mode 100755
similarity index 60%
rename from src/examples_in_my_book/general_problems/dicts/find_top_N_recurring_words.py
rename to src/builtin_structures/find_top_N_recurring_words.py
index d699fe7..91dfc8f
--- a/src/examples_in_my_book/general_problems/dicts/find_top_N_recurring_words.py
+++ b/src/builtin_structures/find_top_N_recurring_words.py
@@ -1,6 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 from collections import Counter
 
@@ -8,24 +8,20 @@ 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 '''
+        3) return the last N words
+    '''
 
     dcounter = Counter()
     for word in seq.split():
-        dcounter[word] += 1    
+        dcounter[word] += 1
+
     return dcounter.most_common(N)
-    
 
 
-def test_find_top_N_recurring_words(module_name='this module'):
+
+if __name__ == '__main__':
     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()
 
diff --git a/src/builtin_structures/find_two_missing_numbers_in_sequence.py b/src/builtin_structures/find_two_missing_numbers_in_sequence.py
new file mode 100755
index 0000000..e532a18
--- /dev/null
+++ b/src/builtin_structures/find_two_missing_numbers_in_sequence.py
@@ -0,0 +1,56 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+"""
+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.
+"""
+
+import math
+
+def find_two_missing_numbers(l1):
+    '''
+    >>> l1 = [1, 3, 5]
+    >>> find_two_missing_numbers(l1)
+    (4, 2)
+    '''
+
+    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 int(num1), int(num2)
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
+
+
+
+
+
diff --git a/src/builtin_structures/get_float_rep_bin.py b/src/builtin_structures/get_float_rep_bin.py
new file mode 100755
index 0000000..156cb77
--- /dev/null
+++ b/src/builtin_structures/get_float_rep_bin.py
@@ -0,0 +1,29 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' Given a real number between 0 and 1 (eg: 0.72), this method print the
+    binary representation. If the Number cannot be represented accurately
+    in binary, with at exit most 32 chars, print error:
+'''
+
+def get_float_rep(num):
+    if num >= 1 or num <= 0: return 'Error 1'
+    result = '.'
+    while num:
+        if len(result) >= 32: return 'Error 2', result
+        r = num*2
+        if r >= 1:
+            result += '1'
+            num = r - 1
+        else:
+            result += '0'
+            num = r
+    return result
+
+
+if __name__ == '__main__':
+    print get_float_rep(0.72) #('Error 2', '.1011100001010001111010111000010')
+    print get_float_rep(0.1) # ('Error 2', '.0001100110011001100110011001100')
+    print get_float_rep(0.5) #'.1'
diff --git a/src/builtin_structures/interserction_two_arrays.py b/src/builtin_structures/interserction_two_arrays.py
new file mode 100755
index 0000000..b0868ef
--- /dev/null
+++ b/src/builtin_structures/interserction_two_arrays.py
@@ -0,0 +1,63 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def intersection_two_arrays_sets(seq1, seq2):
+    '''
+    >>> intersection_two_arrays_sets([1,2,3,5,7,8], [3,5,6])
+    set([3, 5])
+    >>> intersection_two_arrays_sets([1,2,7,8], [3,5,6])
+    set([])
+    '''
+    # O(n)
+    set1 = set(seq1)
+    set2 = set(seq2)
+
+    return set1.intersection(set2)  #same as list(set1 & set2)
+
+
+def intersection_two_arrays_On2(seq1, seq2):
+    '''
+    >>> intersection_two_arrays_On2([1,2,3,5,7,8], [3,5,6])
+    [3, 5]
+    >>> intersection_two_arrays_On2([1,2,7,8], [3,5,6])
+    []
+    '''
+
+    final = []
+
+    for i in seq1:
+        for j in seq2:
+            if i == j:
+                final.append(i)
+
+    return final
+
+
+def intersection_two_arrays_On(seq1, seq2):
+    '''
+    >>> intersection_two_arrays_On([1,2,3,5,7,8], [3,5,6])
+    [5, 3]
+    >>> intersection_two_arrays_On([1,2,7,8], [3,5,6])
+    []
+    '''
+
+    final = []
+
+    while seq1 and seq2:
+
+        if seq1[-1] == seq2[-1]:
+            final.append(seq1.pop())
+            seq2.pop()
+        elif seq1[-1] > seq2[-1]:
+            seq1.pop()
+        else:
+            seq2.pop()
+
+    return final
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
diff --git a/src/builtin_structures/max_subarray_stocks.py b/src/builtin_structures/max_subarray_stocks.py
new file mode 100755
index 0000000..11bf739
--- /dev/null
+++ b/src/builtin_structures/max_subarray_stocks.py
@@ -0,0 +1,54 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+def beating_stock(array):
+
+    imin = 0
+
+    # first deal is just buying in the next day (1)
+    deal = [array[1] - array[imin], imin, 1]
+
+    for i, d in enumerate(array):
+
+        deal_here = d - array[imin]
+
+        if deal_here > deal[0]:
+            deal = [deal_here, imin, i]
+
+        elif d < array[imin]:
+            imin = i
+
+    return deal[0], array[deal[1]], array[deal[2]]
+
+
+def beating_stock2(array):
+
+    deal = 0
+    min_value = array[0]
+
+    for i, d in enumerate(array):
+
+        deal_here = d - min_value
+
+        if deal_here > deal:
+            deal = deal_here
+
+        else:
+            if min_value > array[i]:
+                min_value = array[i]
+
+    return deal
+
+
+
+if __name__ == '__main__':
+    array = [7, 2, 3, 6, 5, 8, 5, 3, 4]
+
+    deal = beating_stock(array)
+    print("Profit: %d, buying at %d, selling at %d." %(deal[0], deal[1], deal[2]))
+
+    deal = beating_stock2(array)
+    print "Profit: " + str(deal)
\ No newline at end of file
diff --git a/src/builtin_structures/number_of_zeros_factorial.txt b/src/builtin_structures/number_of_zeros_factorial.txt
new file mode 100755
index 0000000..066451c
--- /dev/null
+++ b/src/builtin_structures/number_of_zeros_factorial.txt
@@ -0,0 +1,15 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+How to know how many 0 are in 100!
+
+You look for the primes that multiply to 10, i.e. 2 and 5.
+
+There are more 5 than 2s so you can count the fives.
+
+there is 100/5 = 20, so 20 5s. However, there are two 5s in 25, 50, 75 and 100.
+
+result: 20+4 = 24
\ No newline at end of file
diff --git a/src/builtin_structures/palindrome.py b/src/builtin_structures/palindrome.py
new file mode 100755
index 0000000..0002cee
--- /dev/null
+++ b/src/builtin_structures/palindrome.py
@@ -0,0 +1,33 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+from collections import defaultdict
+
+def is_palindrome(array):
+    '''
+    >>> is_palindrome('subi no onibus')
+    True
+    >>> is_palindrome('helllo there')
+    False
+    >>> is_palindrome('h')
+    True
+    >>> is_palindrome('')
+    True
+    '''
+    array = array.strip(' ')
+    if len(array) < 2:
+        return True
+
+    if array[0] == array[-1]:
+        return is_palindrome(array[1:-1])
+    else:
+        return False
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/builtin_structures/permutations.py b/src/builtin_structures/permutations.py
new file mode 100755
index 0000000..14c4134
--- /dev/null
+++ b/src/builtin_structures/permutations.py
@@ -0,0 +1,70 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+def perm(str1):
+    '''
+    >>> perm('123')
+    ['123', '132', '231', '213', '312', '321']
+    '''
+
+    if len(str1) < 2:
+        return str1
+
+    res = []
+    for i, c in enumerate(str1):
+        for cc in perm(str1[i+1:] + str1[:i]):
+            res.append(c + cc)
+    return res
+
+
+def perm2(str1):
+    '''
+    >>> perm2('123')
+    ['123', '132', '213', '231', '312', '321']
+    '''
+    from itertools import permutations
+    return [''.join(p) for p in permutations(str1)]
+
+
+def ispermutation(s1, s2):
+    '''
+    >>> ispermutation('231', '123')
+    True
+    >>> ispermutation('231', '153')
+    False
+    '''
+
+    from collections import Counter
+    aux = Counter()
+    for i in s1:
+        aux[i] += 1
+    for i in s2:
+        aux[i] -= 1
+    for v in aux.values():
+        if v != 0:
+            return False
+    return True
+
+
+
+
+def ispermutation2(s1, s2):
+    '''
+    >>> ispermutation2('231', '123')
+    True
+    >>> ispermutation2('231', '153')
+    False
+    '''
+    if sorted(s1) == sorted(s2):
+        return True
+    else:
+        return False
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
diff --git a/src/builtin_structures/permutations_alphanumeric.py b/src/builtin_structures/permutations_alphanumeric.py
new file mode 100755
index 0000000..1c0ff96
--- /dev/null
+++ b/src/builtin_structures/permutations_alphanumeric.py
@@ -0,0 +1,37 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' Write code to generate all possible case permutations of a given
+lower-cased string
+'''
+
+def alpha_permutation(string):
+    '''
+    >>> alpha_permutation('0ab')
+    ['0Ab', '0Ab', '0ab', '0ab', '0Ba', '0Ba', '0ba', '0ba', 'ab0', 'a0b', 'a0b', 'b0a', 'b0a', 'ba0']
+    >>> alpha_permutation('')
+    ''
+    '''
+
+    if len(string) < 2:
+        return string
+
+    result = []
+
+    for i, c in enumerate(string):
+        rest =  string[i+1:] + string[:i]
+        for cc in alpha_permutation(rest):
+            if cc.isalpha():
+                result.append(c.upper() + cc)
+            result.append(c + cc)
+
+    return result
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/builtin_structures/primes.py b/src/builtin_structures/primes.py
new file mode 100755
index 0000000..59dc1ed
--- /dev/null
+++ b/src/builtin_structures/primes.py
@@ -0,0 +1,47 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+'''
+find prime factors of a number.
+'''
+
+import math
+import random
+
+def find_prime_factors(n):
+    '''
+    >>> find_prime_factors(14)
+    [2, 7]
+    >>> find_prime_factors(19)
+    []
+    '''
+
+    divisors = [d for d in range(2, n//2 + 1) if n % d == 0]
+    primes = [d for d in divisors if is_prime(d)]
+
+    return primes
+
+
+def is_prime(n):
+    for j in range(2, int(math.sqrt(n))):
+        if (n % j) == 0:
+            return False
+    return True
+
+
+''' return a n-bit prime '''
+def generate_prime(number=3):
+    while 1:
+        p = random.randint(pow(2, number-2), pow(2, number-1)-1)
+        p = 2 * p + 1
+        if find_prime_factors(p):
+            return p
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/builtin_structures/prod_other_ints.py b/src/builtin_structures/prod_other_ints.py
new file mode 100755
index 0000000..3caa9bf
--- /dev/null
+++ b/src/builtin_structures/prod_other_ints.py
@@ -0,0 +1,28 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def get_products_of_all_except_at_index(array):
+    '''
+    >>> a = [1, 7, 3, 4]
+    >>> get_products_of_all_except_at_index(a)
+    [84, 12, 28, 21]
+    '''
+    total = 1
+    for n in array:
+        total *= n
+
+    new_array = []
+    for n in array:
+        if n is not 0:
+            item = total/n
+            new_array.append(item)
+        else:
+            new_array.append(n)
+
+    return new_array
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/builtin_structures/ransom_note.py b/src/builtin_structures/ransom_note.py
new file mode 100755
index 0000000..75a07f8
--- /dev/null
+++ b/src/builtin_structures/ransom_note.py
@@ -0,0 +1,34 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+from collections import Counter
+
+def check_if_ransom_note(magazines, note):
+    count = Counter()
+    pm, pn = 0, 0
+
+    while pn < len(note) and pm < len(magazines):
+        char_note = note[pn]
+        if count[char_note]>0:
+            count[char_note] -= 1
+            pn += 1
+        else:
+            char_magazine = magazines[pm]
+            count[char_magazine] += 1
+            pm +=1
+
+    return pn == len(note)
+
+
+
+if __name__ == '__main__':
+
+    magazines1 = "avfegthhgrebvkdsvnijnvyijfdmckdsmovkmmfvskumvl;cdkmioswckofjbkreenyukjemjgnmkmvkmnvdkmvkr g gmvdvmldm vldfkmbldkmlvdkm"
+    magazines2 = "adfsfa"
+    note = "you should disobey"
+
+    print(check_if_ransom_note(magazines1, note))
+    print(check_if_ransom_note(magazines2, note))
diff --git a/src/builtin_structures/reverse_string.py b/src/builtin_structures/reverse_string.py
new file mode 100755
index 0000000..e20d32f
--- /dev/null
+++ b/src/builtin_structures/reverse_string.py
@@ -0,0 +1,37 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def revert(string):
+    '''
+    >>> s = 'hello'
+    >>> revert(s)
+    'olleh'
+    >>> revert('')
+    ''
+    '''
+    return string[::-1]
+
+
+
+def reverse_string_inplace(s):
+    '''
+    >>> s = 'hello'
+    >>> reverse_string_inplace(s)
+    'olleh'
+    >>> reverse_string_inplace('')
+    ''
+    '''
+    if s:
+        s = s[-1] + reverse_string_inplace(s[:-1])
+    return s
+
+
+
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/builtin_structures/reverse_words.py b/src/builtin_structures/reverse_words.py
new file mode 100755
index 0000000..775ad99
--- /dev/null
+++ b/src/builtin_structures/reverse_words.py
@@ -0,0 +1,45 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+def reversing_words(word):
+    """
+    >>> reversing_words('buffy is awesome')
+    'awesome is buffy'
+    """
+    new_word = []
+
+    words = word.split(' ')
+    for word in words[::-1]:
+        new_word.append(word)
+
+    return " ".join(new_word)
+
+
+def reversing_words2(s):
+    """
+    >>> reversing_words2('buffy is awesome')
+    'awesome is buffy'
+    """
+    words = s.split()
+    return ' '.join(reversed(words))
+
+
+def reversing_words3(s):
+    """
+    >>> reversing_words('buffy is awesome')
+    'awesome is buffy'
+    """
+    words = s.split(' ')
+    words.reverse()
+    return ' '.join(words)
+
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/further_examples/arrays_and_strings/rotate_NxN.py b/src/builtin_structures/rotate_NxN.py
old mode 100644
new mode 100755
similarity index 85%
rename from src/further_examples/arrays_and_strings/rotate_NxN.py
rename to src/builtin_structures/rotate_NxN.py
index d238a94..f841bad
--- a/src/further_examples/arrays_and_strings/rotate_NxN.py
+++ b/src/builtin_structures/rotate_NxN.py
@@ -1,8 +1,7 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
-   
 def rotate_NxN(m):
     n = len(m)
     for layer in range(n//2):
@@ -16,7 +15,7 @@ def rotate_NxN(m):
             m[last][last-offset] = m[i][last]
             m[i][last] = top
     return m
-    
+
 
 
 def main():
@@ -25,7 +24,7 @@ def main():
     assert(rotate_NxN(m) == mr)
     m2 = [[1,2,3],[4,5,6],[7,8,9]]
     print(rotate_NxN(m2))
-                   
+
 if __name__ == '__main__':
     main()
 
diff --git a/src/examples_in_my_book/general_problems/dicts/runtime_dicts_with_timeit_module.py b/src/builtin_structures/runtime_dicts_with_timeit_module.py
old mode 100644
new mode 100755
similarity index 58%
rename from src/examples_in_my_book/general_problems/dicts/runtime_dicts_with_timeit_module.py
rename to src/builtin_structures/runtime_dicts_with_timeit_module.py
index c8138fc..b54c637
--- a/src/examples_in_my_book/general_problems/dicts/runtime_dicts_with_timeit_module.py
+++ b/src/builtin_structures/runtime_dicts_with_timeit_module.py
@@ -1,9 +1,19 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
+__author__ = "bt3"
 
-'''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. '''
+'''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
@@ -19,7 +29,7 @@
     print("%d,%10.3f,%10.3f" % (i, lst_time, d_time))
 
 
-""" There rersults are:
+""" There results are:
 10000,     0.192,     0.002
 30000,     0.600,     0.002
 50000,     1.000,     0.002
diff --git a/src/examples_in_my_book/general_problems/lists/runtime_lists_with_timeit_module.py b/src/builtin_structures/runtime_lists_with_timeit_module.py
old mode 100644
new mode 100755
similarity index 97%
rename from src/examples_in_my_book/general_problems/lists/runtime_lists_with_timeit_module.py
rename to src/builtin_structures/runtime_lists_with_timeit_module.py
index c9841bc..f7da733
--- a/src/examples_in_my_book/general_problems/lists/runtime_lists_with_timeit_module.py
+++ b/src/builtin_structures/runtime_lists_with_timeit_module.py
@@ -1,7 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
+__author__ = "bt3"
 
 '''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. '''
 
diff --git a/src/examples_in_my_book/general_problems/numbers/search_entry_matrix.py b/src/builtin_structures/search_entry_matrix.py
old mode 100644
new mode 100755
similarity index 72%
rename from src/examples_in_my_book/general_problems/numbers/search_entry_matrix.py
rename to src/builtin_structures/search_entry_matrix.py
index 0ddd73b..6d70fdd
--- a/src/examples_in_my_book/general_problems/numbers/search_entry_matrix.py
+++ b/src/builtin_structures/search_entry_matrix.py
@@ -1,18 +1,22 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
+__author__ = "bt3"
 
 
+''' 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).
+'''
+
 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
@@ -20,8 +24,9 @@ def find_elem_matrix_bool(m1, value):
             col-=1
         else:
             row+=1
+
     return found
-    
+
 
 
 def test_find_elem_matrix_bool(module_name='this module'):
@@ -30,9 +35,6 @@ def test_find_elem_matrix_bool(module_name='this module'):
     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__':
diff --git a/src/further_examples/arrays_and_strings/simple_str_comprension.py b/src/builtin_structures/simple_str_comprension.py
old mode 100644
new mode 100755
similarity index 54%
rename from src/further_examples/arrays_and_strings/simple_str_comprension.py
rename to src/builtin_structures/simple_str_comprension.py
index d357e69..6a516df
--- a/src/further_examples/arrays_and_strings/simple_str_comprension.py
+++ b/src/builtin_structures/simple_str_comprension.py
@@ -1,11 +1,19 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
-   
 from collections import Counter
+
 def str_comp(s):
-    ''' basic str compression with counts of repeated char'''
+    '''
+    >>> s1 = 'aabcccccaaa'
+    >>> str_comp(s1)
+    'a2b1c5a3'
+    >>> str_comp('')
+    ''
+    '''
+
     count, last = 1, ''
     list_aux = []
     for i, c in enumerate(s):
@@ -17,16 +25,10 @@ def str_comp(s):
             list_aux.append(c)
             count = 1
             last = c
-    list_aux.append(str(count))    
+    list_aux.append(str(count))
     return ''.join(list_aux)
-        
 
-def main():
-    s1 = 'aabcccccaaa'
-    s2 = ''
-    print(str_comp(s1)) # 'a2b1c5a3'
-    print(str_comp(s2))
-                   
-if __name__ == '__main__':
-    main()
 
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
diff --git a/src/builtin_structures/sum_two_numbers_as_strings.py b/src/builtin_structures/sum_two_numbers_as_strings.py
new file mode 100755
index 0000000..ec05a14
--- /dev/null
+++ b/src/builtin_structures/sum_two_numbers_as_strings.py
@@ -0,0 +1,41 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+'''
+find the sum of two integers represented as strings,
+return the sum as string, i.e "123" and "456" would return "579"
+'''
+
+
+def get_number(s):
+    count = 1
+    num = 0
+    p = len(s) -1
+    while p >= 0:
+        num = num + int(s[p])*count
+        count *= 10
+        p -= 1
+    return num
+
+
+def sum_string(s1, s2):
+    '''
+    >>> sum_string('10', '5')
+    '15'
+    >>> sum_string('0', '1')
+    '1'
+    >>> sum_string('123', '456')
+    '579'
+    '''
+
+    n1 = get_number(s1)
+    n2 = get_number(s2)
+    return str(n2 + n1)
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/examples_in_my_book/adt/linked_lists/linked_list_from_stack.py b/src/examples_in_my_book/adt/linked_lists/linked_list_from_stack.py
deleted file mode 100644
index 52efaf6..0000000
--- a/src/examples_in_my_book/adt/linked_lists/linked_list_from_stack.py
+++ /dev/null
@@ -1,71 +0,0 @@
-#!/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()
diff --git a/src/examples_in_my_book/adt/linked_lists/linkedlist.py b/src/examples_in_my_book/adt/linked_lists/linkedlist.py
deleted file mode 100644
index 5a8aa6d..0000000
--- a/src/examples_in_my_book/adt/linked_lists/linkedlist.py
+++ /dev/null
@@ -1,65 +0,0 @@
-#!/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()
-
-
diff --git a/src/examples_in_my_book/adt/linked_lists/node.py b/src/examples_in_my_book/adt/linked_lists/node.py
deleted file mode 100644
index 5b6caf9..0000000
--- a/src/examples_in_my_book/adt/linked_lists/node.py
+++ /dev/null
@@ -1,23 +0,0 @@
-#!/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
-
-
diff --git a/src/examples_in_my_book/adt/linked_lists/ordered_list.py b/src/examples_in_my_book/adt/linked_lists/ordered_list.py
deleted file mode 100644
index 50ab9ca..0000000
--- a/src/examples_in_my_book/adt/linked_lists/ordered_list.py
+++ /dev/null
@@ -1,97 +0,0 @@
-#!/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()
-
-
diff --git a/src/examples_in_my_book/adt/queues/deque.py b/src/examples_in_my_book/adt/queues/deque.py
deleted file mode 100644
index 86573bd..0000000
--- a/src/examples_in_my_book/adt/queues/deque.py
+++ /dev/null
@@ -1,46 +0,0 @@
-#!/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()    
diff --git a/src/examples_in_my_book/adt/queues/linked_queue.py b/src/examples_in_my_book/adt/queues/linked_queue.py
deleted file mode 100644
index 4aadc0a..0000000
--- a/src/examples_in_my_book/adt/queues/linked_queue.py
+++ /dev/null
@@ -1,61 +0,0 @@
-#!/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()      
diff --git a/src/examples_in_my_book/adt/queues/palindrome_checker_with_deque.py b/src/examples_in_my_book/adt/queues/palindrome_checker_with_deque.py
deleted file mode 100644
index 9591099..0000000
--- a/src/examples_in_my_book/adt/queues/palindrome_checker_with_deque.py
+++ /dev/null
@@ -1,34 +0,0 @@
-#!/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()   
-
-
diff --git a/src/examples_in_my_book/adt/queues/queue.py b/src/examples_in_my_book/adt/queues/queue.py
deleted file mode 100644
index 92c9fa9..0000000
--- a/src/examples_in_my_book/adt/queues/queue.py
+++ /dev/null
@@ -1,39 +0,0 @@
-#!/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()
diff --git a/src/examples_in_my_book/adt/queues/queue_from_two_stacks.py b/src/examples_in_my_book/adt/queues/queue_from_two_stacks.py
deleted file mode 100644
index 6af795d..0000000
--- a/src/examples_in_my_book/adt/queues/queue_from_two_stacks.py
+++ /dev/null
@@ -1,48 +0,0 @@
-#!/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()
diff --git a/src/examples_in_my_book/adt/queues/rotating_array.py b/src/examples_in_my_book/adt/queues/rotating_array.py
deleted file mode 100644
index 60b3834..0000000
--- a/src/examples_in_my_book/adt/queues/rotating_array.py
+++ /dev/null
@@ -1,27 +0,0 @@
-#!/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()
-
diff --git a/src/examples_in_my_book/adt/stacks/banlance_parenthesis_str_stack.py b/src/examples_in_my_book/adt/stacks/banlance_parenthesis_str_stack.py
deleted file mode 100644
index c285821..0000000
--- a/src/examples_in_my_book/adt/stacks/banlance_parenthesis_str_stack.py
+++ /dev/null
@@ -1,40 +0,0 @@
-#!/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()
diff --git a/src/examples_in_my_book/adt/stacks/linked_stack.py b/src/examples_in_my_book/adt/stacks/linked_stack.py
deleted file mode 100644
index 7f9b154..0000000
--- a/src/examples_in_my_book/adt/stacks/linked_stack.py
+++ /dev/null
@@ -1,52 +0,0 @@
-#!/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()
diff --git a/src/examples_in_my_book/adt/stacks/reverse_string_with_stack.py b/src/examples_in_my_book/adt/stacks/reverse_string_with_stack.py
deleted file mode 100644
index 3f6ec43..0000000
--- a/src/examples_in_my_book/adt/stacks/reverse_string_with_stack.py
+++ /dev/null
@@ -1,30 +0,0 @@
-#!/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()   
-
-
-
-
diff --git a/src/examples_in_my_book/adt/stacks/set_of_stacks.py b/src/examples_in_my_book/adt/stacks/set_of_stacks.py
deleted file mode 100644
index c58e8e7..0000000
--- a/src/examples_in_my_book/adt/stacks/set_of_stacks.py
+++ /dev/null
@@ -1,47 +0,0 @@
-#!/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()
diff --git a/src/examples_in_my_book/adt/stacks/stack.py b/src/examples_in_my_book/adt/stacks/stack.py
deleted file mode 100644
index 0089f63..0000000
--- a/src/examples_in_my_book/adt/stacks/stack.py
+++ /dev/null
@@ -1,40 +0,0 @@
-#!/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()
diff --git a/src/examples_in_my_book/adt/stacks/stack_with_min.py b/src/examples_in_my_book/adt/stacks/stack_with_min.py
deleted file mode 100644
index 405e9f7..0000000
--- a/src/examples_in_my_book/adt/stacks/stack_with_min.py
+++ /dev/null
@@ -1,55 +0,0 @@
-#!/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()   
-
-
diff --git a/src/examples_in_my_book/general_problems/dicts/delete_duplicate_char_str.py b/src/examples_in_my_book/general_problems/dicts/delete_duplicate_char_str.py
deleted file mode 100644
index b186f2b..0000000
--- a/src/examples_in_my_book/general_problems/dicts/delete_duplicate_char_str.py
+++ /dev/null
@@ -1,32 +0,0 @@
-#!/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()
-
diff --git a/src/examples_in_my_book/general_problems/dicts/find_anagram_hash_function.py b/src/examples_in_my_book/general_problems/dicts/find_anagram_hash_function.py
deleted file mode 100644
index fb2a61b..0000000
--- a/src/examples_in_my_book/general_problems/dicts/find_anagram_hash_function.py
+++ /dev/null
@@ -1,34 +0,0 @@
-#!/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()
-
diff --git a/src/examples_in_my_book/general_problems/dicts/find_dice_probabilities.py b/src/examples_in_my_book/general_problems/dicts/find_dice_probabilities.py
deleted file mode 100644
index 10e2d48..0000000
--- a/src/examples_in_my_book/general_problems/dicts/find_dice_probabilities.py
+++ /dev/null
@@ -1,33 +0,0 @@
-#!/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()
diff --git a/src/examples_in_my_book/general_problems/dicts/veirfy_two_strings_are_anagrams.py b/src/examples_in_my_book/general_problems/dicts/veirfy_two_strings_are_anagrams.py
deleted file mode 100644
index c10266c..0000000
--- a/src/examples_in_my_book/general_problems/dicts/veirfy_two_strings_are_anagrams.py
+++ /dev/null
@@ -1,45 +0,0 @@
-#!/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()
-
-
-
-
diff --git a/src/examples_in_my_book/general_problems/lists/find_closest_num_seq.py b/src/examples_in_my_book/general_problems/lists/find_closest_num_seq.py
deleted file mode 100644
index c3c587c..0000000
--- a/src/examples_in_my_book/general_problems/lists/find_closest_num_seq.py
+++ /dev/null
@@ -1,47 +0,0 @@
-#!/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()
-
diff --git a/src/examples_in_my_book/general_problems/lists/find_duplicate_num_array.py b/src/examples_in_my_book/general_problems/lists/find_duplicate_num_array.py
deleted file mode 100644
index d9330ba..0000000
--- a/src/examples_in_my_book/general_problems/lists/find_duplicate_num_array.py
+++ /dev/null
@@ -1,44 +0,0 @@
-#!/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()
-
-
-
-
-
-
-
-
-
-
diff --git a/src/examples_in_my_book/general_problems/lists/find_long_con_inc_subseq.py b/src/examples_in_my_book/general_problems/lists/find_long_con_inc_subseq.py
deleted file mode 100644
index cb01c54..0000000
--- a/src/examples_in_my_book/general_problems/lists/find_long_con_inc_subseq.py
+++ /dev/null
@@ -1,30 +0,0 @@
-#!/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()
-
diff --git a/src/examples_in_my_book/general_problems/lists/find_majority_in_seq.py b/src/examples_in_my_book/general_problems/lists/find_majority_in_seq.py
deleted file mode 100644
index da38c11..0000000
--- a/src/examples_in_my_book/general_problems/lists/find_majority_in_seq.py
+++ /dev/null
@@ -1,58 +0,0 @@
-#!/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.
-"""
-
-
-
diff --git a/src/examples_in_my_book/general_problems/lists/find_max_profit.py b/src/examples_in_my_book/general_problems/lists/find_max_profit.py
deleted file mode 100644
index 9b5d583..0000000
--- a/src/examples_in_my_book/general_problems/lists/find_max_profit.py
+++ /dev/null
@@ -1,44 +0,0 @@
-#!/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()
-
-
diff --git a/src/examples_in_my_book/general_problems/lists/find_max_subarray.py b/src/examples_in_my_book/general_problems/lists/find_max_subarray.py
deleted file mode 100644
index 36a9328..0000000
--- a/src/examples_in_my_book/general_problems/lists/find_max_subarray.py
+++ /dev/null
@@ -1,44 +0,0 @@
-#!/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()
-
-
-
-
-
-
diff --git a/src/examples_in_my_book/general_problems/lists/find_product_without_division.py b/src/examples_in_my_book/general_problems/lists/find_product_without_division.py
deleted file mode 100644
index 82bcf0d..0000000
--- a/src/examples_in_my_book/general_problems/lists/find_product_without_division.py
+++ /dev/null
@@ -1,33 +0,0 @@
-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()
diff --git a/src/examples_in_my_book/general_problems/lists/find_two_missing_numbers_in_sequence.py b/src/examples_in_my_book/general_problems/lists/find_two_missing_numbers_in_sequence.py
deleted file mode 100644
index 24beab5..0000000
--- a/src/examples_in_my_book/general_problems/lists/find_two_missing_numbers_in_sequence.py
+++ /dev/null
@@ -1,55 +0,0 @@
-#!/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()
-
-
-
-
-
-
-
diff --git a/src/examples_in_my_book/general_problems/lists/greatest_sum_sub_array.py b/src/examples_in_my_book/general_problems/lists/greatest_sum_sub_array.py
deleted file mode 100644
index 10bf2f1..0000000
--- a/src/examples_in_my_book/general_problems/lists/greatest_sum_sub_array.py
+++ /dev/null
@@ -1,27 +0,0 @@
-#!/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()
-
diff --git a/src/examples_in_my_book/general_problems/lists/merge_two_sorted_arrays.py b/src/examples_in_my_book/general_problems/lists/merge_two_sorted_arrays.py
deleted file mode 100644
index 617d183..0000000
--- a/src/examples_in_my_book/general_problems/lists/merge_two_sorted_arrays.py
+++ /dev/null
@@ -1,38 +0,0 @@
-#!/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()
-
-
-
-
-
-
-
-            
-              
diff --git a/src/examples_in_my_book/general_problems/lists/print_all_seq_with_cont_num.py b/src/examples_in_my_book/general_problems/lists/print_all_seq_with_cont_num.py
deleted file mode 100644
index 1bfa771..0000000
--- a/src/examples_in_my_book/general_problems/lists/print_all_seq_with_cont_num.py
+++ /dev/null
@@ -1,39 +0,0 @@
-#!/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()
-
diff --git a/src/examples_in_my_book/general_problems/lists/removing_duplicates_seq.py b/src/examples_in_my_book/general_problems/lists/removing_duplicates_seq.py
deleted file mode 100644
index 9399ae3..0000000
--- a/src/examples_in_my_book/general_problems/lists/removing_duplicates_seq.py
+++ /dev/null
@@ -1,37 +0,0 @@
-#!/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()
-
-
diff --git a/src/examples_in_my_book/general_problems/lists/sum_two_numbers_sequence.py b/src/examples_in_my_book/general_problems/lists/sum_two_numbers_sequence.py
deleted file mode 100644
index bee6a8d..0000000
--- a/src/examples_in_my_book/general_problems/lists/sum_two_numbers_sequence.py
+++ /dev/null
@@ -1,36 +0,0 @@
-#!/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()
-
-
-
diff --git a/src/examples_in_my_book/general_problems/modules/fib_generator.py b/src/examples_in_my_book/general_problems/modules/fib_generator.py
deleted file mode 100644
index b4b812f..0000000
--- a/src/examples_in_my_book/general_problems/modules/fib_generator.py
+++ /dev/null
@@ -1,18 +0,0 @@
-#!/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))
diff --git a/src/examples_in_my_book/general_problems/modules/import_pickle.py b/src/examples_in_my_book/general_problems/modules/import_pickle.py
deleted file mode 100644
index 9aa3ce5..0000000
--- a/src/examples_in_my_book/general_problems/modules/import_pickle.py
+++ /dev/null
@@ -1,31 +0,0 @@
-#!/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()
diff --git a/src/examples_in_my_book/general_problems/modules/passing_cmd_line_args.py b/src/examples_in_my_book/general_problems/modules/passing_cmd_line_args.py
deleted file mode 100644
index 4a05b66..0000000
--- a/src/examples_in_my_book/general_problems/modules/passing_cmd_line_args.py
+++ /dev/null
@@ -1,18 +0,0 @@
-#!/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()
-
-
-
-
diff --git a/src/examples_in_my_book/general_problems/numbers/convert_dec_to_any_base_rec.py b/src/examples_in_my_book/general_problems/numbers/convert_dec_to_any_base_rec.py
deleted file mode 100644
index 63240b8..0000000
--- a/src/examples_in_my_book/general_problems/numbers/convert_dec_to_any_base_rec.py
+++ /dev/null
@@ -1,27 +0,0 @@
-#!/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()
-
diff --git a/src/examples_in_my_book/general_problems/numbers/convert_from_decimal.py b/src/examples_in_my_book/general_problems/numbers/convert_from_decimal.py
deleted file mode 100644
index 6c2c8ed..0000000
--- a/src/examples_in_my_book/general_problems/numbers/convert_from_decimal.py
+++ /dev/null
@@ -1,24 +0,0 @@
-#!/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()
-
-
diff --git a/src/examples_in_my_book/general_problems/numbers/convert_from_decimal_larger_bases.py b/src/examples_in_my_book/general_problems/numbers/convert_from_decimal_larger_bases.py
deleted file mode 100644
index f8a7d71..0000000
--- a/src/examples_in_my_book/general_problems/numbers/convert_from_decimal_larger_bases.py
+++ /dev/null
@@ -1,24 +0,0 @@
-#!/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()
-
-
diff --git a/src/examples_in_my_book/general_problems/numbers/convert_to_decimal.py b/src/examples_in_my_book/general_problems/numbers/convert_to_decimal.py
deleted file mode 100644
index 6c7af35..0000000
--- a/src/examples_in_my_book/general_problems/numbers/convert_to_decimal.py
+++ /dev/null
@@ -1,25 +0,0 @@
-#!/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()
-
-
diff --git a/src/examples_in_my_book/general_problems/numbers/find_fibonacci_seq.py b/src/examples_in_my_book/general_problems/numbers/find_fibonacci_seq.py
deleted file mode 100644
index 911714d..0000000
--- a/src/examples_in_my_book/general_problems/numbers/find_fibonacci_seq.py
+++ /dev/null
@@ -1,44 +0,0 @@
-#!/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()
-
-        
diff --git a/src/examples_in_my_book/general_problems/numbers/finding_if_prime.py b/src/examples_in_my_book/general_problems/numbers/finding_if_prime.py
deleted file mode 100644
index 2c2c447..0000000
--- a/src/examples_in_my_book/general_problems/numbers/finding_if_prime.py
+++ /dev/null
@@ -1,59 +0,0 @@
-#!/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()
-
-
diff --git a/src/examples_in_my_book/general_problems/numbers/generate_prime.py b/src/examples_in_my_book/general_problems/numbers/generate_prime.py
deleted file mode 100644
index a008b4c..0000000
--- a/src/examples_in_my_book/general_problems/numbers/generate_prime.py
+++ /dev/null
@@ -1,35 +0,0 @@
-#!/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))
-
-
-
-
-
-
-
-
-
diff --git a/src/examples_in_my_book/general_problems/numbers/testing_numpy_speed.py b/src/examples_in_my_book/general_problems/numbers/testing_numpy_speed.py
deleted file mode 100644
index 714b3b4..0000000
--- a/src/examples_in_my_book/general_problems/numbers/testing_numpy_speed.py
+++ /dev/null
@@ -1,32 +0,0 @@
-#!/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
-'''
diff --git a/src/examples_in_my_book/general_problems/oop/HashTable.py b/src/examples_in_my_book/general_problems/oop/HashTable.py
deleted file mode 100644
index 073b4b1..0000000
--- a/src/examples_in_my_book/general_problems/oop/HashTable.py
+++ /dev/null
@@ -1,81 +0,0 @@
-#!/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()
-
diff --git a/src/examples_in_my_book/general_problems/sets/__init__.py b/src/examples_in_my_book/general_problems/sets/__init__.py
deleted file mode 100644
index e69de29..0000000
diff --git a/src/examples_in_my_book/general_problems/sets/removing_duplicates_seq_.py b/src/examples_in_my_book/general_problems/sets/removing_duplicates_seq_.py
deleted file mode 100644
index 9399ae3..0000000
--- a/src/examples_in_my_book/general_problems/sets/removing_duplicates_seq_.py
+++ /dev/null
@@ -1,37 +0,0 @@
-#!/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()
-
-
diff --git a/src/examples_in_my_book/general_problems/sets/set_operations_dict.py b/src/examples_in_my_book/general_problems/sets/set_operations_dict.py
deleted file mode 100644
index af68b31..0000000
--- a/src/examples_in_my_book/general_problems/sets/set_operations_dict.py
+++ /dev/null
@@ -1,39 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from collections import OrderedDict
-
-def  set_operations_with_dict():
-    ''' find common in 2 dictionaries '''
-    ''' values() do not support set operations!'''
-    
-    pairs = [('a', 1), ('b',2), ('c',3)]
-    d1 = OrderedDict(pairs)
-    print(d1)   # ('a', 1), ('b', 2), ('c', 3)
-    
-    d2 = {'a':1, 'c':2, 'd':3, 'e':4}
-    print(d2)   # {'a': 1, 'c': 2, 'e': 4, 'd': 3}
-    
-    union = d1.keys() & d2.keys()
-    print(union)    # {'a', 'c'}
-    
-    union_items = d1.items() & d2.items()
-    print(union_items)  # {('a', 1)}
-    
-    subtraction1 = d1.keys() - d2.keys()
-    print(subtraction1)  # {'b'}
-    
-    subtraction2 = d2.keys() - d1.keys()
-    print(subtraction2)  # {'d', 'e'}
-    
-    subtraction_items = d1.items() - d2.items()
-    print(subtraction_items)  # {('b', 2), ('c', 3)}
-
-    ''' we can remove keys from a dict doing: '''
-    d3 = {key:d2[key] for key in d2.keys() - {'c', 'd'}}
-    print(d3) {'a': 1, 'e': 4}
-
-if __name__ == '__main__':
-    set_operations_with_dict()
-
diff --git a/src/examples_in_my_book/general_problems/sets/set_operations_with_dict.py b/src/examples_in_my_book/general_problems/sets/set_operations_with_dict.py
deleted file mode 100644
index af68b31..0000000
--- a/src/examples_in_my_book/general_problems/sets/set_operations_with_dict.py
+++ /dev/null
@@ -1,39 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from collections import OrderedDict
-
-def  set_operations_with_dict():
-    ''' find common in 2 dictionaries '''
-    ''' values() do not support set operations!'''
-    
-    pairs = [('a', 1), ('b',2), ('c',3)]
-    d1 = OrderedDict(pairs)
-    print(d1)   # ('a', 1), ('b', 2), ('c', 3)
-    
-    d2 = {'a':1, 'c':2, 'd':3, 'e':4}
-    print(d2)   # {'a': 1, 'c': 2, 'e': 4, 'd': 3}
-    
-    union = d1.keys() & d2.keys()
-    print(union)    # {'a', 'c'}
-    
-    union_items = d1.items() & d2.items()
-    print(union_items)  # {('a', 1)}
-    
-    subtraction1 = d1.keys() - d2.keys()
-    print(subtraction1)  # {'b'}
-    
-    subtraction2 = d2.keys() - d1.keys()
-    print(subtraction2)  # {'d', 'e'}
-    
-    subtraction_items = d1.items() - d2.items()
-    print(subtraction_items)  # {('b', 2), ('c', 3)}
-
-    ''' we can remove keys from a dict doing: '''
-    d3 = {key:d2[key] for key in d2.keys() - {'c', 'd'}}
-    print(d3) {'a': 1, 'e': 4}
-
-if __name__ == '__main__':
-    set_operations_with_dict()
-
diff --git a/src/examples_in_my_book/general_problems/strings/__init__.py b/src/examples_in_my_book/general_problems/strings/__init__.py
deleted file mode 100644
index e69de29..0000000
diff --git a/src/examples_in_my_book/general_problems/strings/find_all_permutations_string.py b/src/examples_in_my_book/general_problems/strings/find_all_permutations_string.py
deleted file mode 100644
index 4c90e6f..0000000
--- a/src/examples_in_my_book/general_problems/strings/find_all_permutations_string.py
+++ /dev/null
@@ -1,47 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-
-def find_all_permutations_string(str1):
-    ''' print all the permutations of a given string, recursive so runtime is O(n*(n-1)) '''
-    res = []
-    if len(str1) == 1:
-        res = [str1]
-    else:
-        for i, c in enumerate(str1):
-            for perm in find_all_permutations_string(str1[:i] + str1[i+1:]):
-                res += [c + perm]
-    return res
-
-
-def find_all_permutations_string_crazy(str1):
-    ''' crazy simple way of find all the permutations of a string, also using recursion'''
-    return [str1] if len(str1) == 1 else [c + perm for i, c in enumerate(str1) for perm in find_all_permutations_string_crazy(str1[:i]+str1[i+1:])]
-
-
-def find_all_permutations_string_stdlib(str1):
-    ''' find all the permutations of a string just using the available packages '''
-    from itertools import permutations
-    perms = [''.join(p) for p in permutations(str1)]
-    return perms
-
-
-def test_find_all_permutations_string():
-    str1 = "abc"
-    perm_set = {'abc', 'bac', 'cab', 'acb', 'cba', 'bca'}
-    assert(set(find_all_permutations_string(str1)) == perm_set)
-    assert(set(find_all_permutations_string_crazy(str1)) == perm_set)
-    assert(set(find_all_permutations_string_stdlib(str1)) == perm_set)
-    print('Tests passed!')
-
-
-if __name__ == '__main__':
-    test_find_all_permutations_string()
-
-
-
-
-
-  
diff --git a/src/examples_in_my_book/general_problems/strings/find_edit_distance.py b/src/examples_in_my_book/general_problems/strings/find_edit_distance.py
deleted file mode 100644
index f709424..0000000
--- a/src/examples_in_my_book/general_problems/strings/find_edit_distance.py
+++ /dev/null
@@ -1,34 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-def find_edit_distance(str1, str2):
-	''' computes the edit distance between two strings '''
-	m = len(str1)
-	n = len(str2)
-	diff = lambda c1, c2: 0 if c1 == c2 else 1
-	E = [[0] * (n + 1) for i in range(m + 1)]
-	for i in range(m + 1):
-		E[i][0] = i
-	for j in range(1, n + 1):
-		E[0][j] = j
-	for i in range(1, m + 1):
-		for j in range(1, n + 1):
-			E[i][j] = min(E[i-1][j] + 1, E[i][j-1] + 1, E[i-1][j-1] + diff(str1[i-1], str2[j-1]))
-	return E[m][n]
-
-
-def test_find_edit_distance():
-    s = 'sunday'
-    t = 'saturday'
-    assert(find_edit_distance(s, t) == 3)
-    print('Tests passed!')
-
-
-if __name__ == '__main__':
-    test_find_edit_distance()
-
-
-
-
diff --git a/src/examples_in_my_book/general_problems/strings/find_palindrome_rec.py b/src/examples_in_my_book/general_problems/strings/find_palindrome_rec.py
deleted file mode 100644
index ec79fa0..0000000
--- a/src/examples_in_my_book/general_problems/strings/find_palindrome_rec.py
+++ /dev/null
@@ -1,29 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-def find_palindrome_rec(s):
-    ''' recursive way of checking whether a str is a palindrome '''
-    if len(s) > 1: 
-        if s[0] != s[-1]: return False
-        else: find_palindrome_rec(s[1:-1])  
-    return True
-
-
-def test_find_palindrome_rec(module_name='this module'):
-    str1 = 'radar'
-    str2 = ""
-    str3 = 'x'
-    str4 = 'hello'
-    assert(find_palindrome_rec(str1) == True)
-    assert(find_palindrome_rec(str2) == True)
-    assert(find_palindrome_rec(str3) == True)
-    assert(find_palindrome_rec(str4) == False)       
-    s = 'Tests in {name} have {con}!'
-    print(s.format(name=module_name, con='passed'))
-
-
-if __name__ == '__main__':
-    test_find_palindrome_rec()
-
diff --git a/src/examples_in_my_book/general_problems/strings/find_subst_in_str.py b/src/examples_in_my_book/general_problems/strings/find_subst_in_str.py
deleted file mode 100644
index 6caff9b..0000000
--- a/src/examples_in_my_book/general_problems/strings/find_subst_in_str.py
+++ /dev/null
@@ -1,41 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-def find_subst_in_str(str1, set1):
-    sub_str1 = ''
-    found = False
-    
-    while set1:
-        for c in str1:
-            if c in set1:
-                set1.remove(c)
-                found = True
-            if found == True:
-                sub_str1 += c
-            if len(set1) == 0: found = False
-    return sub_str1
-
-	
-
-def test_find_subst_in_str(module_name='this module'):
-    str1 = 'ydxahbcscdk'
-    
-    set1 = {'a','b','c','d'}
-    result = 'dxahbc'
-    
-    assert( find_subst_in_str(str1, set1)==result)
-    
-    set2 = {'a','b','c'}
-    result2 = 'ahbc'
-    assert( find_subst_in_str(str1, set2)==result2)
-
-        
-    s = 'Tests in {name} have {con}!'
-    print(s.format(name=module_name, con='passed'))
-
-
-if __name__ == '__main__':
-    test_find_subst_in_str()
-
diff --git a/src/examples_in_my_book/general_problems/strings/longest_common_substring.py b/src/examples_in_my_book/general_problems/strings/longest_common_substring.py
deleted file mode 100644
index 13aa0af..0000000
--- a/src/examples_in_my_book/general_problems/strings/longest_common_substring.py
+++ /dev/null
@@ -1,32 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-
-def longest_common_substring(str1, str2):
-    ''' find the largest commom substring from 2 strings '''
-    m = [[0 for i in range(len(str2) + 1)] for k in range(len(str1) + 1)]
-    lcs = None
-    max_len = 0
-    for y in range(1, len(str1) + 1):
-        for x in range(1, len(str2) + 1):
-            m[y][x] = m[y - 1][x - 1] + 1 if (str1[y - 1] == str2[x - 1]) else 0
-
-            if m[y][x] > max_len:
-                max_len = m[y][x]
-                lcs = str1[(y - max_len):y]
-    return max_len, lcs   
-    
-
-def test_longest_common_substring():
-    str1 = 'buffy is a vampire slayer'
-    str2 = 'aaas bampires vslay'
-    assert(longest_common_substring(str1, str2) == (6, 'ampire'))
-    print('Tests passed!')
-
-
-if __name__ == '__main__':
-    test_longest_common_substring()
-
-
diff --git a/src/examples_in_my_book/general_problems/strings/reverse_string_inplace_rec.py b/src/examples_in_my_book/general_problems/strings/reverse_string_inplace_rec.py
deleted file mode 100644
index 3157a50..0000000
--- a/src/examples_in_my_book/general_problems/strings/reverse_string_inplace_rec.py
+++ /dev/null
@@ -1,33 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-def reverse_string_inplace_rec(s):
-    ''' takes a string and returns its reverse'''
-    if s:
-        s = s[-1] + reverse_string_inplace_rec(s[:-1])
-    return s
-    
-def reverse_string_inplace(s):
-    s = s[::-1]
-    if s[0] == '\0': 
-        s = s[1:]
-        s += '\0'
-    return s
-        
-
-
-def test_reverse_string_inplace_rec(module_name='this module'):
-    s = 'hello'
-    s2 = 'buffy\0'
-    assert(reverse_string_inplace(s) == 'olleh')
-    assert(reverse_string_inplace(s2) == 'yffub\0')
-    assert(reverse_string_inplace_rec(s) == 'olleh')
-        
-    s = 'Tests in {name} have {con}!'
-    print(s.format(name=module_name, con='passed'))
-
-if __name__ == '__main__':
-    test_reverse_string_inplace_rec()
-
diff --git a/src/examples_in_my_book/general_problems/strings/reversing_words_setence.py b/src/examples_in_my_book/general_problems/strings/reversing_words_setence.py
deleted file mode 100644
index cb392c1..0000000
--- a/src/examples_in_my_book/general_problems/strings/reversing_words_setence.py
+++ /dev/null
@@ -1,23 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-def reversing_words_setence(str1):
-    ''' reverse the words in a sentence'''
-    words = str1.split()
-    rev_set = " ".join(reversed(words))
-    return rev_set
-
-
-def test_reversing_words_setence(module_name='this module'):
-    str1 = "Buffy is a Vampire Slayer"
-    assert(reversing_words_setence(str1) == "Slayer Vampire a is Buffy")
-        
-    s = 'Tests in {name} have {con}!'
-    print(s.format(name=module_name, con='passed'))
-
-
-if __name__ == '__main__':
-    test_reversing_words_setence()
-
diff --git a/src/examples_in_my_book/general_problems/tuples/namedtuple_example.py b/src/examples_in_my_book/general_problems/tuples/namedtuple_example.py
deleted file mode 100644
index c2b23d1..0000000
--- a/src/examples_in_my_book/general_problems/tuples/namedtuple_example.py
+++ /dev/null
@@ -1,17 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from collections import namedtuple
-
-def  namedtuple_example():
-    ''' show some examples for namedtuple '''
-    sunnydale = namedtuple('name', ['job', 'age'])
-    buffy = sunnydale('slayer', '17')
-    print(buffy.job)
-
-
-if __name__ == '__main__':
-    namedtuple_example()
-
-
diff --git a/src/examples_in_my_book/searching/__init__.py b/src/examples_in_my_book/searching/__init__.py
deleted file mode 100644
index e69de29..0000000
diff --git a/src/examples_in_my_book/searching/binary_search.py b/src/examples_in_my_book/searching/binary_search.py
deleted file mode 100644
index 404a59e..0000000
--- a/src/examples_in_my_book/searching/binary_search.py
+++ /dev/null
@@ -1,49 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-
-def binary_search(seq, key):
-    ''' binary search iterative algorithm '''
-    ''' observe that the index is returned '''
-    hi = len(seq)      
-    lo = 0
-    while lo < hi:
-        mid = (hi+lo) // 2
-        if seq[mid] == key:
-            return mid
-        elif key < seq[mid]:
-            hi = mid 
-        else:
-            lo = mid + 1
-    return None
-     
-
-def binary_search_rec(seq, key, lo=0, hi=None):
-    ''' binary search recursive algorithm '''
-    hi = hi or len(seq)
-    if hi < lo: return None
-    mid = (hi + lo) // 2
-    if seq[mid] == key:
-        return mid
-    elif seq[mid] < key:
-        return binary_search_rec(seq, key, mid + 1, hi)
-    else:
-        return binary_search_rec(seq, key, lo, mid - 1)
-
-
-def test_binary_search():
-    seq = [1,2,5,6,7,10,12,12,14,15]
-    key = 6
-    assert(binary_search(seq, key) == 3)
-    assert(binary_search_rec(seq, key) == 3)
-    print('Tests passed!')
-
-
-if __name__ == '__main__':
-    test_binary_search()
-
-
-
-
diff --git a/src/examples_in_my_book/searching/interserction_two_arrays.py b/src/examples_in_my_book/searching/interserction_two_arrays.py
deleted file mode 100644
index 0fa91cf..0000000
--- a/src/examples_in_my_book/searching/interserction_two_arrays.py
+++ /dev/null
@@ -1,77 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' using sets '''
-
-def intersection_two_arrays_sets(seq1, seq2):
-    ''' find the intersection of two arrays using set proprieties '''
-    set1 = set(seq1)
-    set2 = set(seq2)
-    return set1.intersection(set2)  #same as list(set1 & set2
-   
-   
-   
-''' using merge sort '''
-
-def intersection_two_arrays_ms(seq1, seq2):
-    ''' find the intersection of two arrays using merge sort '''
-    res = []
-    while seq1 and seq2:
-        if seq1[-1] == seq2[-1]:
-            res.append(seq1.pop())
-            seq2.pop()
-        elif seq1[-1] > seq2[-1]:
-            seq1.pop()
-        else: 
-            seq2.pop()
-    res.reverse()
-    return res
- 
- 
- 
- 
-''' using binary search '''
- 
-def binary_search(seq, key, lo=0, hi=None):
-    ''' binary search iterative algorithm '''
-    hi = hi or len(seq)      
-    while lo < hi:
-        mid = (hi+lo) // 2
-        if seq[mid] == key:
-            return True
-        elif key > seq[mid]:
-            lo = mid + 1
-        else:
-            hi = mid 
-    return None
-    
-def intersection_two_arrays_bs(seq1, seq2):
-    ''' if A small and B is too large, we can do a binary search on each entry in B '''
-    ''' only works if sorted and the small sequence has not larger nmbers!!!'''
-    if len(seq1) > len(seq2): seq, key = seq1, seq2
-    else: seq, key = seq2, seq1
-    
-    intersec = []
-    for item in key:
-        if binary_search(seq, item):     
-            intersec.append(item)  
-    return intersec   
-    
-
-
-def test_intersection_two_arrays(module_name='this module'):
-    seq1 = [1,2,3,5,7,8]
-    seq2 = [3,5,6]
-    
-    assert(set(intersection_two_arrays_sets(seq1,seq2)) == set([3,5]))
-    assert(intersection_two_arrays_bs(seq1,seq2) == [3,5])
-    assert(intersection_two_arrays_ms(seq1,seq2) == [3,5])
-        
-    s = 'Tests in {name} have {con}!'
-    print(s.format(name=module_name, con='passed'))
-
-
-if __name__ == '__main__':
-    test_intersection_two_arrays()
-
diff --git a/src/examples_in_my_book/sorting/__init__.py b/src/examples_in_my_book/sorting/__init__.py
deleted file mode 100644
index e69de29..0000000
diff --git a/src/examples_in_my_book/sorting/find_k_largest_seq_quickselect.py b/src/examples_in_my_book/sorting/find_k_largest_seq_quickselect.py
deleted file mode 100644
index 820a8d7..0000000
--- a/src/examples_in_my_book/sorting/find_k_largest_seq_quickselect.py
+++ /dev/null
@@ -1,61 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-import random
-
-def swap(A, x, y):
-    tmp = A[x]
-    A[x] = A[y]
-    A[y] = tmp
-
-
-def qselect(A, k, left=None, right=None):
-    left = left or 0
-    right = right or len(A) - 1
-    pivot = random.randint(left, right)
-    pivotVal = A[pivot]
-
-    # Move pivot out of the sorting range
-    swap(A, pivot, right)
-    swapIndex, i = left, left
-    while i <= right - 1:
-        if A[i] < pivotVal:
-            swap(A, i, swapIndex)
-            swapIndex += 1
-        i += 1
-        
-    # Move pivot to final position
-    swap(A, right, swapIndex)
-
-    # Check if pivot matches, else recurse on the correct half
-    rank = len(A) - swapIndex
-    if k == rank:
-        return A[swapIndex]
-    elif k < rank:
-        return qselect(A, k, left=swapIndex+1, right=right)
-    else:
-        return qselect(A, k, left=left, right=swapIndex-1)
-        
-
-
-def find_k_largest_seq_quickselect(seq, k):
-    ''' perform quick select to get kth element, and find all elements larger '''
-    kth_largest = qselect(seq, k)
-    result = []
-    for item in seq:
-        if item >= kth_largest:
-            result.append(item)
-    return result
-
-
-
-def test_find_k_largest_seq_quickselect():
-    seq = [3, 10, 4, 5, 1, 8, 9, 11, 5]
-    k = 2
-    assert(find_k_largest_seq_quickselect(seq,k) == [10, 11])
-    
-
-if __name__ == '__main__':
-    test_find_k_largest_seq_quickselect()
-
diff --git a/src/examples_in_my_book/sorting/heap_sort1.py b/src/examples_in_my_book/sorting/heap_sort1.py
deleted file mode 100644
index 7f174bb..0000000
--- a/src/examples_in_my_book/sorting/heap_sort1.py
+++ /dev/null
@@ -1,23 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-import heapq
-
-def heap_sort1(seq):
-    ''' heap sort with Python's heapq '''
-    h = []
-    for value in seq:
-        heapq.heappush(h, value)
-    return [heapq.heappop(h) for i in range(len(h))]
-
-
-def test_heap_sort1():
-    seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
-    assert(heap_sort1(seq) == sorted(seq))
-    print('Tests passed!')
-
-
-if __name__ == '__main__':
-    test_heap_sort1()
-
diff --git a/src/examples_in_my_book/sorting/heap_sort2.py b/src/examples_in_my_book/sorting/heap_sort2.py
deleted file mode 100644
index e7df361..0000000
--- a/src/examples_in_my_book/sorting/heap_sort2.py
+++ /dev/null
@@ -1,24 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from heap import Heap
-
-def heap_sort2(seq):
-    heap = Heap(seq)
-    
-    res = []
-    for i in range(len(seq)):
-        res.insert(0, heap.extract_max())
-
-    return res
-    
-    
-def test_heap_sort2():
-    seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
-    assert(heap_sort2(seq) == sorted(seq))
-    print('Tests passed!')
-
-
-if __name__ == '__main__':
-    test_heap_sort2()
diff --git a/src/examples_in_my_book/sorting/heap_sort3.py b/src/examples_in_my_book/sorting/heap_sort3.py
deleted file mode 100644
index 9e4ff2a..0000000
--- a/src/examples_in_my_book/sorting/heap_sort3.py
+++ /dev/null
@@ -1,36 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-def heap_sort3(seq):  
-    for start in range((len(seq)-2)//2, -1, -1):
-        siftdown(seq, start, len(seq)-1)
-    for end in range(len(seq)-1, 0, -1):
-        seq[end], seq[0] = seq[0], seq[end]
-        siftdown(seq, 0, end - 1)
-    return seq
- 
-def siftdown(seq, start, end):
-    root = start
-    while True:
-        child = root * 2 + 1
-        if child > end: break
-        if child + 1 <= end and seq[child] < seq[child + 1]:
-            child += 1
-        if seq[root] < seq[child]:
-            seq[root], seq[child] = seq[child], seq[root]
-            root = child
-        else:
-            break
-    
-   
-
-def test_heap_sort():
-    seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
-    assert(heap_sort3(seq) == sorted(seq))
-    print('Tests passed!')
-
-
-if __name__ == '__main__':
-    test_heap_sort3()
-
diff --git a/src/examples_in_my_book/sorting/merge_sort.py b/src/examples_in_my_book/sorting/merge_sort.py
deleted file mode 100644
index 46a27dd..0000000
--- a/src/examples_in_my_book/sorting/merge_sort.py
+++ /dev/null
@@ -1,33 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-   
-def merge_sort(seq):
-    if len(seq) <= 1: return seq
-    mid = len(seq)//2 
-    lft, rgt = seq[:mid], seq[mid:]
-    if len(lft)>1: lft = merge_sort(lft)
-    if len(rgt)>1: rgt = merge_sort(rgt)
-    
-    res = []
-    while lft and rgt: 
-        if lft [-1]>= rgt[-1]:
-            res.append(lft.pop())
-        else: 
-            res.append(rgt.pop())
-    res.reverse()
-    return(lft or rgt) + res   
-    
-
-
-
-def test_merge_sort():
-    seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
-    assert(merge_sort(seq) == sorted(seq))
-    print('Tests passed!')
-
-
-if __name__ == '__main__':
-    test_merge_sort()
diff --git a/src/examples_in_my_book/sorting/quick_sort.py b/src/examples_in_my_book/sorting/quick_sort.py
deleted file mode 100644
index ee4d0c1..0000000
--- a/src/examples_in_my_book/sorting/quick_sort.py
+++ /dev/null
@@ -1,42 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-
-def quick_sort(seq):
-    if len(seq) < 2: return seq
-    pivot = sorted(seq[0], seq[len(seq)//2], seq[-1])[1]
-    print(pivot)
-    left = quick_sort([x for x in seq[1:] if x < pivot])
-    right = quick_sort([x for x in seq[1:] if x >= pivot])
-    return left + [pivot] + right
-    
-    
-""" we can also divide them into two functions """
-def partition(seq):
-    pi,seq = seq[0],seq[1:]                     
-    lo = [x for x in seq if x <= pi]            
-    hi = [x for x in seq if x > pi]             
-    return lo, pi, hi 
-
-def quick_sort_divided(seq):
-    if len(seq) < 2: return seq                
-    lo, pi, hi = partition(seq)                  
-    return quick_sort_divided(lo) + [pi] + quick_sort_divided(hi)
-
-
-   
-
-def test_quick_sort():
-    seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
-    assert(quick_sort(seq) == sorted(seq))
-    assert(quick_sort_divided(seq) == sorted(seq))
-    print('Tests passed!')
-
-
-if __name__ == '__main__':
-    test_quick_sort()
-
-
-
diff --git a/src/examples_in_my_book/trees/__init__.py b/src/examples_in_my_book/trees/__init__.py
deleted file mode 100644
index e69de29..0000000
diff --git a/src/examples_in_my_book/trees/binary_trees/BST.py b/src/examples_in_my_book/trees/binary_trees/BST.py
deleted file mode 100644
index b2384a3..0000000
--- a/src/examples_in_my_book/trees/binary_trees/BST.py
+++ /dev/null
@@ -1,68 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from BT import BT
-
-class BST(BT):
-    def __init__(self, value=None):
-        self.value = value
-        self.left = None
-        self.right = None
-
-    def insert_left(self, new_node):
-        self.insert(value)
-        
-    def insert_right(self, new_node):
-        self.insert(value)
-
-
-    def insert(self, value):
-        if  self.value == None:
-            self.value = value
-        else:
-            if value > self.value:
-                self.right = self.right and self.right.insert(value) or BST(value)
-            else:
-                self.left = self.left and self.left.insert(value) or BST(value)
-        return self
-
-    def find(self, value):
-        if value == self.value:
-            return self
-        elif value > self.value and self.right:
-            return self.right.find(value)
-        elif self.left:
-            return self.left.find(value)
-        return None
-
-
-
-
-def main():
-    """
-    BST
-          4
-       2     6
-     1   3 5   7
-    """
-    tree = BST()
-    tree.insert(4)
-    tree.insert(2)
-    tree.insert(6)
-    tree.insert(1)
-    tree.insert(3)
-    tree.insert(7)
-    tree.insert(5)
-    print(tree.get_right())
-    print(tree.get_right().get_left())
-    print(tree.get_right().get_right())
-    print(tree.get_left())
-    print(tree.get_left().get_left())
-    print(tree.get_left().get_right() == 1)
-    assert(tree.find(30) == None)
-
-
-if __name__ == '__main__':
-    main()
-
diff --git a/src/examples_in_my_book/trees/binary_trees/BST_with_Nodes.py b/src/examples_in_my_book/trees/binary_trees/BST_with_Nodes.py
deleted file mode 100644
index 91cd081..0000000
--- a/src/examples_in_my_book/trees/binary_trees/BST_with_Nodes.py
+++ /dev/null
@@ -1,66 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-
-class Node(object):
-    def __init__(self, value):
-        self.value = value  
-        self.left = None 
-        self.right = None 
-
-    def __repr__(self):
-        return '{}'.format(self.value)
-          
-
-class BSTwithNodes(object):
-    def __init__(self): 
-        self.root = None
-
-
-    def insert(self, value):  
-        if self.root == None:
-            self.root = Node(value)
-        else:
-            current = self.root
-            while True:
-                if value < current.value:
-                    if current.left:
-                        current = current.left
-                    else:
-                        current.left = Node(value)
-                        break;      
-
-                elif value > current.value:               
-                    if current.right:
-                        current = current.right
-                    else:
-                        current.right = Node(value)
-                        break;      
-                else:
-                    break 
-
-
-def main():
-    """
-    BST
-          4
-       2     6
-     1   3 5   7
-    """
-    tree = BSTwithNodes()
-    l1 = [4, 2, 6, 1, 3, 7, 5]
-    for i in l1: tree.insert(i)
-    print(tree.root)
-    print(tree.root.right)
-    print(tree.root.right.left)
-    print(tree.root.right.right)
-    print(tree.root.left)
-    print(tree.root.left.left)
-    print(tree.root.left.right)
-
-
-if __name__ == '__main__':
-    main()
-
diff --git a/src/examples_in_my_book/trees/binary_trees/BT.py b/src/examples_in_my_book/trees/binary_trees/BT.py
deleted file mode 100644
index 15d93b1..0000000
--- a/src/examples_in_my_book/trees/binary_trees/BT.py
+++ /dev/null
@@ -1,72 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-class BT(object):
-    def __init__(self, value):
-        self.value = value
-        self.left = None
-        self.right = None       
-
-    
-    def get_right(self):
-        return self.right
-
-    def get_left(self):
-        return self.left
-
-    def is_leaf(self):
-        return self.left is None and self.right is None
-
-    def set_root(self, obj):
-        self.value = obj
-    
-    def get_root(self):
-        return self.value
-        
-    def insert_left(self, new_node):
-        if self.left == None:
-            self.left = BT(new_node)
-        else:
-            t = BT(self.left)
-            t.left = new_node
-            self.left = t
-    
-    def insert_right(self, new_node):
-        if self.right == None:
-            self.right = BT(new_node)
-        else:
-            t = BT(self.right)
-            t.right = new_node
-            self.right = t
-            
-    def __repr__(self):
-        return '{}'.format(self.value)
-
-
-
-def tests_BT():
-    """
-            1 
-       2       3
-    4   5     6    7
-    """  
-    tree = BT(1)
-    tree.insert_left(2)
-    tree.insert_right(3)
-    tree.get_left().insert_left(4)
-    tree.get_left().insert_right(5)
-    tree.get_right().insert_left(6)
-    tree.get_right().insert_right(7)
-    print(tree.get_right().get_right())
-    tree.get_right().get_right().set_root(8)
-    print(tree.get_right().get_right())
-    assert(tree.get_right().is_leaf() == False)
-    assert(tree.get_right().get_right().is_leaf() ==  True)
-    print("Tests Passed!")
-    
-
-if __name__ == '__main__':
-    tests_BT()
-    
diff --git a/src/examples_in_my_book/trees/binary_trees/BT_lists.py b/src/examples_in_my_book/trees/binary_trees/BT_lists.py
deleted file mode 100644
index 7e6c1c5..0000000
--- a/src/examples_in_my_book/trees/binary_trees/BT_lists.py
+++ /dev/null
@@ -1,61 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-def BinaryTreeList(r):
-    ''' constructs a list with a root and 2 empty sublists for the children. To add a left subtree to the root of a tree, we need to insert a new list into the second position of the root list '''
-    return [r, [], []]
-
-
-def insertLeft(root, newBranch):
-    t = root.pop(1)
-    if len(t) > 1:
-        root.insert(1,[newBranch,t,[]])
-    else:
-        root.insert(1,[newBranch, [], []])
-    return root
-
-
-def insertRight(root, newBranch):
-    t = root.pop(2)
-    if len(t) > 1:
-        root.insert(2,[newBranch,[],t])
-    else:
-        root.insert(2,[newBranch,[],[]])
-    return root
-
-def getRootVal(root):
-    return root[0]
-
-def setRootVal(root, newVal):
-    root[0] = newVal
-
-def getLeftChild(root):
-    return root[1]
-
-def getRightChild(root):
-    return root[2]
-
-
-
-def main():
-    '''
-    3
-    [5, [4, [], []], []]
-    [7, [], [6, [], []]]
-    '''
-
-    r = BinaryTreeList(3)
-    insertLeft(r,4)
-    insertLeft(r,5)
-    insertRight(r,6)
-    insertRight(r,7)
-    print(getRootVal(r)) 
-    print(getLeftChild(r)) 
-    print(getRightChild(r))    
-    
-
-if __name__ == '__main__':
-    main()
-
diff --git a/src/examples_in_my_book/trees/binary_trees/__init__.py b/src/examples_in_my_book/trees/binary_trees/__init__.py
deleted file mode 100644
index e69de29..0000000
diff --git a/src/examples_in_my_book/trees/binary_trees/avl.py b/src/examples_in_my_book/trees/binary_trees/avl.py
deleted file mode 100644
index ca23adc..0000000
--- a/src/examples_in_my_book/trees/binary_trees/avl.py
+++ /dev/null
@@ -1,140 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from BST_with_Nodes import BSTwithNodes, Node
-
-
-class AVL(BSTwithNodes):
-    """AVL binary search tree implementation.
-    Supports insert, find, and delete-min operations in O(lg n) time.
-    """
-    def __init__(self): 
-        self.root = None
-
-    def left_rotate(self, x):
-        y = x.right
-        y.value = x.value
-        if y.value is None:
-            self.root = y
-        else:
-            if y.value.left is x:
-                y.value.left = y
-            elif y.value.right is x:
-                y.value.right = y
-        x.right = y.left
-        if x.right is not None:
-            x.right.value = x
-        y.left = x
-        x.value = y
-        update_height(x)
-        update_height(y)
-
-    def right_rotate(self, x):
-        y = x.left
-        y.value = x.value
-        if y.value is None:
-            self.root = y
-        else:
-            if y.value.left is x:
-                y.value.left = y
-            elif y.value.right is x:
-                y.value.right = y
-        x.left = y.right
-        if x.left is not None:
-            x.left.value = x
-        y.right = x
-        x.value = y
-        update_height(x)
-        update_height(y)
-
-    def insert_item(self, value):
-        if self.root == None:
-            self.root = Node(value)
-        else:
-            current = self.root
-            while True:
-                if value < current.value:
-                    if current.left:
-                        current = current.left
-                    else:
-                        current.left = Node(value)
-                        break;      
-
-                elif value > current.value:               
-                    if current.right:
-                        current = current.right
-                    else:
-                        current.right = Node(value)
-                        break;      
-                else:
-                    break 
-
-
-    def insert(self, value):
-        node = self.insert_item(value)
-        self.rebalance(node)
-        
-        
-    def rebalance(self, node):
-        while node is not None:
-            update_height(node)
-            if height(node.left) >= 2 + height(node.right):
-                if height(node.left.left) >= height(node.left.right):
-                    self.right_rotate(node)
-                else:
-                    self.left_rotate(node.left)
-                    self.right_rotate(node)
-            elif height(node.right) >= 2 + height(node.left):
-                if height(node.right.right) >= height(node.right.left):
-                    self.left_rotate(node)
-                else:
-                    self.right_rotate(node.right)
-                    self.left_rotate(node)
-            node = node.value
-
-
-    def inorder(self, node):       
-        if node is not None:         
-            self.inorder(node.left)
-            print(node.value)
-            self.inorder(node.right)
-
-    def preorder(self, node):           
-        if node is not None:    
-            print(node.value)
-            self.preorder(node.left)
-            self.preorder(node.right)
-
-    def postorder(self, node):           
-        if node is not None:
-            self.postorder(node.left)
-            self.postorder(node.right)
-            print(node.value)
-
-
-def height(node):
-    if node is None: return -1
-    else: return node.height
-
-def update_height(node):
-    node.height = max(height(node.left), height(node.right)) + 1
-
-
-
-def main():
-    tree = AVL()
-    tree.insert(4)
-    tree.insert(2)
-    tree.insert(6)
-    tree.insert(1)
-    tree.insert(3)
-    tree.insert(7)
-    tree.insert(5)
-    print('Inorder Traversal:')
-    tree.inorder(tree.root) 
-
-
-
-if __name__ == '__main__':
-    main()
diff --git a/src/examples_in_my_book/trees/binary_trees/veritfy_if_BST.py b/src/examples_in_my_book/trees/binary_trees/veritfy_if_BST.py
deleted file mode 100644
index 8aeb9c1..0000000
--- a/src/examples_in_my_book/trees/binary_trees/veritfy_if_BST.py
+++ /dev/null
@@ -1,56 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-from BT import BT
-
-def is_bst(root, min=float('-inf'), max=float('inf')):
-    left, right, value = root.left, root.right, root.value
-    if min < value < max:
-        if left and right:
-            return is_bst(left, min, value) and is_bst(right, value, max)
-        elif left:
-            return is_bst(left, min, value)
-        elif right:
-            return is_bst(right, value, max)
-        return True
-    return False
-
-
-def main():
-    """
-    BST
-          4
-       2     6
-     1   3 5   7
-
-    BT
-          4
-       2     6
-     1   8 5   7
-    """
-    bst = BT(4)
-    bst.insert_left(2)
-    bst.insert_right(6)
-    bst.get_left().insert_left(1)
-    bst.get_left().insert_right(3)
-    bst.get_right().insert_left(5)
-    bst.get_right().insert_right(7)
-    print('is_bst(bst) =', is_bst(bst))   
-     
-    bt = BT(4)
-    bt.insert_left(2)
-    bt.insert_right(6)
-    bt.get_left().insert_left(1)
-    bt.get_left().insert_right(8)
-    bt.get_right().insert_left(5)
-    bt.get_right().insert_right(7)
-    print('is_bst(bt) =', is_bst(bt))
-    
-
-if __name__ == '__main__':
-    main()
-    
-    
-
diff --git a/src/examples_in_my_book/trees/simple_trees/__init__.py b/src/examples_in_my_book/trees/simple_trees/__init__.py
deleted file mode 100644
index e69de29..0000000
diff --git a/src/examples_in_my_book/trees/traversals/BST.py b/src/examples_in_my_book/trees/traversals/BST.py
deleted file mode 100644
index b2384a3..0000000
--- a/src/examples_in_my_book/trees/traversals/BST.py
+++ /dev/null
@@ -1,68 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from BT import BT
-
-class BST(BT):
-    def __init__(self, value=None):
-        self.value = value
-        self.left = None
-        self.right = None
-
-    def insert_left(self, new_node):
-        self.insert(value)
-        
-    def insert_right(self, new_node):
-        self.insert(value)
-
-
-    def insert(self, value):
-        if  self.value == None:
-            self.value = value
-        else:
-            if value > self.value:
-                self.right = self.right and self.right.insert(value) or BST(value)
-            else:
-                self.left = self.left and self.left.insert(value) or BST(value)
-        return self
-
-    def find(self, value):
-        if value == self.value:
-            return self
-        elif value > self.value and self.right:
-            return self.right.find(value)
-        elif self.left:
-            return self.left.find(value)
-        return None
-
-
-
-
-def main():
-    """
-    BST
-          4
-       2     6
-     1   3 5   7
-    """
-    tree = BST()
-    tree.insert(4)
-    tree.insert(2)
-    tree.insert(6)
-    tree.insert(1)
-    tree.insert(3)
-    tree.insert(7)
-    tree.insert(5)
-    print(tree.get_right())
-    print(tree.get_right().get_left())
-    print(tree.get_right().get_right())
-    print(tree.get_left())
-    print(tree.get_left().get_left())
-    print(tree.get_left().get_right() == 1)
-    assert(tree.find(30) == None)
-
-
-if __name__ == '__main__':
-    main()
-
diff --git a/src/examples_in_my_book/trees/traversals/BST_ancestor.py b/src/examples_in_my_book/trees/traversals/BST_ancestor.py
deleted file mode 100644
index c61933d..0000000
--- a/src/examples_in_my_book/trees/traversals/BST_ancestor.py
+++ /dev/null
@@ -1,46 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from BST_traversal import TranversalBST
-
-def find_ancestor(path, low_value, high_value):
-    ''' find the lowest ancestor in a BST '''       
-    while path:
-        current_value = path[0]
-        if current_value < low_value:
-            try:
-                path = path[2:]
-            except:
-                return current_value
-        elif current_value > high_value:
-            try:
-                path = path[1:]
-            except:
-                return current_value
-        elif low_value <= current_value <= high_value:
-            return current_value
-    return None
-
-
-def test_find_ancestor():
-    """
-            10 
-       5       15
-    1   6     11    50
-    """     
-    t = TranversalBST()
-    l1 = [10, 5, 15, 1, 6, 11, 50]
-    for i in l1: t.insert(i)
-    path = t.preorder()
-    assert(find_ancestor(path, 1, 6) == 5)
-    assert(find_ancestor(path, 1, 11) == 10) 
-    assert(find_ancestor(path, 11, 50) == 15)   
-    assert(find_ancestor(path, 5, 15) == 10)  
-    
-    
-    print("Tests passsed!")
-    
-if __name__ == '__main__':
-    test_find_ancestor()
-
diff --git a/src/examples_in_my_book/trees/traversals/BST_traversal.py b/src/examples_in_my_book/trees/traversals/BST_traversal.py
deleted file mode 100644
index 8a6b21b..0000000
--- a/src/examples_in_my_book/trees/traversals/BST_traversal.py
+++ /dev/null
@@ -1,88 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from BST import BST
-
-class TranversalBST(object):
-    def __init__(self):
-        self.bst = BST(None)
-        self.nodes = []
-        
-    def insert(self, value):
-        if not self.bst.value:
-            self.bst.value = value
-        else:
-            self.bst.insert(value)
-
-    def contains(self, value):
-        return bool(self.bst.find(value))
-
-    def get(self, index):
-        for i, value in enumerate(self.inorder()):
-            if i == index:
-                return value
-
-    def inorder(self):
-        current = self.bst  
-        self.nodes = []
-        stack = []
-        while len(stack) > 0 or current is not None:
-            if current is not None:
-                stack.append(current)   
-                current = current.left
-            else:
-                current = stack.pop()
-                self.nodes.append(current.value)
-                current = current.right
-        return self.nodes
-
-
-    def preorder(self):
-        self.nodes = []
-        stack = [self.bst]  
-        while len(stack) > 0:
-            curr = stack.pop()
-            if curr is not None:
-                self.nodes.append(curr.value)
-                stack.append(curr.right)
-                stack.append(curr.left)
-        return self.nodes
-
-
-    def preorder2(self):
-        self.nodes = []
-        current = self.bst  
-        stack = []
-        while len(stack) > 0 or current is not None:
-            if current is not None:
-                self.nodes.append(current.value)
-                stack.append(current)   
-                current = current.left
-            else:
-                current = stack.pop()               
-                current = current.right            
-        return self.nodes
-
-
-
-def main():
-    """
-            10 
-       5       15
-    1   6     11    50
-    """     
-    t = TranversalBST()
-    t.insert(10)
-    t.insert(5)
-    t.insert(15)
-    t.insert(1)
-    t.insert(6)
-    t.insert(11)
-    t.insert(50)
-    print(t.preorder())
-    print(t.preorder2())
-    print(t.inorder())
-
-if __name__ == '__main__':
-    main()    
diff --git a/src/examples_in_my_book/trees/traversals/BST_with_Nodes_traversal.py b/src/examples_in_my_book/trees/traversals/BST_with_Nodes_traversal.py
deleted file mode 100644
index f443753..0000000
--- a/src/examples_in_my_book/trees/traversals/BST_with_Nodes_traversal.py
+++ /dev/null
@@ -1,68 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from BST_with_Nodes import BSTwithNodes, Node
-
-class BSTTraversal(BSTwithNodes):
-    def __init__(self): 
-        self.root = None
-        self.nodes_BFS = []
-        self.nodes_DFS_pre = []
-        self.nodes_DFS_post = []
-        self.nodes_DFS_in = []
-
-    def BFS(self): 
-        self.root.level = 0 
-        queue = [self.root]
-        current_level = self.root.level
-
-        while len(queue) > 0:                 
-            current_node = queue.pop(0)
-            if current_node.level > current_level:
-                current_level += 1
-            self.nodes_BFS.append(current_node.value)
-
-            if current_node.left:
-                current_node.left.level = current_level + 1
-                queue.append(current_node.left)
-                  
-            if current_node.right:
-                current_node.right.level = current_level + 1
-                queue.append(current_node.right)
-      
-        return self.nodes_BFS 
-
-    def DFS_inorder(self, node):      
-        if node is not None:         
-            self.DFS_inorder(node.left)
-            self.nodes_DFS_in.append(node.value)
-            self.DFS_inorder(node.right)
-        return self.nodes_DFS_in
-
-    def DFS_preorder(self, node):          
-        if node is not None:    
-            self.nodes_DFS_pre.append(node.value)
-            self.DFS_preorder(node.left)
-            self.DFS_preorder(node.right)
-        return self.nodes_DFS_pre
-
-    def DFS_postorder(self, node):           
-        if node is not None:
-            self.DFS_postorder(node.left)
-            self.DFS_postorder(node.right)
-            self.nodes_DFS_post.append(node.value)
-        return self.nodes_DFS_post
-
-def main():
-    tree = BSTTraversal()     
-    l1 = [10, 5, 15, 1, 6, 11, 50]
-    for i in l1: tree.insert(i)
-    
-    print('Breadth-First Traversal: ', tree.BFS())    
-    print('Inorder Traversal: ', tree.DFS_inorder(tree.root))   
-    print('Preorder Traversal: ', tree.DFS_preorder(tree.root))
-    print('Postorder Traversal: ', tree.DFS_postorder(tree.root)) 
-
-if __name__ == '__main__':
-    main()
diff --git a/src/examples_in_my_book/trees/traversals/BST_with_extra_methods.py b/src/examples_in_my_book/trees/traversals/BST_with_extra_methods.py
deleted file mode 100644
index fd6a424..0000000
--- a/src/examples_in_my_book/trees/traversals/BST_with_extra_methods.py
+++ /dev/null
@@ -1,95 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from BST_traversal import TranversalBST
-from BST import BST
-
-class BSTwithExtra(TranversalBST):
-    def __init__(self):
-        self.bst = BST(None)
-        self.nodes = []  
-                      
-    def get_inorder(self, k):
-        for i, value in enumerate(self.inorder()):
-            if value == k:
-                return i
-                
-    def get_preorder(self, k):
-        for i, value in enumerate(self.preorder()):
-            if value == k:
-                return i
-                                    
-
-    def is_balanced(self, threshold=1):
-        maxd = self.get_max_depth()
-        mind = self.get_min_depth()
-        print('Max depth: ' + str(maxd))
-        print('Min depth: ' + str(mind))
-        return maxd -mind
-
-    def get_min_depth(self, node=None, initial=1):
-        if node is None and initial == 1:
-            node = self.bst
-        if node.left and node.right:
-            return 1 + min(self.get_min_depth(node.left, 0),
-                       self.get_min_depth(node.right, 0))
-        else:
-            if node.left:
-                return 1 + self.get_max_depth(node.left, 0)
-            elif node.right:
-                return 1 + self.get_max_depth(node.right, 0)
-            else:
-                return 0
-    
-    def get_max_depth(self, node=None, initial=1):
-        if node is None and initial == 1:
-            node = self.bst
-        if node.left and node.right:
-            return 1 + max(self.get_max_depth(node.left, 0),
-                       self.get_max_depth(node.right, 0))
-        else:
-            if node.left:
-                return 1 + self.get_max_depth(node.left, 0)
-            elif node.right:
-                return 1 + self.get_max_depth(node.right, 0)
-            else:
-                return 0
-
-def main():
-    """
-            10 
-       5       15
-    1   6     11    50
-                        60
-                            70
-                                80
-    """     
-    t = BSTwithExtra()
-    l1 = [10, 5, 15, 1, 6, 11, 50, 60, 70, 80]
-    for i in l1: t.insert(i)
-    print(t.inorder())
-    print(t.preorder())
-    assert(t.get_max_depth() == 5)
-    assert(t.get_min_depth() == 2)
-    assert(t.is_balanced() == 3)    
-    assert(t.get_inorder(10) == 3)
-    assert(t.get_preorder(10) == 0)    
-    
-    
-    """
-            1 
-       2       3
-    4   5     6    7
-    """  
-    t2 = BSTwithExtra()
-    l2 = [1, 2, 3, 4, 5, 6, 7, 8]
-    for i in l2: t2.insert(i)
-    print(t2.inorder())
-    print(t2.preorder())
-    assert(t2.is_balanced() == 0)    
-   
-    print("Tests Passed!")
-
-if __name__ == '__main__':
-    main()
diff --git a/src/examples_in_my_book/trees/traversals/__init__.py b/src/examples_in_my_book/trees/traversals/__init__.py
deleted file mode 100644
index e69de29..0000000
diff --git a/src/further_examples/arrays_and_strings/comb_str.py b/src/further_examples/arrays_and_strings/comb_str.py
deleted file mode 100644
index 9e9f966..0000000
--- a/src/further_examples/arrays_and_strings/comb_str.py
+++ /dev/null
@@ -1,29 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' give all the combinations of a str or list:
-    >>> l1 = (1, 2, 3)
-    >>> comb_str(l1)
-    [[1], [1, [2]], [1, [2, 3]], [1, [3]], [2], [2, 3], [3]]
-    >>> comb_str([])
-    []
-'''
-
-
-
-def comb_str(l1):
-    if len(l1) < 2: return l1
-    result = []
-    for i in range(len(l1)):    
-        result.append([l1[i]])
-        for comb in comb_str(l1[i+1:]):
-            result.append([l1[i], comb])
-    return result
-    
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/arrays_and_strings/find_first_non_repetead_char.py b/src/further_examples/arrays_and_strings/find_first_non_repetead_char.py
deleted file mode 100644
index a6b57a0..0000000
--- a/src/further_examples/arrays_and_strings/find_first_non_repetead_char.py
+++ /dev/null
@@ -1,30 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' find the first non-repetead char in a str.
-   ---> we use a dict to count occurences
-   >>> find_non_rep_char("cut")
-   'c'
-   >>> s1 = 'google'
-   >>> find_non_rep_char(s1)
-   'l'
-   >>> find_non_rep_char('ccc')
-   >>> find_non_rep_char('')
-'''
-
-from collections import Counter
-def  find_non_rep_char(s1):
-    aux_dict = Counter()
-    for i in s1:
-        aux_dict[i] += 1
-    for i in s1:
-        if aux_dict[i] < 2: return i  # remember it's <2
-    # not handling anything else: return None
-
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/arrays_and_strings/find_if_is_substr.py b/src/further_examples/arrays_and_strings/find_if_is_substr.py
deleted file mode 100644
index d8fd6d6..0000000
--- a/src/further_examples/arrays_and_strings/find_if_is_substr.py
+++ /dev/null
@@ -1,38 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Find if a s2 is a substring of a s1
-    >>> s1 = 'buffy is a vampire slayer'
-    >>> s2 = 'vampire'
-    >>> s3 = 'angel'
-    >>> isSubstr(s1, s2)
-    True
-    >>> isSubstr(s1, s3)
-    False
-    >>> s4 = 'pirevam'
-    >>> find_substr(s2, s4)
-    True
-    >>> find_substr(s1, s4)
-    False
-'''
-
-def isSubstr(s1, s2):
-    if s1 in s2 or s2 in s1: return True
-    return False
-
-   
-def find_substr(s1, s2):
-    if s1 == '' or s2 == '': return True #empty str is always substr
-    for i, c in enumerate(s1):
-        if c == s2[0]:
-            test_s1 = s1[i:]+s1[:i]
-            return isSubstr(s2, test_s1)
-    return False
-
-
-                   
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/arrays_and_strings/find_if_only_unique_chars.py b/src/further_examples/arrays_and_strings/find_if_only_unique_chars.py
deleted file mode 100644
index fe804bb..0000000
--- a/src/further_examples/arrays_and_strings/find_if_only_unique_chars.py
+++ /dev/null
@@ -1,41 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-   
-def unique_char(s):
-    if len(s) > 256: return False
-    set_chars = set()
-    for i in s:
-        if i in set_chars:
-            return False
-        else:
-            set_chars.add(i) 
-    return True
-    
-    
-    
-def unique_char_no_add(s):
-    if len(s) < 2: return True
-    for i, c in enumerate(s):
-        for j in s[i+1:]:
-            if j == c:
-                return False
-    return True
-    
-
-def main():
-    s1 = 'abcdefg'
-    s2 = 'buffy'
-    s3 = ''
-    print(unique_char(s1))
-    print(unique_char(s2))
-    print(unique_char(s3))
-    print(unique_char_no_add(s1) )
-    print(unique_char_no_add(s2))
-    print(unique_char_no_add(s3))
-    
-                   
-if __name__ == '__main__':
-    main()
-
diff --git a/src/further_examples/arrays_and_strings/perm_str.py b/src/further_examples/arrays_and_strings/perm_str.py
deleted file mode 100644
index 6c32dfa..0000000
--- a/src/further_examples/arrays_and_strings/perm_str.py
+++ /dev/null
@@ -1,24 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' give all the permutation of a str:
-    >>> str1 = 'hat'
-    >>> perm_str(str1)
-    ['hat', 'hta', 'aht', 'ath', 'tha', 'tah']
-    >>> perm_str('')
-    ''
-'''
-
-def perm_str(str1):
-    if len(str1) < 2: return str1
-    result = []
-    for i in range(len(str1)):       
-        for perm in perm_str(str1[:i] + str1[i+1:]):
-            result.append(str1[i] + perm)
-    return result
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/arrays_and_strings/remove_specified_char_from_str.py b/src/further_examples/arrays_and_strings/remove_specified_char_from_str.py
deleted file mode 100644
index 7c7dc36..0000000
--- a/src/further_examples/arrays_and_strings/remove_specified_char_from_str.py
+++ /dev/null
@@ -1,29 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' remove the chars in a list from a string
-   ---> handle whitespaces!!!!
-   >>> remove_char_str('I love google', 'oe')
-   'I lv ggl'
-   >>> remove_char_str('google', '')
-   'google'
-   >>> remove_char_str('google', 'google')
-   ''
-'''
-
-
-def  remove_char_str(s1, charlist):
-    set_aux = set(charlist)
-    lt_aux = [] # we use list intead of concat. strs because it's more efficient
-    for c in s1:
-        if c not in set_aux:
-            lt_aux.append(c)
-    return ''.join(lt_aux)      # IF NON CHARS, RETURN '' not NONE!
-
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/arrays_and_strings/reverse_str.py b/src/further_examples/arrays_and_strings/reverse_str.py
deleted file mode 100644
index 442877f..0000000
--- a/src/further_examples/arrays_and_strings/reverse_str.py
+++ /dev/null
@@ -1,26 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-   
-def reverse_str(s):
-    ''' in place '''
-    sr_ls = []
-    for i in range(len(s)-1, -1, -1):
-        sr_ls.append(s[i])
-    return ''.join(sr_ls)
-        
-
-
-
-def main():
-    s1 = 'abcdefg'
-    s2 = 'buffy'
-    s3 = ''
-    print(reverse_str(s1))
-    print(reverse_str(s2))
-    print(reverse_str(s3))
-                   
-if __name__ == '__main__':
-    main()
-
diff --git a/src/further_examples/arrays_and_strings/reverse_words_setence.py b/src/further_examples/arrays_and_strings/reverse_words_setence.py
deleted file mode 100644
index 110eb33..0000000
--- a/src/further_examples/arrays_and_strings/reverse_words_setence.py
+++ /dev/null
@@ -1,44 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' reverse words in a setence, keeping the words right 
-   >>> str1 = 'I love Google and Python!'
-   >>> reverse_words(str1)
-   'Python! and Google love I'
-   >>> reverse_words('bla')
-   'bla'
-   >>> reverse_words('')
-   ''
-   >>> reverse_words_brute(str1)
-   'Python! and Google love I'
-   >>> reverse_words_brute('bla')
-   'bla'
-   >>> reverse_words_brute('')
-   ''
-'''
-
-def reverse_words(str1):
-    l1 = str1.split(' ')
-    l1.reverse()
-    return ' '.join(l1)
-    
-def reverse_words_brute(str1):
-    aux_lt = []
-    aux_str = ''
-    for i, c in enumerate(str1):
-        if c != ' ':
-            aux_str += c    # WE COULD HAVE USED LT HERE, MORE EFFICIENT
-        elif c == ' ':
-            aux_lt.append(aux_str)  # WE COULD HAVE USED STR BUT NOT EFFICIENT!
-            aux_str = ''
-    aux_lt.append(aux_str) # REMEMBER THAT THE LAST ONE DOEN'T HAVE SPACE!
-    aux_lt.reverse()   
-    return ' '.join(aux_lt)
-
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/arrays_and_strings/verify_if_perm.py b/src/further_examples/arrays_and_strings/verify_if_perm.py
deleted file mode 100644
index b4476be..0000000
--- a/src/further_examples/arrays_and_strings/verify_if_perm.py
+++ /dev/null
@@ -1,49 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-   
-def ver_perm(s1, s2):
-    ''' worst case O(nlogn + mlogm) = O(NlogN) '''
-    if len(s1) != len(s2): return False
-    s1 = sorted(s1)
-    s2 = sorted(s2)
-    return s1 == s2
-
-from collections import Counter
-def ver_perm_dict(s1, s2):
-    ''' worst case O(n + n +2n) = O(n)'''
-    if len(s1) != len(s2): return False
-    dict_aux = Counter()
-    for c in s1:
-        dict_aux[c] += 1
-    for c in s2:
-        dict_aux[c] -= 1
-    for item in dict_aux:
-        if dict_aux[item]:
-            return False
-    return True
-
-import time
-def main():
-    s1 = 'ufyfbufyfb'
-    s2 = 'buffybuffy'
-    s3 = 'uuyfbuuyfb'
-    s4 = ''
-    start = time.time()
-    print(ver_perm(s1, s2))
-    print(ver_perm(s1, s3))
-    print(ver_perm(s1, s4))
-    final1 = time.time() - start
-    
-    start = time.time()
-    print(ver_perm_dict(s1, s2))
-    print(ver_perm_dict(s1, s3))
-    print(ver_perm_dict(s1, s4))
-    final2 = time.time() - start
-    
-    print(final2-final1)
-                      
-if __name__ == '__main__':
-    main()
-
diff --git a/src/further_examples/bit_operations/clear_bits.py b/src/further_examples/bit_operations/clear_bits.py
deleted file mode 100644
index e5802cd..0000000
--- a/src/further_examples/bit_operations/clear_bits.py
+++ /dev/null
@@ -1,40 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Clear a bit in a binary number. It is almost like the reverse of set bit:
-    1) first create a number filled of 1s, with 0 at i (can create 0001000 and ~)
-    2) AND the number so it clears the ith bit
-        
-    >>> num = int('10010000', 2)
-    >>> clear_bit(num, 4)   
-    '0b10000000'
-    >>> num = int('10010011', 2)
-    >>> clear_all_bits_from_i_to_0(num, 2)  
-    '0b10010000'
-    >>> num = int('1110011', 2)
-    >>> clear_all_bits_from_most_sig_to_1(num, 2)  
-    '0b11'
-'''
-
-
-
-def clear_bit(num, i):
-    mask = ~ (1 << i)   # -0b10001
-    return bin(num & mask)
-
-
-def clear_all_bits_from_i_to_0(num, i):
-    mask = ~ ( (1 << (i+1)) - 1)   
-    return bin(num & mask)    
-
-
-def clear_all_bits_from_most_sig_to_1(num, i):
-    mask =  ( 1 << i) -1
-    return bin(num & mask)       
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/bit_operations/get_bit.py b/src/further_examples/bit_operations/get_bit.py
deleted file mode 100644
index a32c71e..0000000
--- a/src/further_examples/bit_operations/get_bit.py
+++ /dev/null
@@ -1,41 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Get a bit in a binary number:
-    1) Shifts 1 over by i bits
-    2) make an AND with the number
-    3) all the other than the bit at i are clean, now compare to 0
-    4) if the new value is not 0, bit i is 1
-    >>> num = int('0100100', 2)
-    >>> get_bit(num, 0)   
-    0
-    >>> get_bit(num, 1)   
-    0
-    >>> get_bit(num, 2)   
-    1
-    >>> get_bit(num, 3)   
-    0
-    >>> get_bit(num, 4)   
-    0
-    >>> get_bit(num, 5)   
-    1
-    >>> get_bit(num, 6)   
-    0
-'''
-
-
-
-def get_bit(num, i):
-    mask = 1 << i
-    return num & mask != 0
-
-
-    
-    
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/bit_operations/set_bit.py b/src/further_examples/bit_operations/set_bit.py
deleted file mode 100644
index 3f98336..0000000
--- a/src/further_examples/bit_operations/set_bit.py
+++ /dev/null
@@ -1,38 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Set a bit in a binary number:
-    1) Shifts 1 over by i bits
-    2) make an OR with the number, only the value at bit i will change and all the others bit
-    of the mask are zero so will not affect the num
-    >>> num = int('0100100', 2)
-    >>> set_bit(num, 0)   
-    '0b100101'
-    >>> set_bit(num, 1)   
-    '0b100110'
-    >>> set_bit(num, 2)    # nothing change
-    '0b100100'
-    >>> set_bit(num, 3)   
-    '0b101100'
-    >>> set_bit(num, 4)   
-    '0b110100'
-    >>> set_bit(num, 5)     # nothing change
-    '0b100100'
-'''
-
-
-
-def set_bit(num, i):
-    mask = 1 << i
-    return bin( num | mask ) 
-
-
-    
-    
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/linked_list/check_pal.py b/src/further_examples/linked_list/check_pal.py
deleted file mode 100644
index 5bf971e..0000000
--- a/src/further_examples/linked_list/check_pal.py
+++ /dev/null
@@ -1,40 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Given a linked list, check if the nodes form a palindrome '''
-
-from linked_list_fifo import LinkList, Node
-
-def isPal(l1):
-    if len(l1) < 2: return True
-    if l1[0] != l1[-1]: return False
-    return isPal(l1[1:-1])
-
-    
-    
-def checkllPal(ll):
-    node = ll.head
-    l1 = []
-    while node:
-        l1.append(node.value)   
-        node = node.next
-    return isPal(l1)  
-
-        
-
-def main():
-    ll = LinkList()
-    l1 = [1, 2, 3, 2, 1]
-    for i in l1:
-        ll.addNode(i)
-    print(checkllPal(ll))
- 
-    ll.addNode(2)
-    ll.addNode(3)
-    print(checkllPal(ll))
-    
-                       
-if __name__ == '__main__':
-    main()
-
diff --git a/src/further_examples/linked_list/circ_ll.py b/src/further_examples/linked_list/circ_ll.py
deleted file mode 100644
index ba6d3b3..0000000
--- a/src/further_examples/linked_list/circ_ll.py
+++ /dev/null
@@ -1,72 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-''' Build a class for a circular linked list and implement a function to see whether
-    a linked list is circular'''
-
-from linked_list_fifo import Node, LinkList
-
-class Node(object):
-    def __init__(self, value = None, next = None):
-        self.value = value
-        self.next = next
-
-
-class CircLinkList(object):
-    def __init__(self):
-        self.head = None
-        self.tail = None
-        self.lenght = 0
-    
-    def addNode(self, value):
-        node = Node(value, self.head)
-        if not self.head:
-            self.head = node
-        if self.tail:
-           self.tail.next = node
-        self.tail = node
-        self.lenght += 1
-        
-    def printList(self):
-        size = self.lenght
-        node = self.head
-        i = 0
-        while i < size:
-            print(node.value)
-            node = node.next   
-            i += 1
-        
-        
- 
-def isCircularll(ll):
-    p1 = ll.head
-    p2 = ll.head
-    
-    while p2 and p2.next:
-        p1 = p1.next
-        p2 = p2.next.next
-        
-        if p1 == p2:
-            return True
-    return False
-
-def main():
-    ll = CircLinkList()
-    for i in range(10):
-        ll.addNode(i)
-    ll.printList()
-    
-    print(isCircularll(ll))
-    
-    ll2 = LinkList()
-    for i in range(10):
-        ll2.addNode(i)
-    ll2.printList() 
-
-    print(isCircularll(ll2)) 
-    
-                   
-if __name__ == '__main__':
-    main()
diff --git a/src/further_examples/linked_list/double_linked_list_fifo.py b/src/further_examples/linked_list/double_linked_list_fifo.py
deleted file mode 100644
index 349ead6..0000000
--- a/src/further_examples/linked_list/double_linked_list_fifo.py
+++ /dev/null
@@ -1,53 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Implement a double-linked list, which is very simple, we just need inherets from a Linked List Class and  add an attribute for prev.'''
-
-from linked_list_fifo import LinkList
-
-class dNode(object):
-    def __init__(self, value = None, next = None):
-        self.value = value
-        self.next = next
-        self.prev = None    # THIS IS THE EXTRA ATTRIBUTE FOR DOUBLE L
-        self.children = None    # THIS IS NOT USED HERE, IS EXAMPLES WITH MANY LL INSIDE LLs
-        
-class dLinkList(LinkList):
- 
-    def addNode(self, value):
-        node = dNode(value)
-        if not self.head:
-            self.head = node
-        if self.tail:
-            node.prev = self.tail   # ADD THIS WHEN DOUBLE L
-            self.tail.next = node
-        self.tail = node
-        self.length += 1
-    
-            
-    def printListInverse(self): # THIS IS THE EXTRA METHOD FOR DOUBLE L
-        node = self.tail
-        while node:
-            print(node.value)
-            node = node.prev
- 
-                        
-        
-
-from collections import Counter
-
-def main():
-  
-    ll = dLinkList()
-    for i in range(1, 10):
-        ll.addNode(i)
-    print('Printing the list...')
-    ll.printList()
-    print('Now, printing the list inversely...')
-    ll.printListInverse()
-    
-  
-    
-if __name__ == '__main__':
-    main()
diff --git a/src/further_examples/linked_list/find_kth.py b/src/further_examples/linked_list/find_kth.py
deleted file mode 100644
index bcac35c..0000000
--- a/src/further_examples/linked_list/find_kth.py
+++ /dev/null
@@ -1,105 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Find the mth-to-last element of a linked list.
-    One option is having two pointers, separated by m. P1 start at the roots (p1 = self.root) and p2 is m-behinf pointer, which is created when p1 is at m. When p1 reach the end, p2 is the node. '''
-
-from linked_list_fifo import Node
-
-class LinkList(object):
-    def __init__(self):
-        self.head = None
-        self.tail = None
-        self.lenght = 0
-        
-    def addNode(self, value):
-        node = Node(value)
-        if not self.head:
-            self.head = node
-        if self.tail:
-            self.tail.next = node
-        self.tail = node
-        self.lenght += 1
-        
-    def removeNode(self, index):
-        prev = None
-        node = self.head
-        i = 0
-        while node and i < index:
-            prev = node
-            node = node.next
-            i += 1
-        if i == index:    
-            if not prev:
-                self.head = node.next
-            else:
-                prev.next = node.next
-            self.lenght -= 1
-        else:
-            print('Index not found')       
-        
-    def findkth_from_begin(self, k):
-        node = self.head
-        i = 0
-        while node and i < k:
-            node = node.next
-            i += 1
-        while node:
-            print(node.value)
-            node = node.next
-            
-    def findkth_to_last(self, k):
-        node = self.head
-        key = self.lenght - k
-        i = 0
-        while node and i < key:
-            node = node.next
-            i += 1
-        print(node.value)
-
-    def findkth_to_last_2pointers(self, k):
-        node = self.head
-        pointer = self.head
-        i = 0
-        while pointer and i < k:
-            pointer = pointer.next
-            i += 1
-        while pointer:
-            node = node.next
-            pointer = pointer.next
-        print(node.value)
-        
-    def findkth_to_last_2pointers2(self, k):
-        p1 = self.head
-        p2 = self.head
-        i = 0
-        while p1:
-            if i >= k: # ---> notice >= not >!
-                p2 = p2.next
-            p1 = p1.next
-            i += 1
-        print(p2.value)
-           
-            
-def main():
-    ll = LinkList()
-    for i in range(1, 11):
-        ll.addNode(i)
-    # list is 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11
-    # so 0th from last is 11, 1th to last is 10, 
-    # 2th from last is 9!
-    
-    
-    print('Finding from begin...')
-    ll.findkth_from_begin(2)    
-    print('Finding to last, case 1...')
-    ll.findkth_to_last(2) #9  
-    print('Finding to last, case 2...')
-    ll.findkth_to_last_2pointers(2)  
-    print('Finding to last, case 3...')
-    ll.findkth_to_last_2pointers2(2)  
-              
-if __name__ == '__main__':
-    main()            
-
diff --git a/src/further_examples/linked_list/hash_table.py b/src/further_examples/linked_list/hash_table.py
deleted file mode 100644
index e367ea7..0000000
--- a/src/further_examples/linked_list/hash_table.py
+++ /dev/null
@@ -1,65 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' The first example design a Hash table using chaining to avoid collisions. The second 
-    uses two lists.'''
-
-from linked_list_fifo import Node, LinkList
-
-class HashTableLL(object):
-    def __init__(self, size):
-        self.size = size
-        self.slots = []
-        self._createHashTable()
-
-    def _createHashTable(self):
-        for i in range(self.size) :
-            self.slots.append(LinkList())
-    
-    def findIndex(self, item):
-        return item%self.size
-
-    def addItem(self, item):
-        index = self.findIndex(item)
-        self.slots[index].addNode(item)
-        return self
-
-    
-    def delItem(self, item):
-        index = self.findIndex(item)
-        self.slots[index].deleteNode(item)
-        return self
-
-
-    def printHashTable(self):
-        for i in range(self.size):
-            print('\nSlot {}:'.format(i))
-            print(self.slots[i].printList())
-            
-    
-
-       
-
-def test_hash_tables():
-    H1 = HashTableLL(3)
-    for i in range (0, 20):
-        H1.addItem(i)
-    H1.printHashTable()
-    print('\n\nNow deleting:')
-    H1.delItem(0)   
-    H1.delItem(0)        
-    H1.delItem(0) 
-    H1.delItem(0) 
-    H1.printHashTable()
-'''
-    H2 = HashTable2L(3)
-    H2[54]="buffy"
-    H2[26]="xander"
-    H2[17]="giles"
-    print(H.2slots)
-'''
-
-
-if __name__ == '__main__':
-    test_hash_tables()       
diff --git a/src/further_examples/linked_list/linked_list_fifo.py b/src/further_examples/linked_list/linked_list_fifo.py
deleted file mode 100644
index c7777a3..0000000
--- a/src/further_examples/linked_list/linked_list_fifo.py
+++ /dev/null
@@ -1,183 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' A class for a linked list that has the nodes in a FIFO order (such as a queue)'''
-
-
-class Node(object):
-    def __init__(self, value = None, next = None):
-        self.value = value
-        self.next = next
-        
-class LinkList(object):
-    def __init__(self):
-        self.head = None
-        self.tail = None
-        self.length = 0
-    
-    def addNode(self, value):
-        node = Node(value)
-        if not self.head:
-            self.head = node
-        if self.tail:
-            self.tail.next = node
-        self.tail = node
-        self.length += 1
-    
-    def printList(self):
-        node = self.head
-        while node:
-            print(node.value)
-            node = node.next
-     
-    def addInOrder(self, item):
-        new_node = Node(item)
-        node = self.head
-        previous = None
-        stop = False
-        while node and not stop:
-            if node.value > item:
-                stop = True
-            else:
-                previous = node
-                node = node.next
-
-        if not previous:
-            new_node.next = self.head
-            self.head = new_node
-        else:
-            new_node.next = node 
-            previous.next = new_node
-    
-            
-    
-    def deleteNode(self, index):
-        prev = None
-        node = self.head
-        i = 0
-        while node and i < index:
-            prev = node
-            node = node.next
-            i += 1
-        if i == index:
-            if not prev:
-                self.head = node.next
-            else:
-                prev.next = node.next
-            self.length -= 1
-        else:
-            print('Index not found!')
-
-
-    def deleteNodeIfOrdered(self, item):
-        node = self.head
-        previous = None
-        found = False
-        while node and not found:
-            if node.value == item:
-                found = True
-            else:
-                previous = node
-                node = node.next
-        
-        if found:
-            if not previous:
-                self.head = node.next
-            else:
-                previous.next = node.next
-        else:
-            print('Node not found!')            
-            
-                       
-    def removeDupl(self):
-        prev = None
-        node = self.head
-        aux_dict = Counter()      
-        while node:           
-            value_here = node.value
-            if aux_dict[value_here] == 0:
-                aux_dict[value_here] = 1
-            else:              
-                if prev == None:
-                    self.head = node.next
-                else:
-                    prev.next = node.next
-                self.length -= 1              
-            prev = node
-            node = node.next   
-            
-    def removeDupl_no_buf(self):
-        node = self.head
-        while node:
-            pivot = node.value
-            pointer = node.next
-            prev = node
-            while pointer:
-                value_here = pointer.value
-                if value_here == pivot:
-                    prev.next = pointer.next
-                    self.length -= 1 
-                prev = pointer
-                pointer = pointer.next
-            node = node.next      
-                    
-    def searchIfOrdered(self, item):
-        node = self.head
-        found = False
-        stop = False
-        while node and not found and not stop:
-            if node.value  == item:
-                found = True
-            else:
-                if node.value > item:
-                    stop = True
-                else:
-                    node = node.next
-        return found                        
-    
-    
-    
-    
-        
-
-from collections import Counter
-
-def main():
-    
-    ll = LinkList()
-    for i in range(1, 10):
-        ll.addNode(i)
-        ll.addNode(i+1)
-    print('Linked List with duplicates:')    
-    ll.printList()
-    print('Length before deleting duplicate is: ', ll.length)
-    ll.removeDupl()
-    ll.printList()
-    print('Lenght after deleting duplicates is: ', ll.length)   
-    
-    ll = LinkList()
-    for i in range(1, 10):
-        ll.addNode(i)
-        ll.addNode(i+1)
-    print('Linked List with duplicates:')    
-    ll.printList()
-    print('Length before deleting duplicate is: ', ll.length)
-    ll.removeDupl_no_buf()
-    ll.printList()
-    print('Lenght after deleting duplicates is: ', ll.length)      
-
-
-    ll = LinkList()
-    l1 = [4, 2, 5, 7, 1, 9]
-    for i in l1:
-        ll.addInOrder(i)
-    ll.printList() 
-    print(ll.searchIfOrdered(7))       
-    print(ll.searchIfOrdered(3))    
-    ll.deleteNodeIfOrdered(7)
-    ll.printList() 
-
-    
-if __name__ == '__main__':
-    main()
diff --git a/src/further_examples/linked_list/linked_list_lifo.py b/src/further_examples/linked_list/linked_list_lifo.py
deleted file mode 100644
index ae061ac..0000000
--- a/src/further_examples/linked_list/linked_list_lifo.py
+++ /dev/null
@@ -1,82 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-''' Implement a unordered linked list, i.e. a LIFO linked list (like a stack) '''
-
-class Node(object):
-    def __init__(self, value = None, next = None):
-        self.value = value
-        self.next = next
-
-class LinkList(object):
-    def __init__(self):
-        self.head = None
-        self.lenght = 0
-        
-    def addNode(self, value):
-        node = Node(value)
-        node.next = self.head
-        self.head = node
-        self.lenght += 1
-        
-    def printList(self):
-        node = self.head
-        while node:
-            print(node.value)
-            node = node.next
-
-    def deleteNode(self, index):
-        prev = None
-        node = self.head
-        i = 0
-        while node and i < index:
-            prev = node
-            node = node.next
-            i += 1
-        if index == i:
-            self.lenght -= 1    
-            if prev == None:
-                self.head = node.next
-            else:
-                prev.next = node.next
-        else:
-            print('Node with index {} not found'.format(index))
-         
-
-    def deleteNodeByValue(self, item):
-        prev = None
-        node = self.head       
-        found = False
-        while node and not found:
-            if node.value == item:
-                found = True
-            else:
-                prev = node
-                node = node.next
-        if found:
-            self.lenght -= 1 
-            if prev == None:
-                self.head = node.next
-            else:
-                prev.next = node.next
-        else:
-            print('Node with value {} not found'.format(item))
-
-
-def main():
-    ll = LinkList()
-    for i in range(1, 11):
-        ll.addNode(i)
-    print('The list is:')
-    ll.printList()
-    print('The list after deleting node with index 2 (value 8):')
-    ll.deleteNode(2)
-    ll.printList()
-    print('The list after deleting node with value 2 (index 7):')
-    ll.deleteNodeByValue(2)
-    ll.printList()
-
-if __name__ == '__main__':
-    main()
diff --git a/src/further_examples/linked_list/part_ll.py b/src/further_examples/linked_list/part_ll.py
deleted file mode 100644
index 520e885..0000000
--- a/src/further_examples/linked_list/part_ll.py
+++ /dev/null
@@ -1,45 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' This function partionate a linked list in a value, where everything smaller than this value
-    goes to the front, and everything large goes to the back:'''
-
-from linked_list_fifo import LinkList, Node
-        
-def partList(ll, n):
-    more = LinkList()
-    less = LinkList()
-    node_old = ll.head
-    while node_old:
-        item = node_old.value
-        if item < n:
-            less.addNode(item)
-        elif item > n:
-            more.addNode(item)
-        node_old = node_old.next
-    
-    less.addNode(n)
-    nodemore = more.head
-    while nodemore:
-        less.addNode(nodemore.value)
-        nodemore = nodemore.next  
-    return less
-
-
-
-def main():
-    ll = LinkList()
-    l1 = [6, 7, 3, 4, 9, 5, 1, 2, 8]
-    for i in l1:
-        ll.addNode(i)
-    print('Before Part')    
-    ll.printList()
-    print('After Part')
-    newll = partList(ll, 6)
-    newll.printList()
-   
-                   
-if __name__ == '__main__':
-    main()
-
diff --git a/src/further_examples/linked_list/sum_ll.py b/src/further_examples/linked_list/sum_ll.py
deleted file mode 100644
index 504d627..0000000
--- a/src/further_examples/linked_list/sum_ll.py
+++ /dev/null
@@ -1,70 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Supposing two linked lists represening numbers, such that in each of their 
-    nodes they carry one digit. This function sums the two numbers that these
-    two linked lists represent, returning a third list representing the sum:'''
-
-from linked_list_fifo import Node, LinkList
-
-
-def sumlls(l1, l2):
-    lsum = LinkList()
-    dig1 = l1.head
-    dig2 = l2.head
-    next = 0
-    while dig1 and dig2:
-        d1 = dig1.value
-        d2 = dig2.value      
-        sum_d = d1 + d2 + next
-        if sum_d > 9:
-            next = sum_d//10
-            lsum.addNode(sum_d%10)
-            
-        else:   
-            lsum.addNode(sum_d)
-            next = 0
-        
-        dig1 = dig1.next
-        dig2 = dig2.next
-    
-    if dig1:
-        sum_d = next + dig1.value
-        if sum_d > 9:
-            lsum.addNode(sum_d%10)           
-        else:   
-            lsum.addNode(sum_d)   
-        dig1 = dig1.next
-    
-    if dig2:
-        sum_d = next + dig2.value
-        if sum_d > 9:
-            lsum.addNode(sum_d%10)           
-        else:   
-            lsum.addNode(sum_d)   
-        dig2 = dig2.next    
-    
-    
-    return lsum
-
-
-
-def main():
-    l1 = LinkList() # 2671
-    l1.addNode(1)
-    l1.addNode(7)
-    l1.addNode(6)
-    l1.addNode(2)
-    
-    l2 = LinkList() # 455
-    l2.addNode(5)
-    l2.addNode(5)
-    l2.addNode(4)
-    
-    lsum = sumlls(l1, l2)
-    lsum.printList()# 3126
-
-
-if __name__ == '__main__':
-    main()
diff --git a/src/further_examples/queues_stacks/animal_shelter.py b/src/further_examples/queues_stacks/animal_shelter.py
deleted file mode 100644
index 1a5b6d7..0000000
--- a/src/further_examples/queues_stacks/animal_shelter.py
+++ /dev/null
@@ -1,87 +0,0 @@
-class Node(object):
-    def __init__(self, name, which):
-        self.name = name
-        self.which = which
-        self.next = next
-        self.timestamp = 0
-
-
-
-class AnimalShelter(object):
-    def __init__(self):
-        self.first_cat = None
-        self.first_dog = None
-        self.last_cat = None
-        self.last_dog = None
-        self.counter = 0
-       
-
-    def enqueue(self, name, which):
-        self.counter += 1        
-        node = Node(name, which)   
-        node.timestamp = self.counter  
-        
-        if which == 'cat':
-            if not self.first_cat:
-                self.first_cat = node
-            if self.last_cat:
-                self.last_cat.next = node
-            self.last_cat = node
-            
-        if which == 'dog':
-            if not self.first_dog:
-                self.first_dog = node
-            if self.last_dog:
-                self.last_dog.next = node
-            self.last_dog = node  
-
-    
-    
-    def dequeueDog(self):
-        if self.first_dog:
-            node = self.first_dog
-            self.first_dog = node.next
-            return str(node.name)
-        raise Exception('No Dogs!')    
-                        
-                      
-                        
-    def dequeueCat(self):
-        if self.first_cat:
-            node = self.first_cat
-            self.first_cat = node.next
-            return str(node.name)
-        raise Exception('No Cats!')       
-
-
-
-    def dequeueAny(self):
-        nodecat = self.first_cat
-        nodedog = self.first_dog
-        if nodecat and not nodedog:
-            return self.dequeueCat()
-        elif nodedog and not nodecat:
-            return self.dequeueDog()
-        elif nodedog and nodecat:
-            if nodedog.timestamp < nodecat.timestamp:
-                return self.dequeueDog()
-            else: 
-                return self.dequeueCat()
-        raise Exception('No Animals!')   
-        
-
-
-
-def main():
-    qs = AnimalShelter()
-    qs.enqueue('bob', 'cat')
-    qs.enqueue('mia', 'cat')
-    qs.enqueue('yoda', 'dog')
-    qs.enqueue('wolf', 'dog')  
-    
-    assert(qs.dequeueDog() == 'yoda')
-    assert(qs.dequeueCat() == 'bob')         
-    print(qs.dequeueAny() == 'mia')     
-
-if __name__ == '__main__':
-    main()
diff --git a/src/further_examples/queues_stacks/queue_2_stacks.py b/src/further_examples/queues_stacks/queue_2_stacks.py
deleted file mode 100644
index ee9f185..0000000
--- a/src/further_examples/queues_stacks/queue_2_stacks.py
+++ /dev/null
@@ -1,60 +0,0 @@
-class MyQueue(object):
-    def __init__(self):
-        self.enq = []
-        self.deq = []
-        
-    def enqueue(self, item):
-        self.enq.append(item)    
-        
-    def _addStacks(self):
-        aux = []
-        if self.enq:
-            while self.enq:
-                aux.append(self.enq.pop())
-        aux.extend(self.deq) 
-        self.deq = aux
-    
-    def dequeue(self):
-        self._addStacks()
-        if self.deq:
-            return self.deq.pop()         
-        raise Exception('Cannot "deque": Queue is empty')
-        
-    def peek(self):
-        if self.deq:
-            return self.deq[-1]
-        elif self.enq:
-            return self.enq[0]
-        raise Exception('Cannot "peek": Queue is empty')
-   
-    def isEmpty(self):
-        return not (bool(self.enq) or bool(self.deq))
-    
-    def size(self):
-        return len(self.enq) + len(self.deq)
-
-    def printQueue(self):
-        self._addStacks()
-        if self.deq:
-            aux = str(self.deq).strip('[]') 
-            return 'Front --> ' + aux +' <-- Back' 
-        else:
-            raise Exception('Cannot "printQueue": Queue is empty')
-          
-
-def main():
-    q = MyQueue()
-    for i in range(1, 11):
-        q.enqueue(i)
-        print(q.printQueue())    
-    assert(q.peek() == 1)
-    assert(q.isEmpty() == False)
-    assert(q.size() == 10)    
-        
-    for i in range (1, 10):
-        q.dequeue()
-        print(q.printQueue()) 
-      
-    
-if __name__ == '__main__':
-    main()
diff --git a/src/further_examples/queues_stacks/setofStacks.py b/src/further_examples/queues_stacks/setofStacks.py
deleted file mode 100644
index 44c4c3e..0000000
--- a/src/further_examples/queues_stacks/setofStacks.py
+++ /dev/null
@@ -1,165 +0,0 @@
-from stack import Stack, Node
-
-class SetOfStacks(object):
-    def __init__(self, capacity):
-        assert(capacity > 1)
-        self.capacity = capacity        
-        self.stack_now = None
-        self.stack_now_size = 0               
-        self.old_stacks = []
-                    
-                    
-    def _checkIfFull(self):
-        return self.stack_now_size == self.capacity
-        
-
-    def _addStack(self):       
-        self.stack_now =  Stack()
-        self.stack_now_size = 0
-        
-                        
-    def _archiveStack(self):
-        self.old_stacks.append(self.stack_now)
-        self.stack_now = None
-        self.stack_now_size = 0   
-
-     
-    def _popItem(self):
-        if self.stack_now.top:
-            value = self.stack_now.top.value
-            if self.stack_now.top.next:
-                node = self.stack_now.top
-                self.stack_now.top = self.stack_now.top.next              
-            else:
-                self.stack_now = [] 
-            return value
-        raise Exception('Stack is empty.')    
-    
-
-    def numberOfStacksUsed(self):
-        if self.stack_now:
-            return len(self.old_stacks) + 1
-        else:
-            return len(self.old_stacks) 
-
-
-    def seeTop(self):
-        if self.stack_now:
-            return self.stack_now.top.value
-        elif self.old_stacks:
-            return self.old_stacks[-1].top.value
-        raise Exception('Stack is Empty')
-       
-            
-    def isEmpty(self):
-        return not (bool(self.stack_now) or bool(self.old_stacks))
-           
-    
-    def _sizeStackInUse(self):
-        return self.stack_now_size
-
-
-    def size(self):
-        return self._sizeStackInUse() + self.capacity*len(self.old_stacks)
-                        
- 
-    def push(self, item):
-        if not self.stack_now:
-             self._addStack()
-        
-        node = Node(item)
-        node.next = self.stack_now.top
-        self.stack_now.top = node         
-        
-        self.stack_now_size += 1
-        
-        if self._checkIfFull():
-            self._archiveStack()
-        
-        
-    def pop(self):  
-        if not self.stack_now:
-            if not self.old_stacks:
-                raise Exception('Stack is empty')
-            else:
-                self.stack_now = self.old_stacks.pop()
-                self.stack_now_size = self.capacity - 1
-                self._popItem()
-        else:
-            self._popItem() 
-            if self.stack_now:
-                self.stack_now_size -= 1
-            else:
-                self.stack_now_size = 0
-            
-
-        
-def main():
-    s1 = SetOfStacks(3)
-    
-    print(s1.numberOfStacksUsed())
-    print(s1.isEmpty())
-    print(s1.size())
-    
-    s1.push(1)
-    print('Push item 1')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())
-    
-    s1.push(2)
-    s1.push(3)
-    print('Push item 2 and 3')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())
-    
-    s1.push(4)
-    print('Push item 4')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())   
-    
-    s1.push(5)
-    print('Push item 5')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    s1.pop()
-    print('Pop item 5')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    s1.pop()
-    print('Pop item 4')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    s1.pop()
-    s1.pop()
-    print('Pop item 3 e 2')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    s1.pop()
-    print('Pop item 1')
-    print(s1.numberOfStacksUsed())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    
-    
-   
-if __name__ == '__main__':
-    main()           
diff --git a/src/further_examples/queues_stacks/setofStacksList.py b/src/further_examples/queues_stacks/setofStacksList.py
deleted file mode 100644
index a9c5d9d..0000000
--- a/src/further_examples/queues_stacks/setofStacksList.py
+++ /dev/null
@@ -1,154 +0,0 @@
-from stack import StackList
-
-class SetOfStacksList(object):
-    def __init__(self, capacity):
-        assert(capacity > 1)
-        self.capacity = capacity        
-        self.stack_now = []            
-        self.old_stacks = []                   
-                    
-    def _checkIfFull(self):
-        return len(self.stack_now) == self.capacity
-              
-                        
-    def _archiveStack(self):
-        self.old_stacks.append(self.stack_now)
-        self.stack_now = []
-
-
-    def _popItem(self):
-        if self.stack_now:
-            return self.stack_now.pop()
-        raise Exception('Stack is empty.')    
- 
- 
-    def _sizeStackInUse(self):
-        return len(self.stack_now)  
-
-
-    def numberOfStacksUsed(self):
-        if self.stack_now:
-            return len(self.old_stacks) + 1
-        else:
-            return len(self.old_stacks) 
-
-
-    def seeTop(self):
-        if self.stack_now:
-            return self.stack_now[-1]
-        elif self.old_stacks:
-            return self.old_stacks[-1][-1]
-        raise Exception('Stack is Empty')
-       
-            
-    def isEmpty(self):
-        return not(bool(self.stack_now) or bool(self.old_stacks))
-           
-           
-    def size(self):
-        return len(self.stack_now) + self.capacity*len(self.old_stacks)
-                        
-                        
-    def push(self, item):
-        self.stack_now.append(item)         
-        if self._checkIfFull():
-            self._archiveStack()
-        
-        
-    def pop(self):  
-        if not self.stack_now:
-            if not self.old_stacks:
-                raise Exception('Stack is empty')
-            else:
-                self.stack_now = self.old_stacks.pop()
-        return self.stack_now.pop()
-        
-    def popAt(self, index):
-        number_of_stacks = self.size()
-        if index < number_of_stacks:
-            if index == number_of_stacks - 1 and  self.stack_now:
-                return self.stack_now.pop()
-            if index < number_of_stacks - 1:
-                stack_here = self.old_stacks[index]
-                return stack_here.pop()
-            raise Exception('Stack at index {} is empty.'.format(index))
-        raise Exception('Index larger than the number of stacks.')
-            
-    def printStacks(self):
-        return str(self.old_stacks), str(self.stack_now)
-
-        
-def main():
-    s1 = SetOfStacksList(3)
-    
-    print(s1.numberOfStacksUsed())
-    print(s1.isEmpty())
-    print(s1.size())
-    
-    s1.push(1)
-    print('Push item 1')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())
-    
-    s1.push(2)
-    s1.push(3)
-    print('Push item 2 and 3')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())
-    
-    s1.push(4)
-    print('Push item 4')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())   
-    
-    s1.push(5)
-    print('Push item 5')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    s1.pop()
-    print('Pop item 5')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    s1.pop()
-    print('Pop item 4')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    s1.pop()
-    s1.pop()
-    print('Pop item 3 e 2')
-    print(s1.numberOfStacksUsed())
-    print(s1.seeTop())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    s1.pop()
-    print('Pop item 1')
-    print(s1.numberOfStacksUsed())
-    print(s1.isEmpty())
-    print(s1.size())  
-    
-    
-    s2 = SetOfStacksList(3)
-    for i in range(1, 11):
-        s2.push(i)
-    print(s2.printStacks())
-    print(s2.popAt(2))
-    
-   
-if __name__ == '__main__':
-    main()           
diff --git a/src/further_examples/queues_stacks/sort_stack.py b/src/further_examples/queues_stacks/sort_stack.py
deleted file mode 100644
index d6dcc80..0000000
--- a/src/further_examples/queues_stacks/sort_stack.py
+++ /dev/null
@@ -1,21 +0,0 @@
-def sortStack(s):
-    bufs = []
-    while s:
-        item = s.pop()
-        count, i = 0, 0
-        while bufs and bufs[-1] > item:
-            s.append(bufs.pop())
-            count += 1
-        bufs.append(item)  
-        while i < count:
-            bufs.append(s.pop())
-            i += 1
-    return bufs
-
-def main():
-    s = [3, 5, 1, 2, 6, 7, 8]
-    print(sortStack(s))
-
-    
-if __name__ == '__main__':
-    main()
diff --git a/src/further_examples/queues_stacks/stackMinElemO1.py b/src/further_examples/queues_stacks/stackMinElemO1.py
deleted file mode 100644
index ee29e77..0000000
--- a/src/further_examples/queues_stacks/stackMinElemO1.py
+++ /dev/null
@@ -1,107 +0,0 @@
-from stack import Stack, Node, StackList
-
-
-class StackMinElen(Stack):
-    def __init__(self):
-        self.top = None
-        self.mins = []
-              
-    def printMin(self):
-        if self.mins:
-            return self.mins[-1]
-        raise Exception('Stack is empty.')
-
-
-    def pop(self):
-        if self.top:
-            self.mins.pop()
-            node = self.top
-            self.top = node.next      
-            return node.value    
-        raise Exception('Stack is empty.')
-
-    
-    def push(self, item): 
-        if self.top:
-            min_so_far = self.mins[-1]
-            if min_so_far > item:
-                self.mins.append(item)
-            else:
-                self.mins.append(min_so_far)
-        else:
-            self.mins.append(item)       
-        node = Node(item)
-        node.next = self.top
-        self.top = node
-        
-        
-        
-
-class StackListMinElen(StackList):
-    def __init__(self):
-        self.items = []
-        self.mins = []
-
-    def printMin(self):
-        if self.mins:
-            return self.mins[-1]
-        raise Exception('Stack is Empty')
-
-    def push(self, item):     
-        self.items.append(item)  
-        if self.mins:
-            if self.mins[-1] > item:
-                self.mins.append(item)
-            else:
-                self.mins.append(self.mins[-1])
-        else:
-            self.mins.append(item)
-                                                          
-    def pop(self):
-        if self.items:
-            self.mins.pop()
-            return self.items.pop()
-        raise Exception('Stack is Empty')
-
-
-
-
-        
-def main():
-    s1 = StackListMinElen()
-    l1 = [4, 2, 6, 3, 1, 5]
-    for i in l1:
-        s1.push(i)  
-    print('Min: ', s1.printMin())
-    print('Pop: ', s1.pop())
-    print('Min: ', s1.printMin())
-    print('Pop: ', s1.pop())
-    print('Min: ', s1.printMin())
-    print('Pop: ', s1.pop())        
-    print('Min: ', s1.printMin())
-    print('Pop: ', s1.pop())        
-    print('Min: ', s1.printMin())
-    print('Pop: ', s1.pop())        
-    print('Min: ', s1.printMin())   
-
-
-    s2 = StackMinElen()
-    l1 = [4, 2, 6, 3, 1, 5]
-    for i in l1:
-        s2.push(i)  
-    print('Min: ', s2.printMin())
-    print('Pop: ', s2.pop())
-    print('Min: ', s2.printMin())
-    print('Pop: ', s2.pop())
-    print('Min: ', s2.printMin())
-    print('Pop: ', s2.pop())        
-    print('Min: ', s2.printMin())
-    print('Pop: ', s2.pop())        
-    print('Min: ', s2.printMin())
-    print('Pop: ', s2.pop())        
-    print('Min: ', s2.printMin())   
-
-
-
-if __name__ == '__main__':
-    main()           
diff --git a/src/further_examples/queues_stacks/stack_.py b/src/further_examples/queues_stacks/stack_.py
deleted file mode 100644
index 931f095..0000000
--- a/src/further_examples/queues_stacks/stack_.py
+++ /dev/null
@@ -1,94 +0,0 @@
-#!/usr/bin/python3
-# steinkirch at gmail.com
-# astro.sunysb.edu/steinkirch
-
-class Node(object):
-    def __init__(self, value=None):
-        self.value = value
-        self.next = None
-
-
-class Stack(object):
-    def __init__(self):
-        self.top = None
-
-    def push(self, item):
-        node = Node(item)
-        node.next = self.top
-        self.top = node
-
-    def pop(self):
-        if self.top:
-            node = self.top
-            self.top = node.next            
-            return node.value
-        raise Exception('Stack is empty.')
-
-    def isEmpty(self):
-        return bool(self.top)
-    
-    def seeTop(self):
-        if self.top:
-            return self.top.value
-        raise Exception('Stack is empty.')
-    
-    def size(self):
-        node = self.top
-        count = 0
-        while node:
-            count +=1
-            node = node.next
-        return count
-   
-            
-class StackList(list):
-    def __init__(self):
-        self.items = []
-     
-    def push(self, item):
-        self.items.append(item)
-        
-    def pop(self):
-        if self.items:
-            return self.items.pop()
-        raise Exception('Stack is empty.')
-       
-    def seeTop(self):
-        if self.items:
-            return self.items[-1]
-        raise Exception('Stack is empty.')
-     
-    def size(self):
-        return len(self.items)
-        
-    def isEmpty(self):
-        return bool(self.items)
-   
-        
-def main():
-    s1 = StackList()
-    print(s1.isEmpty())
-    for i in range(1, 10):
-        s1.push(i)
-    print(s1.isEmpty())
-    print(s1.size())
-    print(s1.seeTop())
-    s1.pop()
-    print(s1.size())
-    print(s1.seeTop())       
-    
-    
-    s2 = Stack()
-    print(s2.isEmpty())
-    for i in range(1, 10):
-        s2.push(i)
-    print(s2.isEmpty())
-    print(s2.size())
-    print(s2.seeTop())
-    s2.pop()
-    print(s2.size())
-    print(s2.seeTop())    
-
-
-if __name__ == '__main__':
-    main()           
diff --git a/src/further_examples/searching/binary_search.py b/src/further_examples/searching/binary_search.py
deleted file mode 100644
index b942f79..0000000
--- a/src/further_examples/searching/binary_search.py
+++ /dev/null
@@ -1,112 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' A recursive and an iterative example of binary search in Python.
-    Remember: sequence must be sorted! You can return True/False or the index:
-    >>> l1 = [1, 2, 3, 4, 5, 6, 7]
-    >>> binary_search_rec(l1, 1)
-    0
-    >>> binary_search_rec(l1, 2)
-    1
-    >>> binary_search_rec(l1, 3)
-    2
-    >>> binary_search_rec(l1, 4)
-    3
-    >>> binary_search_rec(l1, 5)
-    4
-    >>> binary_search_rec(l1, 6)
-    5
-    >>> binary_search_rec(l1, 7)         
-    6
-    >>> binary_search_rec(l1, 8)       
-    >>> l1 = [1, 2, 3, 4, 5, 6]
-    >>> binary_search_rec(l1, 1)
-    0
-    >>> binary_search_rec(l1, 2)
-    1
-    >>> binary_search_rec(l1, 3)
-    2
-    >>> binary_search_rec(l1, 4)
-    3
-    >>> binary_search_rec(l1, 5)
-    4
-    >>> binary_search_rec(l1, 6)
-    5
-    >>> binary_search_rec(l1, 7) 
-    >>> l1 = [1, 2, 3, 4, 5, 6, 7]
-    >>> binary_search_iter(l1, 1)
-    0
-    >>> binary_search_iter(l1, 2)
-    1
-    >>> binary_search_iter(l1, 3)
-    2
-    >>> binary_search_iter(l1, 4)
-    3
-    >>> binary_search_iter(l1, 5)
-    4
-    >>> binary_search_iter(l1, 6)
-    5
-    >>> binary_search_iter(l1, 7)         
-    6
-    >>> binary_search_iter(l1, 8)       
-    >>> l1 = [1, 2, 3, 4, 5, 6]
-    >>> binary_search_iter(l1, 1)
-    0
-    >>> binary_search_iter(l1, 2)
-    1
-    >>> binary_search_iter(l1, 3)
-    2
-    >>> binary_search_iter(l1, 4)
-    3
-    >>> binary_search_iter(l1, 5)
-    4
-    >>> binary_search_iter(l1, 6)
-    5
-    >>> binary_search_iter(l1, 7)      
-'''
-    
-
-def binary_search_iter(seq, key):
-    hi, lo = len(seq), 0      
-    while lo < hi: # here is >> m = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
-    >>> binary_search_matrix_rec(m, 6)
-    (1, 2)
-    >>> binary_search_matrix_rec(m, 12)
-    >>> binary_search_matrix_iter(m, 6)
-    (1, 2)
-    >>> binary_search_matrix_iter(m, 12)   
-    >>> binary_search_matrix_iter(m, 1)
-    (0, 0)
-    
-    (2) Another solution is "discarding" arrays in the way. The efficiency is O(logm).
-    >>> m = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
-    >>> searching_matrix(m, 6)
-    (1, 2)
-    >>> searching_matrix(m, 12)   
-     
-'''
-    
-
-def binary_search_matrix_rec(m, key, lo=0, hi=None):   
-    if not m: return None
-    rows = len(m)
-    cols = len(m[0])
-    hi = hi or rows*cols
-    if hi > lo: # -----> REMEMBER THIS OR INDEX WILL EXPLODE!!!!!!!!
-        mid = (hi + lo)//2
-        row = mid//cols
-        col = mid%cols
-        item = m[row][col]
-        if key == item: return row, col
-        elif key < item: return binary_search_matrix_rec(m, key, lo, mid-1)
-        else: return binary_search_matrix_rec(m, key, mid+1, hi)
-    return None
-
-
-
-def binary_search_matrix_iter(m, key):
-    if not m: return None
-    rows = len(m)
-    cols = len(m[0])
-    lo, hi = 0, rows*cols
-    while lo < hi:  
-        mid = (hi + lo)//2
-        row = mid//rows
-        col = mid%rows
-        item = m[row][col]
-        if key == item: return (row, col)
-        elif key < item: hi = mid
-        else: lo = mid +1
-    return None
-
-
-def searching_matrix(m, key):
-    if not m: return None
-    rows = len(m)
-    cols = len(m[0])
-    i, j = 0, cols -1    
-    while i < rows and j > 0:
-        item = m[i][j]
-        if key == item: return (i, j)
-        elif key < item: j -= 1
-        else: i += 1
-    return None
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
diff --git a/src/further_examples/searching/find_str_array_with_empty_str.py b/src/further_examples/searching/find_str_array_with_empty_str.py
deleted file mode 100644
index 6ccdc9b..0000000
--- a/src/further_examples/searching/find_str_array_with_empty_str.py
+++ /dev/null
@@ -1,52 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Given a sorted an array with empty strings, we use binary search to find some string (since
-    the list is sorted):
-    --> we deal with the empty strings with strip and then run to left and right, or move
-    mid to the closed non-empty str (remember that the index must be conserved):
-    >>> l1 = ['acre', 'ball', '', 'coach', '', 'cut', '']
-    >>> find_str_array_with_empty_str(l1, l1[0])
-    0
-    >>> find_str_array_with_empty_str(l1, l1[1])
-    1
-    >>> find_str_array_with_empty_str(l1, l1[3])
-    3
-    >>> find_str_array_with_empty_str(l1, l1[5])
-    5
-    >>> find_str_array_with_empty_str(l1, 'bla')
-'''
-
-
-def find_str_array_with_empty_str(seq, s1):
-    if not seq or not s1: return None
-    hi = len(seq)
-    lo = 0
-    while hi > lo:
-        mid = (hi+lo)//2
-        
-        if seq[mid] == '':
-            while True:
-                left = mid-1
-                right = mid+1
-                if left < lo or right > hi: return None
-                elif right < hi and seq[right]: 
-                    mid = right
-                    break
-                elif left > lo and seq[left]: 
-                    mid = left
-                    break
-                right += 1
-                left -= 1
-       
-        if s1 == seq[mid] == s1: return mid
-        elif s1 < seq[mid]: hi = mid 
-        else: lo = mid + 1
-    
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/sorting/merge_sort.py b/src/further_examples/sorting/merge_sort.py
deleted file mode 100644
index 7797b22..0000000
--- a/src/further_examples/sorting/merge_sort.py
+++ /dev/null
@@ -1,70 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Some examples of how to implement Merge Sort in Python 
-    --> RUNTIME: WORST/BEST/AVERAGE Is O(nlogn)
-    --> space complexity is O(n) for arrays
-    --> not in place, good for large arrays
-    >>> seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
-    >>> merge_sort(seq) == sorted(seq)
-    True
-    >>> seq2 = [3, 3, 3, 3, 3, 3, 3, 3]
-    >>> merge_sort(seq2) == sorted(seq2)
-    True
-    >>> seq3 = []
-    >>> merge_sort(seq3) == sorted(seq3)
-    True
-'''
-
-''' This is the main function that keep dividing the seq '''
-def merge_sort(seq):
-    if len(seq) < 2 : return seq    # base case
-    mid = len(seq)//2
-    left, right = None, None            # we could have declared the arrays here, 
-                                        # but this would allocate unecessary extra space   
-    if seq[:mid]: left = merge_sort(seq[:mid])
-    if seq[mid:]: right = merge_sort(seq[mid:])   # notice that mid is included!
-    
-    return merge(left, right)      # merge iteratively
-
-
-''' The two following merge functions are O(2n)=O(n) and O(n) respectively. They
-    illustrate many features in Python that '''
-def merge_2n(left, right):
-    if not left or not right: return left or right # nothing to be merged
-    result = []
-    while left and right:
-        if left[-1] >= right[-1]:
-            result.append(left.pop())
-        else:
-            result.append(right.pop())
-    result.reverse()
-    return (left or right) + result
-
-
-def merge(left, right):
-    if not left or not right: return left or right # nothing to be merged
-    result = []
-    i, j = 0, 0
-    while i < len(left) and j < len(right):
-        if left[i] <= right[j]:
-            result.append(left[i])
-            i += 1
-        else:
-            result.append(right[j])
-            j += 1
-    if left[i:] : result.extend(left[i:])   # REMEMBER TO TO ENXTEND NOT APPEND
-    if right[j:] : result.extend(right[j:])
-    return result
-    
-    
-   
-
-
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
-
diff --git a/src/further_examples/sorting/merge_sorted_things.py b/src/further_examples/sorting/merge_sorted_things.py
deleted file mode 100644
index fb935df..0000000
--- a/src/further_examples/sorting/merge_sorted_things.py
+++ /dev/null
@@ -1,95 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' --> In the case of two arrays: we can merge two arrays using the merge function from the merge sort
-    --> we can do this for files too, merging each two
-
-        1) If we can modify the arrays (pop) we can use:
-            def merge(left, right):
-                if not left or not right: return left or right # nothing to be merged
-                result = []
-                while left and right:
-                    if left[-1] >= right[-1]:
-                        result.append(left.pop())
-                    else:
-                        result.append(right.pop())
-                result.reverse()
-                return (left or right) + result
-        
-        
-        2) If we can't modify or we want to in place, we need two pointers:
-        >>> l1 = [1, 2, 3, 4, 5, 6, 7]
-        >>> l2 = [2, 4, 5, 8]
-        >>> merge(l1, l2)
-        [1, 2, 2, 3, 4, 4, 5, 5, 6, 7, 8]
-    
-    
-        3) For example, in the case we have a big array filled 0s in the end, and another array with the size of the number of 0s:
-        >>> l1 = [1, 2, 3, 4, 5, 6, 7, 0, 0, 0, 0]
-        >>> l2 = [2, 4, 5, 8]
-        >>> merge_two_arrays_inplace(l1, l2)
-        [1, 2, 2, 3, 4, 4, 5, 5, 6, 7, 8]
-        
-        
-        4) If we want to merge sorted files (and we have plenty of RAM to load all files):
-        >>> list_files = ['1.dat', '2.dat', '3.dat']
-        >>> merge_files(list_files)
-        [1, 1, 2, 3, 3, 3, 4, 5, 5, 5, 6, 7, 8]
-''' 
-
-def merge(left, right):
-    if not left or not right: return left or right # nothing to be merged
-    result = []
-    i, j = 0, 0
-    while i < len(left) and j < len(right):
-        if left[i] <= right[j]:
-            result.append(left[i])
-            i += 1
-        else:
-            result.append(right[j])
-            j += 1
-    if left[i:] : result.extend(left[i:])   # REMEMBER TO TO ENXTEND NOT APPEND
-    if right[j:] : result.extend(right[j:])
-    return result
-
-
- 
-def merge_two_arrays_inplace(l1, l2):
-    if not l1 or not l2: return l1 or l2 # nothing to be merged
-    p2 = len(l2) - 1    
-    p1 = len(l1) - len(l2) - 1   
-    p12 = len(l1) - 1
-    while p2 >= 0 and p1 >= 0:
-        item_to_be_merged = l2[p2]
-        item_bigger_array = l1[p1]       
-        if item_to_be_merged < item_bigger_array:
-            l1[p12] = item_bigger_array
-            p1 -= 1
-        else:
-            l1[p12] = item_to_be_merged
-            p2 -= 1
-        p12 -= 1
-    return l1
-
-
-def merge_files(list_files):
-    result = []
-    final = []
-    for filename in list_files:
-        aux = []
-        with open(filename, 'r') as file:
-            for line in file:
-                aux.append(int(line))
-        result.append(aux)  
-    final.extend(result.pop())
-    for l in result:
-        final = merge(l, final)
-    return final      
-
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
-
diff --git a/src/further_examples/sorting/quick_sort.py b/src/further_examples/sorting/quick_sort.py
deleted file mode 100644
index 201aa0c..0000000
--- a/src/further_examples/sorting/quick_sort.py
+++ /dev/null
@@ -1,74 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-
-''' Some examples of how to implement Quick Sort in Python 
-    --> RUNTIME: BEST/AVERAGE Is O(nlogn), WORST is O(n2)
-    --> the first example is not in place, the second is in place
-    --> test with two element arrays, identical values
-    
-    Quick sort in place:
-    1) select pivot as the index = 0
-    2) start pointer1 at index = 1 and pointer2 in the last element
-    3) while pointer1 < pointer2:
-        if value in pointer1 <= pivot
-            swap value in pointer1 with value in pointer2 and advanced pointer2
-        else
-            advance pointer1
-    4) now the array is like this:
-        [pivot, larger than pivot, smaller than pivot]
-    5) swap the pivot where pointer 1 stop
-    6) do recursively for [smaller] + [pivot] + [larger]
-    
-    >>> seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
-    >>> quick_sort(seq) == sorted(seq)
-    True
-    >>> quick_sort([3, 3, 3, 3, 3, 3]) == [3, 3, 3, 3, 3, 3]
-    True
-    >>> quick_sort([]) == []
-    True
-    >>> quick_sort([2,1]) == [1, 2]
-    True
-    >>> quick_sort_in(seq) == sorted(seq)
-    True
-    >>> quick_sort_in([3, 3, 3, 3, 3, 3]) == [3, 3, 3, 3, 3, 3]
-    True
-    >>> quick_sort_in([]) == []
-    True
-    >>> quick_sort_in([2,1]) == [1, 2]
-    True
-'''
-
-def quick_sort(seq):
-    if len(seq) < 2 : return seq    
-    mid = len(seq)//2
-    pi = seq[mid]
-    seq = seq[:mid] + seq[mid+1:]  
-    left = quick_sort([x for x in seq if x <= pi])    # REMEMBER TO INCLUDE X  (OR IN RIGHT)
-    right = quick_sort([x for x in seq if x > pi])   
-    return left + [pi] + right
-    
-
-
-
-def quick_sort_in(seq): 
-    if len(seq) < 2 : return seq 
-    if len(seq) == 2 and seq[0] > seq[1]:
-        seq[0], seq[1] = seq[1], seq[0]   # problems when only 2 elements because of swap
-    pivot = seq[0]  # start at the ends because we don't know how many elements
-    p1, p2 = 1, len(seq) -1   # set pointers at both ends
-    while p1 < p2: # must be < or out of range
-        if seq[p1] <= pivot: # must be <= because of pivot swap
-                seq[p1], seq[p2] = seq[p2], seq[p1]
-                p2 -= 1
-        else:
-            p1 += 1
-    seq[0], seq[p1] = seq[p1], pivot 
-    return quick_sort_in(seq[p1+1:]) + [seq[p1]] + quick_sort_in(seq[:p1])
-
-
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
diff --git a/src/further_examples/sorting/sort_anagrams_together.py b/src/further_examples/sorting/sort_anagrams_together.py
deleted file mode 100644
index c0b5b42..0000000
--- a/src/further_examples/sorting/sort_anagrams_together.py
+++ /dev/null
@@ -1,35 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' A method to sort an array so that all the anagrams are together. Since we only
-    want the anagrams to be grouped, we can use a dictionary for this task. This
-    algorithm is O(n).
-    >>> l1 = ['hat', 'ball', 'tha', 'cut', 'labl', 'hta', 'cool', 'cuy', 'uct']
-    >>> sort_anagrams_together(l1)
-    ['cut', 'uct', 'cool', 'ball', 'labl', 'hat', 'tha', 'hta', 'cuy']
-'''
-
-from collections import defaultdict
-def sort_anagrams_together(l1):
-    result = []
-    
-    # step 1 save the anagrams together
-    dict_aux = defaultdict(list) # rememebr to indicate the type
-    for word in l1:
-        key = ''.join(sorted(word)) # need to sort the strings and join it
-        dict_aux[key].append(word) # because only sorted give a list of each char
-    
-    # step 2 print the anagrams. Note that if you want everything
-    # sorted you would have to sort the keys and insert the angrams after that    
-    for key in dict_aux:
-        result.extend(dict_aux[key])
-        
-    return result
-    
-    
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/trees_graphs/binary_search_tree.py b/src/further_examples/trees_graphs/binary_search_tree.py
deleted file mode 100644
index a58c937..0000000
--- a/src/further_examples/trees_graphs/binary_search_tree.py
+++ /dev/null
@@ -1,102 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch 2013
-
-from binary_tree import BinaryTree, NodeBT
-
-''' Implementation of a binary search tree and its properties. 
-    We use the Binary Tree class and its Node class as superclasses, and  we modify the methods
-    that are needeed to create a BST (polymorphism). For example, the following bst:   
-       
-                              7                      ---> level 0
-                   4                  9              ---> level 1
-               2       5          8       10         ---> level 2
-             1            6                          ---> level 3 
-             
-    has the following properties:
-    
-        - SIZE OR NUMBER OF NODES: n = 10
-        - NUMBER OF BRANCHES OR INTERNAL NODES: b = n-1 = 9
-        - VALUE OF ROOT = 7
-        - MAX_DEPTH OR HEIGHT: h = 3
-        - IS BALANCED? YES
-        - IS BST? YES
-        - INORDER DFT: 1, 2, 4, 5, 6, 7, 8, 9, 10
-        - POSTORDER DFT: 1, 2, 6, 5, 4, 8, 10, 9, 7
-        - PREORDER DFT: 7, 4, 2, 1, 5, 6, 9, 8, 10
-        - BFT:  7, 4, 9, 2, 5, 8, 10, 1, 6
-'''
-
-
-class NodeBST(NodeBT):
-
-    def _addNextNode(self, value, level_here=1):
-        ''' Aux for self.addNode(value): for BST, best O(1), worst O(log n) '''
-        self.traversal = []
-        new_node = NodeBST(value, level_here)
-        if not self.item:
-            self.item = new_node
-        elif value < self.item:  
-            self.left = self.left and self.left._addNextNode(value, level_here+1) or new_node
-        else:
-            self.right = self.right and self.right._addNextNode(value, level_here+1) or new_node         
-        return self 
-     
-    def _searchForNode(self, value):
-        ''' Traverse the tree looking for the node. For BST it is O(logn) if the
-            tree is balanced, otherwise it can be O(n) '''
-        if self.item == value: return self
-        elif value > self.item and self.right: return self.right._findNode(value)
-        elif value < self.item and self.left: return self.left._findNode(value)
-        return None
-
-
-     
-class BinarySearchTree(BinaryTree):
-    '''     
-    >>> bst = BinarySearchTree()
-    >>> l1 = [7, 4, 5, 9, 2, 8, 1, 6, 10]
-    >>> for i in l1: bst.addNode(i)
-    >>> bst.hasNode(3)
-    False
-    >>> bst.hasNode(10)
-    True
-    >>> bst.printTree('pre')
-    [7, 4, 2, 1, 5, 6, 9, 8, 10]
-    >>> bst.printTree('post')
-    [1, 2, 6, 5, 4, 8, 10, 9, 7]
-    >>> bst.printTree('in')
-    [1, 2, 4, 5, 6, 7, 8, 9, 10]
-    >>> bst.printTree('bft')
-    [7, 4, 9, 2, 5, 8, 10, 1, 6]
-    >>> bst.getHeight()
-    3
-    >>> bst.isBST()
-    True
-    >>> bst.isBalanced()
-    False
-    >>> bst.isBalanced(2)
-    False
-    >>> bst.getAncestor(2, 9)
-    7
-    >>> bst.getAncestor(2, 9, 'bst')
-    7
-    >>> bst.getAncestor(2, 9, 'pre-post')
-    7
-    >>> bst.getAncestor(2, 9, 'post-in')
-    7
-    '''
-
-
-    def addNode(self, value):
-        ''' Add new node to the tree, by the left first, O(n).
-            The only difference from the Binary Tree class is the node class is
-            NodeBST and not NodeBT '''
-        if not self.root: self.root = NodeBST(value)
-        else: self.root._addNextNode(value) 
-          
-
-
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
-
diff --git a/src/further_examples/trees_graphs/binary_tree.py b/src/further_examples/trees_graphs/binary_tree.py
deleted file mode 100644
index a33fa1a..0000000
--- a/src/further_examples/trees_graphs/binary_tree.py
+++ /dev/null
@@ -1,464 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch 2013
-# http://astro.sunysb.edu/steinkirch
-
-
-
-
-''' Implementation of a binary tree and its properties. For example, the following bt:   
-   
-                               1                ---> level 0
-                        2             3         ---> level 1
-                  4         5                   ---> level 2
-              6      7                          ---> level 3
-            8   9                               ---> level 4   
-                                                
-    has the following properties:
-    
-        - SIZE OR NUMBER OF NODES: n = 9
-        - NUMBER OF BRANCHES OR INTERNAL NODES: b = n-1 = 8
-        - VALUE OF ROOT = 1
-        - MAX_DEPTH OR HEIGHT: h = 4
-        - IS BALANCED? NO
-        - IS BST? NO
-        - INORDER DFT: 8, 6, 9, 4, 7, 2, 5, 1, 3
-        - POSTORDER DFT: 8, 9, 6, 7, 4, 5, 2, 3, 1
-        - PREORDER DFT: 1, 2, 4, 6, 8, 9, 7, 5, 3
-        - BFT:  1, 2, 3, 4, 5, 6, 7, 8, 9
-'''
-
-from collections import deque
-class NodeBT(object):
-    def __init__(self, item=None, level=0):
-        ''' Construtor for a Node in the Tree '''
-        self.item = item
-        self.level = level
-        self.left = None
-        self.right = None
-        self.traversal = []   
-        #self.parent = None # not used here but can be necessary for some problems
-        
-    ''' 
-        METHODS TO MODIFY NODES
-    '''  
-    
-    def _addNextNode(self, value, level_here=1):
-        ''' Aux for self.addNode(value)'''
-        self.traversal = []
-        new_node = NodeBT(value, level_here)
-        if not self.item:
-            self.item = new_node
-        elif not self.left:
-            self.left = new_node
-        elif not self.right:
-            self.right = new_node
-        else:
-            self.left = self.left._addNextNode(value, level_here+1) 
-        return self  
-       
-
-
-    '''
-        METHODS TO PRINT/SHOW NODES' ATTRIBUTES 
-    '''   
-
-    def __repr__(self):
-        ''' Private method for this class'string representation'''
-        return '{}'.format(self.item)     
-
-    def _getDFTpreOrder(self, node):
-        ''' Traversal Pre-Order, O(n)'''
-        if node:
-            if node.item: self.traversal.append(node.item)
-            self._getDFTpreOrder(node.left)
-            self._getDFTpreOrder(node.right)   
-        return self
-                      
-    def _printDFTpreOrder(self, noderoot):
-        ''' Fill the pre-order traversal array '''
-        self.traversal = []
-        self._getDFTpreOrder(noderoot)
-        return self.traversal
-
-    def _getDFTinOrder(self, node):
-        ''' Traversal in-Order, O(n)'''
-        if node:
-            self._getDFTinOrder(node.left)
-            if node.item: self.traversal.append(node.item)
-            self._getDFTinOrder(node.right)   
-        return self
-                  
-    def _printDFTinOrder(self, noderoot):
-        ''' Fill the in-order traversal array '''
-        self.traversal = []
-        self._getDFTinOrder(noderoot)
-        return self.traversal
-
-    def _getDFTpostOrder(self, node):
-        ''' Traversal post-Order, O(n)'''
-        if node:
-            self._getDFTpostOrder(node.left)
-            self._getDFTpostOrder(node.right)   
-            if node.item: self.traversal.append(node.item)
-        return self      
-    
-    def _getBFT(self, node):
-        ''' Traversal bft, O(n)'''   
-        if node:
-            queue = deque() 
-            queue.append(node)
-            while len(queue) > 0:
-                current = queue.popleft()
-                if current.item: self.traversal.append(current)
-                if current.left: queue.append(current.left)
-                if current.right: queue.append(current.right)        
-        return self 
-
-    def _printBFT(self, noderoot):
-        ''' Fill the in-order traversal array '''
-        self.traversal = []
-        self._getBFT(noderoot)
-        return self.traversal
- 
-           
-    def _printDFTpostOrder(self, noderoot):
-        ''' Fill the post-order traversal array '''
-        self.traversal = []
-        self._getDFTpostOrder(noderoot)
-        return self.traversal
-
-    def _searchForNode(self, value):
-        ''' Traverse the tree looking for the node'''
-        if self.item == value: return self
-        else:
-            found = None
-            if self.left: found = self.left._searchForNode(value) 
-            if self.right: found =  found or self.right._searchForNode(value) 
-            return found
-
-    def _findNode(self, value):
-        ''' Find whether a node is in the tree.
-            if the traversal was calculated, it is just a membership
-            checking, which is O(1), otherwise it is necessary to traverse 
-            the binary tree, so best case is O(1) and worst is O(n). '''
-        if self.traversal: return value in self.traversal
-        else: return self._searchForNode(value)
-
-    def _isLeaf(self):
-        ''' Return True if the node is a leaf '''
-        return not self.right and not self.left
-
-    def _getMaxHeight(self):
-        ''' Get the max height at the node, O(n)'''
-        levelr, levell = 0, 0
-        if self.right:
-            levelr = self.right._getMaxHeight() + 1
-        if self.left:
-            levell = self.left._getMaxHeight() + 1          
-        return max(levelr, levell)  
-
-    def _getMinHeight(self, level=0):
-        ''' Get the min height at the node, O(n)'''
-        levelr, levell = -1, -1
-        if self.right:
-            levelr = self.right._getMinHeight(level +1)
-        if self.left:
-            levell = self.left._getMinHeight(level +1)           
-        return min(levelr, levell) + 1  
-    
-    def _isBalanced(self):
-        ''' Find whether the tree is balanced, by calculating heights first, O(n2) '''
-        if self._getMaxHeight() - self._getMinHeight() < 2:
-            return False
-        else:
-            if self._isLeaf():
-                return True
-            elif self.left and self.right:
-                return self.left._isBalanced() and   self.right._isBalanced()        
-            elif not self.left and self.right:
-                return  self.right._isBalanced() 
-            elif not self.right and self.left:
-                 return  self.right._isBalanced()    
-
-
-  
-    def _isBalancedImproved(self):
-        ''' Find whehter the tree is balanced in each node, O(n) '''
-        return 'To Be written'
-
-    ''' There are two solutions to check whether a bt is a bst:
-    (1) Do an inorder, check if the inorder is sorted. However inorder
-        can't handle the difference between duplicate values on the left
-        or on the right (if it is in the right, the tree is not bst).
-    '''  
-
-
-    def _isBST(self):
-        ''' Find whether the tree is a BST, inorder '''
-        if self.item:
-            if self._isLeaf(): return True  
-            elif self.left:
-                if self.left.item < self.item: return self.left._isBST() 
-                else: return False
-            elif self.right:
-                if self.right.item > self.item: return self.right._isBST()
-                else: return False
-        else:
-            raise Exception('Tree is empty')
- 
-
-    def _getAncestorBST(self, n1, n2):
-        ''' Return the ancestor of two nodes if it is a bst.
-            we are supposing the values in the tree are unique.'''
-        if n1 == self.item or n2 == self.item : return self.item 
-        elif self.item < n1 and self.item < n2:
-            self.right.getAncestorBST(n1, n2)
-        elif self.item > n1 and self.item > n2:
-            self.left.getAncestorBST(n1, n2)
-        else:
-            return self.item 
-
-   
-          
-    
-class BinaryTree(object):
-    '''
-    >>> bt = BinaryTree()
-    >>> for i in range(1, 10): bt.addNode(i)
-    >>> bt.hasNode(7)
-    True
-    >>> bt.hasNode(12)
-    False
-    >>> bt.printTree()
-    [1, 2, 4, 6, 8, 9, 7, 5, 3]
-    >>> bt.printTree('pre')
-    [1, 2, 4, 6, 8, 9, 7, 5, 3]
-    >>> bt.printTree('bft')
-    [1, 2, 3, 4, 5, 6, 7, 8, 9]
-    >>> bt.printTree('post')
-    [8, 9, 6, 7, 4, 5, 2, 3, 1]
-    >>> bt.printTree('in')
-    [8, 6, 9, 4, 7, 2, 5, 1, 3]
-    >>> bt.hasNode(9)
-    True
-    >>> bt.hasNode(11)
-    False
-    >>> bt.isLeaf(8)
-    True
-    >>> bt.getNodeLevel(1)
-    0
-    >>> bt.getNodeLevel(8)
-    4
-    >>> bt.getSizeTree()
-    9
-    >>> bt.isRoot(10)
-    False
-    >>> bt.isRoot(1)
-    True
-    >>> bt.getHeight()
-    4
-    >>> bt.isBST(1)
-    False
-    >>> bt.isBalanced()
-    False
-    >>> bt.isBalanced(2)
-    False
-    >>> bt.getAncestor(8, 5)
-    2
-    >>> bt.getAncestor(8, 5, 'pre-post')
-    2
-    >>> bt.getAncestor(8, 5, 'post-in')
-    2
-    '''
-  
-  
-       
-    def __init__(self):
-        ''' Construtor for the Binary Tree, which is a container of Nodes'''
-        self.root = None
-         
-
-    ''' 
-        METHODS TO MODIFY THE TREE
-    '''    
-    
-    def addNode(self, value):
-        ''' Add new node to the tree, by the left first, O(n) '''
-        if not self.root: self.root = NodeBT(value)
-        else: self.root._addNextNode(value) 
-
-    '''
-        METHODS TO PRINT/SHOW TREES' ATTRIBUTES 
-    '''    
-       
-    def __repr__(self):
-        ''' Private method for this class'string representation'''
-        return '{}'.format(self.item) 
-
-    def printTree(self, order = 'pre'):
-        ''' Print Tree in the chosen order '''
-        if self.root:
-            if order == 'pre': return self.root._printDFTpreOrder(self.root)
-            elif order == 'in': return self.root._printDFTinOrder(self.root)
-            elif order == 'post': return self.root._printDFTpostOrder(self.root)
-            elif order == 'bft': return self.root._printBFT(self.root)                       
-        else: raise Exception('Tree is empty')
-
-    def hasNode(self, value):
-        ''' Verify whether the node is in the Tree '''
-        return bool(self.root._findNode(value)) 
- 
-    def isLeaf(self, value):
-        ''' Return True if the node is a Leaf '''
-        node = self.root._searchForNode(value)
-        return node._isLeaf() 
-        
-    def getNodeLevel(self, item):
-        ''' Return the level of the node, best O(1), worst O(n) '''
-        node = self.root._searchForNode(item)
-        if node: return node.level
-        else: raise Exception('Node not found')
- 
-    def getSizeTree(self):
-        ''' Return how many nodes in the tree, O(n) ''' 
-        return len(self.root._printDFTpreOrder(self.root))
-        
-    def isRoot(self, value):
-        '''Return the root of the tree '''
-        return self.root.item == value
-    
-    def getHeight(self):
-        ''' Returns the height/depth of the tree, best/worst O(n)  '''
-        return self.root._getMaxHeight()
- 
-    def isBalanced(self, method=1):
-        ''' Return True if the tree is balanced'''
-        if method == 1:
-            ''' O(n2)'''
-            return self.root._isBalanced()    
-        else:
-            ''' O(n)'''
-            return self.root._isBalancedImproved()    
-    
-
-
-    ''' The followin methods are for searching the lowest common ancestor
-    in a BT. Since a simple BT does not have ordering, it can be O(n). If
-    we have a link for the ancestors, the steps are:
-        (1) search both trees in order to find the nodes separately
-        (2) list all ancestors 
-        (3) find first that mach  
-        obs: if we do this too many times we can do a pre and use the methods here'''
-
-    def isBST(self, method=1):
-        ''' Return True if the tree is BST'''
-        if method == 1:
-            inorder = self.root._printDFTinOrder(self.root)
-            return inorder == sorted(inorder)
-        elif method == 2:
-            return self.root._isBST()
-
-
-    def _getAncestorPreIn(self, preorder, inorder, value1, value2):
-        ''' Return the ancestor of two nodes with pre and in'''
-        root = preorder[0]
-        preorder = preorder[1:]
-        i = 0
-        item = inorder[0]
-        value1left, value2left = False, False      
-        while item != root and i < len(inorder): 
-            if item == value1: value1left = True
-            elif item == value2: value2left = True
-            i += 1
-            item = inorder[i]               
-        if (value1left and not value2left) or (value2left and not value1left):
-            return root
-        else:
-            return self._getAncestorPreIn(preorder, inorder[:i] + inorder[i+1:], value1, value2)
-
-    def _getAncestorPrePost(self, preorder, postorder, value1, value2):
-        ''' Return the ancestor of two nodes with pre and post'''
-        root = preorder[0]
-        preorder = preorder[1:]
-        postorder = postorder[:-1]              
-        value1right, value2right = False, False      
-        i = len(postorder)-1
-        itempre = preorder[0]
-        itempos = postorder[i]       
-        while itempre != itempos and i > 0:
-            if itempos == value1: value1right = True
-            elif itempos == value2: value2right = True                     
-            i -= 1
-            itempos = postorder[i]
-  
-        if (value1right and not value2right) or (value2right and not value1right):
-            return root
-        else:
-            return self._getAncestorPrePost(preorder, postorder[:i] + postorder[i+1:], value1, value2)        
-                      
-    def _getAncestorInPost(self, inorder, postorder, value1, value2):
-        ''' Return the ancestor of two nodes with in and post'''
-        root = postorder[-1]
-        postorder = postorder[:-1]              
-        value1left, value2left = False, False      
-        i = 0
-        item = inorder[i]      
-        while item != root and i < len(inorder):
-            if item == value1: value1left = True
-            elif item == value2: value2left = True                     
-            i += 1
-            item = inorder[i]
-  
-        if (value1left and not value2left) or (value2left and not value1left):
-            return root
-        else:
-            return self._getAncestorInPost(postorder, inorder[:i] + inorder[i+1:], value1, value2)      
- 
- 
-
- 
-        
-    def _getAncestorBST2(self, preorder, value1, value2):
-        ''' Return the ancestor of two nodes if it is a bst, using traversal'''
-        while preorder:
-            current = preorder[0]
-            if current < value1:
-                try: preorder = preorder[2:]
-                except: return current
-            elif current > value2:
-                try: preorder = preorder[1:]
-                except: return current
-            elif value1 <= current <= value2:
-                return current
-        return None  
-
-    def getAncestor(self, value1, value2, method='pre-in'):
-        ''' Return the commom ancestor for two nodes'''
-        if method == 'pre-in':
-            ''' Using pre and inorder, best/worst O(n)'''  
-            preorder = self.root._printDFTpreOrder(self.root)
-            inorder = self.root._printDFTinOrder(self.root)
-            return self._getAncestorPreIn(preorder, inorder, value1, value2)   
-        if method == 'pre-post':
-            ''' Using pre and postorder, best/worst O(n)'''  
-            preorder = self.root._printDFTpreOrder(self.root)
-            postorder = self.root._printDFTpostOrder(self.root)
-            return self._getAncestorPrePost(preorder, postorder, value1, value2)        
-        if method == 'post-in':
-            ''' Using in and postorder, best/worst O(n)'''  
-            inorder = self.root._printDFTinOrder(self.root)
-            postorder = self.root._printDFTpostOrder(self.root)
-            return self._getAncestorInPost(inorder, postorder, value1, value2)     
-        if method == 'bst':
-            if self.isBST():
-                return self.root._getAncestorBST(value1, value2)   
-                
-                #preorder = self.root._printDFTpreOrder(self.root)
-                #return self._getAncestorBST2(preorder, value1, value2)   
-            else:
-                return Exception('The tree is not a BST')     
-     
- 
-if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
diff --git a/src/further_examples/trees_graphs/traversals.py b/src/further_examples/trees_graphs/traversals.py
deleted file mode 100644
index a962d46..0000000
--- a/src/further_examples/trees_graphs/traversals.py
+++ /dev/null
@@ -1,131 +0,0 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-from BST import BST
-
-
-from collections import deque
-class TranversalBST(object):
-    def __init__(self):
-        self.bst = BST(None)
-        self.nodes = []
-        
-    def insert(self, value):
-        if not self.bst.value:
-            self.bst.value = value
-        else:
-            self.bst.insert(value)
-
-    def contains(self, value):
-        return bool(self.bst.find(value))
-
-    def get(self, index):
-        for i, value in enumerate(self.inorder()):
-            if i == index:
-                return value
-
-    def inorder(self):
-        current = self.bst  
-        self.nodes = []
-        stack = []
-        while len(stack) > 0 or current is not None:
-            if current is not None:
-                stack.append(current)   
-                current = current.left
-            else:
-                current = stack.pop()
-                self.nodes.append(current.value)
-                current = current.right
-        return self.nodes
-
-
-    def preorder(self):
-        self.nodes = []
-        stack = [self.bst]  
-        while len(stack) > 0:
-            curr = stack.pop()
-            if curr is not None:
-                self.nodes.append(curr.value)
-                stack.append(curr.right)
-                stack.append(curr.left)
-        return self.nodes
-
-
-    def preorder2(self):
-        self.nodes = []
-        current = self.bst  
-        stack = []
-        while len(stack) > 0 or current is not None:
-            if current is not None:
-                self.nodes.append(current.value)
-                stack.append(current)   
-                current = current.left
-            else:
-                current = stack.pop()               
-                current = current.right            
-        return self.nodes
-
-
-
-    def preorder3(self):
-        self.nodes = []
-        node = self.bst
-        if not node: return None
-        stack = []  
-        stack.append(node)  
-        while stack:
-            node = stack.pop()
-            self.nodes.append(node.value)
-            if node.right: stack.append(node.right) # RIGHT FIRST!
-            if node.left: stack.append(node.left)
-        return self.nodes
-
-
-
-    
-    def BFT(self):
-        self.nodes = []
-        node = self.bst
-        if not node: return None
-        queue = deque() 
-        queue.append(node)  
-        while queue:
-            node = queue.popleft()
-            self.nodes.append(node.value)
-            if node.left: queue.append(node.left) # LEFT FIRST!
-            if node.right: queue.append(node.right)
-
-        return self.nodes
-
-
-
-
-def main():
-    """
-            10 
-       5       15
-    1   6     11    50
-    """     
-    t = TranversalBST()
-    t.insert(10)
-    t.insert(5)
-    t.insert(15)
-    t.insert(1)
-    t.insert(6)
-    t.insert(11)
-    t.insert(50)
-    print(t.preorder())
-    print(t.preorder2())
-    print(t.preorder3()) 
-    print(t.inorder())
-    print(t.BFT())
-    '''
-    [10, 5, 1, 6, 15, 11, 50]
-    [10, 5, 1, 6, 15, 11, 50]
-    [10, 5, 1, 6, 15, 11, 50]
-    [1, 5, 6, 10, 11, 15, 50]
-    [10, 5, 15, 1, 6, 11, 50]
-    '''
-if __name__ == '__main__':
-    main()    
diff --git a/src/examples_in_my_book/general_problems/modules/__init__.py b/src/searching_and_sorting/searching/__init__.py
similarity index 100%
rename from src/examples_in_my_book/general_problems/modules/__init__.py
rename to src/searching_and_sorting/searching/__init__.py
diff --git a/src/searching_and_sorting/searching/binary_search.py b/src/searching_and_sorting/searching/binary_search.py
new file mode 100644
index 0000000..79570cf
--- /dev/null
+++ b/src/searching_and_sorting/searching/binary_search.py
@@ -0,0 +1,66 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def binary_search(array, item, hi=None, lo=0):
+    '''
+    >>> binary_search([2,3,5,6,8,10,15,23], 15)
+    6
+    >>> binary_search([2,3,5,6,8,10,15,23], 4)
+    False
+    >>> binary_search([1,3,4,5,7,8 ,10,12,23], 10)
+    6
+    >>> binary_search([1,3,4,5,7,8 ,10,12,23], 22)
+    False
+    '''
+
+    hi = hi or len(array)
+    if hi < lo:
+        return False
+
+    mid = (hi + lo)//2
+    if  item == array[mid]:
+        return mid
+    elif item < array[mid]:
+        return binary_search(array, item, hi=mid-1, lo=lo)
+    else:
+        return binary_search(array, item, hi=hi, lo=mid+1)
+
+
+
+
+def binary_search_iter(array, item):
+    '''
+    >>> binary_search_iter([2,3,5,6,8,10,15,23], 15)
+    6
+    >>> binary_search_iter([2,3,5,6,8,10,15,23], 4)
+    False
+    >>> binary_search_iter([1,3,4,5,7,8 ,10,12,23], 10)
+    6
+    >>> binary_search_iter([1,3,4,5,7,8 ,10,12,23], 22)
+    False
+    '''
+    lo, hi = 0, len(array)
+
+    while lo < hi:
+        mid = (hi+lo)//2
+        if array[mid] == item:
+            return mid
+        elif array[mid] > item:
+            hi = mid
+        else:
+            lo=mid+1
+    return False
+
+
+
+
+
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/searching_and_sorting/searching/binary_search_matrix.py b/src/searching_and_sorting/searching/binary_search_matrix.py
new file mode 100644
index 0000000..98f3d96
--- /dev/null
+++ b/src/searching_and_sorting/searching/binary_search_matrix.py
@@ -0,0 +1,92 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def binary_search_matrix_rec(m, key, lo=0, hi=None):
+    '''
+    >>> m = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
+    >>> binary_search_matrix_rec(m, 6)
+    (1, 2)
+    >>> binary_search_matrix_rec(m, 12)
+    '''
+    if not m:
+        return None
+
+    rows = len(m)
+    cols = len(m[0])
+    hi = hi or rows*cols
+
+    if hi > lo:
+
+        mid = (hi + lo)//2
+        row = mid//cols
+        col = mid%cols
+        item = m[row][col]
+
+        if key == item:
+            return row, col
+        elif key < item:
+            return binary_search_matrix_rec(m, key, lo, mid-1)
+        else:
+            return binary_search_matrix_rec(m, key, mid+1, hi)
+
+    return None
+
+
+
+def binary_search_matrix_iter(m, key):
+    '''
+
+    '''
+
+    if not m:
+        return None
+    rows = len(m)
+    cols = len(m[0])
+    lo, hi = 0, rows*cols
+
+    while lo < hi:
+        mid = (hi + lo)//2
+        row = mid//rows
+        col = mid%rows
+        item = m[row][col]
+        if key == item:
+            return (row, col)
+        elif key < item:
+            hi = mid
+        else:
+            lo = mid +1
+
+    return None
+
+
+def searching_matrix(m, key):
+    '''
+    >>> m = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
+    >>> searching_matrix(m, 6)
+    (1, 2)
+    >>> searching_matrix(m, 12)
+    '''
+
+    if not m:
+        return None
+    rows = len(m)
+    cols = len(m[0])
+    i, j = 0, cols -1
+
+    while i < rows and j > 0:
+        item = m[i][j]
+        if key == item:
+            return (i, j)
+        elif key < item:
+            j -= 1
+        else:
+            i += 1
+
+    return None
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
diff --git a/src/further_examples/searching/find_item_rotated_sorted_array.py b/src/searching_and_sorting/searching/find_item_rotated_sorted_array.py
similarity index 50%
rename from src/further_examples/searching/find_item_rotated_sorted_array.py
rename to src/searching_and_sorting/searching/find_item_rotated_sorted_array.py
index e8a24fb..2c5eadd 100644
--- a/src/further_examples/searching/find_item_rotated_sorted_array.py
+++ b/src/searching_and_sorting/searching/find_item_rotated_sorted_array.py
@@ -1,44 +1,37 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
-
-''' Given a sorted array that was rotated, find an item with binary search:
-    >>> l1 = [3, 4, 5, 6, 7, 1, 2]
-    >>> find_element_rot_array(l1, 7)
-    4
-    >>> find_element_rot_array(l1, 3)
-    0
-    >>> find_element_rot_array(l1, 4)
-    1
-    >>> find_element_rot_array(l1, 5)
-    2
-    >>> find_element_rot_array(l1, 6)
-    3
-    >>> find_element_rot_array(l1, 1)
-    5
-    >>> find_element_rot_array(l1, 2)
-    6
-    >>> find_element_rot_array(l1, 8)   
-    
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+
+'''
+Given a sorted array that was rotated, find an item with binary search:
 '''
 
 def find_element_rot_array(seq, key, lo=0, hi=None):
+
     hi = hi or len(seq)
-    if hi <= lo: return None # base case: <= for odd and even numbers!
-    mid = (hi + lo) // 2    
-    if key == seq[mid]: return mid
-    
+    if hi <= lo:
+        return None # base case: <= for odd and even numbers!
+
+    mid = (hi + lo) // 2
+
+    if key == seq[mid]:
+        return mid
+
     # if left is ordered --> we work here
     if seq[lo] <= seq[mid]:
+
         # now, is the key there?
         if key < seq[mid] and key >= seq[lo]:
             return find_element_rot_array(seq, key, lo, mid)
         else:
         # all the other cases
             return find_element_rot_array(seq, key, mid+1, hi)
-    
+
     # right is ordered --> we work here
     else:
+
         # now, is the key there?
         if key > seq[mid] and key <= seq[hi-1]: # stupid hi-1!!!
             return find_element_rot_array(seq, key, mid+1, hi)
@@ -46,11 +39,13 @@ def find_element_rot_array(seq, key, lo=0, hi=None):
         # all the other cases
             return find_element_rot_array(seq, key, lo, mid)
 
-    
-    
-    
+
+def test_find_element_rot_array():
+    l1 = [3, 4, 5, 6, 7, 1, 2]
+    assert(find_element_rot_array(l1, 7) == 4 )
+    print("Tests passed!")
+
 
 if __name__ == '__main__':
-    import doctest
-    doctest.testmod()
+    test_find_element_rot_array()
 
diff --git a/src/examples_in_my_book/searching/find_max_unimodal_array.py b/src/searching_and_sorting/searching/find_max_unimodal_array.py
similarity index 76%
rename from src/examples_in_my_book/searching/find_max_unimodal_array.py
rename to src/searching_and_sorting/searching/find_max_unimodal_array.py
index 04c07c5..1a57dd5 100644
--- a/src/examples_in_my_book/searching/find_max_unimodal_array.py
+++ b/src/searching_and_sorting/searching/find_max_unimodal_array.py
@@ -1,13 +1,15 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
+__author__ = "bt3"
 
 def find_max_unimodal_array(A):
-    if len(A) <= 2 : return None
+    if len(A) <= 2 :
+        return None
     left = 0
     right = len(A)-1
+
     while right > left +1:
+
         mid = (left + right)//2
         if A[mid] > A[mid-1] and A[mid] > A[mid+1]:
             return A[mid]
@@ -15,11 +17,12 @@ def find_max_unimodal_array(A):
             left = mid
         else:
             right = mid
+
     return None
 
 
 def test_find_max_unimodal_array():
-    seq = [1, 2, 5, 6, 7, 10, 12, 9, 8, 7, 6] 
+    seq = [1, 2, 5, 6, 7, 10, 12, 9, 8, 7, 6]
     assert(find_max_unimodal_array(seq) == 12)
     print('Tests passed!')
 
@@ -28,5 +31,5 @@ def test_find_max_unimodal_array():
     test_find_max_unimodal_array()
 
 
-     
-  
+
+
diff --git a/src/examples_in_my_book/searching/find_sqrt_bin_search.py b/src/searching_and_sorting/searching/find_sqrt_bin_search.py
similarity index 81%
rename from src/examples_in_my_book/searching/find_sqrt_bin_search.py
rename to src/searching_and_sorting/searching/find_sqrt_bin_search.py
index 99fec1c..6bef19f 100644
--- a/src/examples_in_my_book/searching/find_sqrt_bin_search.py
+++ b/src/searching_and_sorting/searching/find_sqrt_bin_search.py
@@ -1,11 +1,11 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
+__author__ = "bt3"
+
+''' implement square root using binary search '''
 
 
 def find_sqrt_bin_search(n, error=0.001):
-    ''' implement square root using binary search '''
     lower = n < 1 and n or 1
     upper = n < 1 and 1 or n
     mid = lower + (upper - lower) / 2.0
diff --git a/src/searching_and_sorting/searching/find_str_array_with_empty_str.py b/src/searching_and_sorting/searching/find_str_array_with_empty_str.py
new file mode 100644
index 0000000..fa66428
--- /dev/null
+++ b/src/searching_and_sorting/searching/find_str_array_with_empty_str.py
@@ -0,0 +1,54 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' Given a sorted an array with empty strings,
+    we use binary search to find some string (since the list is sorted):
+    --> we deal with the empty strings with strip and then run to left
+    and right, or move mid to the closed non-empty str (remember that
+    the index must be conserved):
+'''
+
+
+def find_str_array_with_empty_str(seq, s1):
+    if not seq or not s1:
+        return None
+    hi = len(seq)
+    lo = 0
+
+    while hi > lo:
+        mid = (hi+lo)//2
+
+        if seq[mid] == '':
+            while True:
+                left = mid-1
+                right = mid+1
+                if left < lo or right > hi: return None
+                elif right < hi and seq[right]:
+                    mid = right
+                    break
+                elif left > lo and seq[left]:
+                    mid = left
+                    break
+                right += 1
+                left -= 1
+
+        if s1 == seq[mid] == s1:
+            return mid
+        elif s1 < seq[mid]:
+            hi = mid
+        else:
+            lo = mid + 1
+
+
+
+def test_find_str_array_with_empty_str():
+    seq = ['acre', 'ball', '', 'coach', '', 'cut', '']
+    key = seq[1]
+    assert(find_str_array_with_empty_str(seq, key) == 1)
+    print('Tests passed!')
+
+
+if __name__ == '__main__':
+    test_find_str_array_with_empty_str()
diff --git a/src/examples_in_my_book/searching/find_time_occurence_list.py b/src/searching_and_sorting/searching/find_time_occurence_list.py
similarity index 70%
rename from src/examples_in_my_book/searching/find_time_occurence_list.py
rename to src/searching_and_sorting/searching/find_time_occurence_list.py
index 17c3137..af26ded 100644
--- a/src/examples_in_my_book/searching/find_time_occurence_list.py
+++ b/src/searching_and_sorting/searching/find_time_occurence_list.py
@@ -1,7 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
+__author__ = "bt3"
 
 def binary_serch_counting(lst1, k, lo=0, hi=None):
     if hi is None: hi = len(lst1)
@@ -15,26 +14,28 @@ def binary_serch_counting(lst1, k, lo=0, hi=None):
         else:
             return mid
     return -1
-    
-    
+
+
 def find_time_occurrence_list(seq, k):
-    """ find how many times a k element appears in a sorted list. One way of doing this is using 
-    collections.OrderedDict to no mess with the sorting, and add entries for every count. This 
-    should be O(n). It has a O(1) space complexity since the size of the dict is fixed.
-    Another way, since the array is sorted, it to use binary search, since this is only O(logn). 
+    """ find how many times a k element appears in a sorted list.
+    One way of doing this is using collections.OrderedDict to no
+    mess with the sorting, and add entries for every count. This
+    should be O(n). It has a O(1) space complexity since the size of
+    the dict is fixed. Another way, since the array is sorted, it to
+    use binary search, since this is only O(logn).
     """
     index_some_k = binary_serch_counting(seq, k)
     count = 1
     sizet = len(seq)
-   
+
     for i in range(index_some_k+1, sizet): # go up
         if seq[i] == k: count +=1
-        else: break        
-    
+        else: break
+
     for i in range(index_some_k-1, -1, -1): # go down
         if seq[i] == k: count +=1
-        else: break  
-                    
+        else: break
+
     return count
 
 
diff --git a/src/examples_in_my_book/searching/ordered_sequential_search.py b/src/searching_and_sorting/searching/ordered_sequential_search.py
similarity index 91%
rename from src/examples_in_my_book/searching/ordered_sequential_search.py
rename to src/searching_and_sorting/searching/ordered_sequential_search.py
index a252986..8f24d20 100644
--- a/src/examples_in_my_book/searching/ordered_sequential_search.py
+++ b/src/searching_and_sorting/searching/ordered_sequential_search.py
@@ -1,6 +1,7 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 
 def ordered_sequential_search(seq, n):
@@ -19,7 +20,7 @@ def test_ordered_sequential_search(module_name='this module'):
     n2 = 7
     assert(ordered_sequential_search(seq, n1) == True)
     assert(ordered_sequential_search(seq, n2) == False)
-        
+
     s = 'Tests in {name} have {con}!'
     print(s.format(name=module_name, con='passed'))
 
diff --git a/src/searching_and_sorting/searching/quick_select.py b/src/searching_and_sorting/searching/quick_select.py
new file mode 100644
index 0000000..ef5a629
--- /dev/null
+++ b/src/searching_and_sorting/searching/quick_select.py
@@ -0,0 +1,89 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+import random
+
+''' The simplest way...'''
+def quickSelect(seq, k):
+    # this part is the same as quick sort
+    len_seq = len(seq)
+    if len_seq < 2: return seq
+
+    # we could use a random choice here doing
+    #pivot = random.choice(seq)
+    ipivot = len_seq // 2
+    pivot = seq[ipivot]
+
+    # O(n)
+    smallerList = [x for i,x in enumerate(seq) if x <= pivot and  i != ipivot]
+    largerList = [x for i,x in enumerate(seq) if x > pivot and  i != ipivot]
+
+    # here starts the different part
+    m = len(smallerList)
+    if k == m:
+        return pivot
+    elif k < m:
+        return quickSelect(smallerList, k)
+    else:
+        return quickSelect(largerList, k-m-1)
+
+
+
+''' If you don't want to use pythons feature at all and
+    also select pivot randomly'''
+
+def swap(seq, x, y):
+    tmp = seq[x]
+    seq[x] = seq[y]
+    seq[y] = tmp
+
+
+def quickSelectHard(seq, k, left=None, right=None):
+    left = left or 0
+    right = right or len(seq) - 1
+    #ipivot = random.randint(left, right)
+    ipivot = len(seq)//2
+    pivot = seq[ipivot]
+
+    # Move pivot out of the sorting range
+    swap(seq, ipivot, right)
+    swapIndex, i = left, left
+    while i < right:
+        if seq[i] < pivot:
+            swap(seq, i, swapIndex)
+            swapIndex += 1
+        i += 1
+
+    # Move pivot to final position
+    swap(seq, right, swapIndex)
+
+    # Check if pivot matches, else recurse on the correct half
+    rank = len(seq) - swapIndex
+
+
+    if k == rank:
+        return seq[swapIndex]
+    elif k < rank:
+        return quickSelectHard(seq, k, swapIndex+1, right)
+    else:
+        return quickSelectHard(seq, k, left, swapIndex-1)
+
+
+
+
+if __name__ == '__main__':
+    # Checking the Answer
+    seq = [10, 60, 100, 50, 60, 75, 31, 50, 30, 20, 120, 170, 200]
+    #seq = [3, 7, 2, 1, 4, 6, 5, 10, 9, 11]
+
+    # we want the middle element
+    k = len(seq) // 2
+
+    # Note that this only work for odd arrays, since median in
+    # even arrays is the mean of the two middle elements
+    print(quickSelect(seq, k))
+    print(quickSelectHard(seq, k))
+    import numpy
+    print numpy.median(seq)
\ No newline at end of file
diff --git a/src/examples_in_my_book/searching/searching_in_a_matrix.py b/src/searching_and_sorting/searching/searching_in_a_matrix.py
similarity index 90%
rename from src/examples_in_my_book/searching/searching_in_a_matrix.py
rename to src/searching_and_sorting/searching/searching_in_a_matrix.py
index d3cdfbd..92a3bdc 100644
--- a/src/examples_in_my_book/searching/searching_in_a_matrix.py
+++ b/src/searching_and_sorting/searching/searching_in_a_matrix.py
@@ -1,16 +1,17 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 import numpy
 
 def searching_in_a_matrix(m1, value):
-    """ searches an element in a matrix where in every row, the values are increasing from left to  
+    """ searches an element in a matrix where in every row, the values are increasing from left to
     right, but the last number in a row is smaller than the first number in the next row.
     The naive brute force solution scan all numbers and cost O(nm).  However, since the numbers are
     already sorted, the matrix can be viewed as a 1D sorted array.  The binary search algorithm is
     suitable. The efficience is O(logmn)."""
-    
+
     rows = len(m1)
     cols = len(m1[0])
     lo = 0
@@ -24,7 +25,7 @@ def searching_in_a_matrix(m1, value):
         elif v > value: hi = mid
         else: lo = mid+1
     return False
-       
+
 
 
 def test_searching_in_a_matrix():
diff --git a/src/examples_in_my_book/searching/sequential_search.py b/src/searching_and_sorting/searching/sequential_search.py
similarity index 89%
rename from src/examples_in_my_book/searching/sequential_search.py
rename to src/searching_and_sorting/searching/sequential_search.py
index 9cc2947..6d389ce 100644
--- a/src/examples_in_my_book/searching/sequential_search.py
+++ b/src/searching_and_sorting/searching/sequential_search.py
@@ -1,6 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 
 def sequential_search(seq, n):
@@ -16,7 +16,7 @@ def test_sequential_search(module_name='this module'):
     n2 = 7
     assert(sequential_search(seq, n1) == True)
     assert(sequential_search(seq, n2) == False)
-        
+
     s = 'Tests in {name} have {con}!'
     print(s.format(name=module_name, con='passed'))
 
@@ -29,4 +29,4 @@ def test_sequential_search(module_name='this module'):
 Case	            Best Case	    Worst Case	    Average Case
 item is present	        1           	n	            n2
 item is not present	    n	            n           	n
-""""
+"""
\ No newline at end of file
diff --git a/src/further_examples/sorting/1.dat b/src/searching_and_sorting/sorting/1.dat
similarity index 100%
rename from src/further_examples/sorting/1.dat
rename to src/searching_and_sorting/sorting/1.dat
diff --git a/src/further_examples/sorting/2.dat b/src/searching_and_sorting/sorting/2.dat
similarity index 100%
rename from src/further_examples/sorting/2.dat
rename to src/searching_and_sorting/sorting/2.dat
diff --git a/src/further_examples/sorting/3.dat b/src/searching_and_sorting/sorting/3.dat
similarity index 100%
rename from src/further_examples/sorting/3.dat
rename to src/searching_and_sorting/sorting/3.dat
diff --git a/src/examples_in_my_book/general_problems/numbers/__init__.py b/src/searching_and_sorting/sorting/__init__.py
similarity index 100%
rename from src/examples_in_my_book/general_problems/numbers/__init__.py
rename to src/searching_and_sorting/sorting/__init__.py
diff --git a/src/examples_in_my_book/sorting/bubble_sort.py b/src/searching_and_sorting/sorting/bubble_sort.py
similarity index 65%
rename from src/examples_in_my_book/sorting/bubble_sort.py
rename to src/searching_and_sorting/sorting/bubble_sort.py
index c48fb7b..0d72e77 100644
--- a/src/examples_in_my_book/sorting/bubble_sort.py
+++ b/src/searching_and_sorting/sorting/bubble_sort.py
@@ -1,10 +1,13 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 
 def bubble_sort(seq):
-    ''' implement bubble sort, a O(n^2) not efficient algorithm'''
+    """
+    Implementation of bubble sort.
+    O(n2) and thus highly ineffective.
+    """
     size = len(seq) -1
     for num in range(size, 0, -1):
         for i in range(num):
@@ -13,15 +16,11 @@ def bubble_sort(seq):
                 seq[i] = seq[i+1]
                 seq[i+1] = temp
     return seq
-    
 
 
 def test_bubble_sort(module_name='this module'):
     seq = [4, 5, 2, 1, 6, 2, 7, 10, 13, 8]
     assert(bubble_sort(seq) == sorted(seq))
-        
-    s = 'Tests in {name} have {con}!'
-    print(s.format(name=module_name, con='passed'))
 
 
 if __name__ == '__main__':
diff --git a/src/examples_in_my_book/sorting/count_sort.py b/src/searching_and_sorting/sorting/count_sort.py
similarity index 83%
rename from src/examples_in_my_book/sorting/count_sort.py
rename to src/searching_and_sorting/sorting/count_sort.py
index 8288237..8bdfc23 100644
--- a/src/examples_in_my_book/sorting/count_sort.py
+++ b/src/searching_and_sorting/sorting/count_sort.py
@@ -1,6 +1,7 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 
 from collections import defaultdict
@@ -13,12 +14,11 @@ def count_sort_dict(a):
     for k in range(min(c), max(c) + 1):
         b.extend(c[k])
     return b
-	
+
 
 def test_count_sort():
     seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2, 5, 4, 1, 5, 3]
     assert(count_sort_dict(seq) == sorted(seq))
-    print('Tests passed!')
 
 
 if __name__ == '__main__':
diff --git a/src/examples_in_my_book/sorting/gnome_sort.py b/src/searching_and_sorting/sorting/gnome_sort.py
similarity index 73%
rename from src/examples_in_my_book/sorting/gnome_sort.py
rename to src/searching_and_sorting/sorting/gnome_sort.py
index a9f4b41..efad801 100644
--- a/src/examples_in_my_book/sorting/gnome_sort.py
+++ b/src/searching_and_sorting/sorting/gnome_sort.py
@@ -1,11 +1,8 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
+__author__ = "bt3"
 
-from do_benchmark import benchmark
 
-@benchmark
 def gnome_sort(seq):
     ''' sort a sequence using the gnome sort alg '''
     i = 0
@@ -21,7 +18,6 @@ def gnome_sort(seq):
 def test_gnome_sort():
     seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2, 5, 4, 1, 5, 3]
     assert(gnome_sort(seq) == sorted(seq))
-    print('Tests passed!')
 
 
 if __name__ == '__main__':
@@ -29,7 +25,7 @@ def test_gnome_sort():
 
 
 
-    
-    
-    
-    
+
+
+
+
diff --git a/src/examples_in_my_book/sorting/heap.py b/src/searching_and_sorting/sorting/heap.py
similarity index 91%
rename from src/examples_in_my_book/sorting/heap.py
rename to src/searching_and_sorting/sorting/heap.py
index cf1d890..b22326c 100644
--- a/src/examples_in_my_book/sorting/heap.py
+++ b/src/searching_and_sorting/sorting/heap.py
@@ -1,6 +1,7 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 class Heap(object):
     def __init__(self, data):
@@ -19,13 +20,13 @@ def left_child(self, i):
 
     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) 
+        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 != largest:
diff --git a/src/searching_and_sorting/sorting/heap_sort.py b/src/searching_and_sorting/sorting/heap_sort.py
new file mode 100644
index 0000000..bcbf639
--- /dev/null
+++ b/src/searching_and_sorting/sorting/heap_sort.py
@@ -0,0 +1,84 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' Heapsort using Pythons libraries'''
+
+import heapq
+
+def heap_sort1(seq):
+    ''' heap sort with Python's heapq '''
+    h = []
+    for value in seq:
+        heapq.heappush(h, value)
+    return [heapq.heappop(h) for i in range(len(h))]
+
+
+def test_heap_sort1():
+    seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
+    assert(heap_sort1(seq) == sorted(seq))
+    print('Tests passed!')
+
+
+
+''' Heapsort using my Heap class '''
+
+from heap import Heap
+
+def heap_sort2(seq):
+    heap = Heap(seq)
+
+    res = []
+    for i in range(len(seq)):
+        res.insert(0, heap.extract_max())
+
+    return res
+
+
+def test_heap_sort2():
+    seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
+    print heap_sort2(seq)
+    print('Tests passed!')
+
+
+''' A third way of doing heap sort '''
+
+def heap_sort3(seq):
+    for start in range((len(seq)-2)//2, -1, -1):
+        siftdown(seq, start, len(seq)-1)
+    for end in range(len(seq)-1, 0, -1):
+        seq[end], seq[0] = seq[0], seq[end]
+        siftdown(seq, 0, end - 1)
+    return seq
+
+def siftdown(seq, start, end):
+    root = start
+    while True:
+        child = root * 2 + 1
+        if child > end: break
+        if child + 1 <= end and seq[child] < seq[child + 1]:
+            child += 1
+        if seq[root] < seq[child]:
+            seq[root], seq[child] = seq[child], seq[root]
+            root = child
+        else:
+            break
+
+
+
+def test_heap_sort3():
+    seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
+    assert(heap_sort3(seq) == sorted(seq))
+    print('Tests passed!')
+
+
+
+
+
+
+
+if __name__ == '__main__':
+    test_heap_sort1()
+    test_heap_sort2()
+    test_heap_sort3()
diff --git a/src/examples_in_my_book/sorting/insertion_sort.py b/src/searching_and_sorting/sorting/insertion_sort.py
similarity index 87%
rename from src/examples_in_my_book/sorting/insertion_sort.py
rename to src/searching_and_sorting/sorting/insertion_sort.py
index 3dd522e..922e3a6 100644
--- a/src/examples_in_my_book/sorting/insertion_sort.py
+++ b/src/searching_and_sorting/sorting/insertion_sort.py
@@ -1,6 +1,7 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
 
 
 
@@ -30,7 +31,6 @@ def test_insertion_sort():
     seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2, 5, 4, 1, 5, 3]
     assert(insertion_sort(seq) == sorted(seq))
     assert(insertion_sort_rec(seq) == sorted(seq))
-    print('Tests passed!')
 
 
 if __name__ == '__main__':
@@ -38,7 +38,7 @@ def test_insertion_sort():
 
 
 
-    
-    
-    
-    
+
+
+
+
diff --git a/src/searching_and_sorting/sorting/merge_and_sort_two_arrays.py b/src/searching_and_sorting/sorting/merge_and_sort_two_arrays.py
new file mode 100644
index 0000000..4af24a8
--- /dev/null
+++ b/src/searching_and_sorting/sorting/merge_and_sort_two_arrays.py
@@ -0,0 +1,46 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+'''
+You have two arrays with N integers in them. Merge those arrays using a
+recursive algorithm so that the integers in the final array are sorted.
+'''
+
+def merge_arrays(a1, a2):
+    '''
+    >>> merge_arrays([5, 4, 3], [6, 2, 9])
+    [2, 3, 4, 5, 6, 9]
+    >>> merge_arrays([2, 6], [6, 2])
+    [2, 2, 6, 6]
+    >>> merge_arrays([], [])
+    []
+    '''
+    # if they are not sorted yet
+    a1.sort()
+    a2.sort()
+
+    merge = []
+    p1, p2 = 0, 0
+
+    while p1 < len(a1) and p2 < len(a2):
+        if a1[p1] <= a2[p2]:
+            merge.append(a1[p1])
+            p1 += 1
+        else:
+            merge.append(a2[p2])
+            p2 +=1
+
+    if a1[p1:]:
+        merge.extend(a1[p1:])
+
+    if a2[p2:]:
+        merge.extend(a2[p2:])
+
+    return merge
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/searching_and_sorting/sorting/merge_sort.py b/src/searching_and_sorting/sorting/merge_sort.py
new file mode 100644
index 0000000..fd5ac54
--- /dev/null
+++ b/src/searching_and_sorting/sorting/merge_sort.py
@@ -0,0 +1,54 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def merge_sort(array):
+    '''
+    >>> merge_sort([3 ,5, 1, 2, 10, 6])
+    [1, 2, 3, 5, 6, 10]
+    '''
+    if len(array) < 2:
+        return array
+
+    mid = len(array)//2
+    left = merge_sort(array[:mid])
+    right = merge_sort(array[mid:])
+
+    res = []
+    i, j = 0, 0
+    while i < len(left) and j < len(right):
+        if left[i] <= right[j]:
+            res.append(left[i])
+            i += 1
+        else:
+            res.append(right[j])
+            j += 1
+
+    if left[i:]:
+       res.extend(left[i:])
+    if right[j:]:
+        res.extend(right[j:])
+    return res
+
+
+
+''' Merge sort for files '''
+def merge_files(list_files):
+    result = []
+    final = []
+    for filename in list_files:
+        aux = []
+        with open(filename, 'r') as file:
+            for line in file:
+                aux.append(int(line))
+        result.append(aux)
+    final.extend(result.pop())
+    for l in result:
+        final = merge(l, final)
+    return final
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/searching_and_sorting/sorting/quick_sort.py b/src/searching_and_sorting/sorting/quick_sort.py
new file mode 100644
index 0000000..5596d1a
--- /dev/null
+++ b/src/searching_and_sorting/sorting/quick_sort.py
@@ -0,0 +1,46 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+def qs(array):
+    '''
+    >>> qs([4,1,6,2,7,9,3])
+    [1, 2, 3, 4, 6, 7, 9]
+    '''
+    if len(array) < 2:
+        return array
+
+    piv = len(array)//2
+    piv_element = array[piv]
+    new_array = array[:piv] + array[piv+1:]
+
+    left  = [a for a in new_array if a <= piv_element]
+    right = [a for a in new_array if a > piv_element]
+
+    return qs(left) + [array[piv]] + qs(right)
+
+
+
+# we can also divide them into two functions
+def partition(seq):
+    pi,seq = seq[0],seq[1:]
+    lo = [x for x in seq if x <= pi]
+    hi = [x for x in seq if x > pi]
+    return lo, pi, hi
+
+def quick_sort_divided(seq):
+    '''
+    >>> quick_sort_divided([4,1,6,2,7,9,3])
+    [1, 2, 3, 4, 6, 7, 9]
+    '''
+    if len(seq) < 2:
+        return seq
+    lo, pi, hi = partition(seq)
+    return quick_sort_divided(lo) + [pi] + quick_sort_divided(hi)
+
+
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
\ No newline at end of file
diff --git a/src/examples_in_my_book/sorting/selection_sort.py b/src/searching_and_sorting/sorting/selection_sort.py
similarity index 80%
rename from src/examples_in_my_book/sorting/selection_sort.py
rename to src/searching_and_sorting/sorting/selection_sort.py
index 7c6ddac..65fc169 100644
--- a/src/examples_in_my_book/sorting/selection_sort.py
+++ b/src/searching_and_sorting/sorting/selection_sort.py
@@ -1,6 +1,6 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
+
+__author__ = "bt3"
 
 
 def selection_sort(seq):
@@ -17,7 +17,6 @@ def selection_sort(seq):
 def test_selection_sort():
     seq = [3, 5, 2, 6, 8, 1, 0, 3, 5, 6, 2]
     assert(selection_sort(seq) == sorted(seq))
-    print('Tests passed!')
 
 
 if __name__ == '__main__':
@@ -25,7 +24,7 @@ def test_selection_sort():
 
 
 
-    
-    
-    
-    
+
+
+
+
diff --git a/src/searching_and_sorting/sorting/sort_anagrams_together.py b/src/searching_and_sorting/sorting/sort_anagrams_together.py
new file mode 100644
index 0000000..1a20417
--- /dev/null
+++ b/src/searching_and_sorting/sorting/sort_anagrams_together.py
@@ -0,0 +1,34 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+''' A method to sort an array so that all the anagrams are together.
+    Since we only want the anagrams to be grouped, we can use a
+    dictionary for this task. This algorithm is O(n).
+'''
+
+from collections import defaultdict
+
+def sort_anagrams_together(l1):
+    '''
+    >>> l1 = ['hat', 'ball', 'tha', 'cut', 'labl', 'hta', 'cool', 'cuy', 'uct']
+    >>> sort_anagrams_together(l1)
+    ['cuy', 'cut', 'uct', 'cool', 'ball', 'labl', 'hat', 'tha', 'hta']
+    '''
+    result = []
+
+    dict_aux = defaultdict(list)
+    for word in l1:
+        key = ''.join(sorted(word))
+        dict_aux[key].append(word)
+
+    for key in dict_aux:
+        result.extend(dict_aux[key])
+
+    return result
+
+if __name__ == '__main__':
+    import doctest
+    doctest.testmod()
+
diff --git a/src/examples_in_my_book/general_problems/oop/__init__.py b/src/trees/__init__.py
old mode 100644
new mode 100755
similarity index 100%
rename from src/examples_in_my_book/general_problems/oop/__init__.py
rename to src/trees/__init__.py
diff --git a/src/trees/binary_search_tree.py b/src/trees/binary_search_tree.py
new file mode 100755
index 0000000..9f82203
--- /dev/null
+++ b/src/trees/binary_search_tree.py
@@ -0,0 +1,120 @@
+#!/usr/bin/python
+
+__author__ = "bt3"
+
+
+class Node(object):
+
+    def __init__(self, item=None,):
+
+        self.item = item
+        self.left = None
+        self.right = None
+
+    def __repr__(self):
+        return '{}'.format(self.item)
+
+
+    def _add(self, value):
+        new_node = Node(value)
+
+        if not self.item:
+            self.item = new_node
+
+        else:
+            if value > self.item:
+                self.right = self.right and self.right._add(value) or new_node
+            elif value < self.item:
+                self.left = self.left and self.left._add(value) or new_node
+            else:
+                print("BSTs do not support repeated items.")
+
+        return self # this is necessary!!!
+
+
+    def _search(self, value):
+        if self.item == value:
+            return True # or self
+
+        elif self.left and value < self.item:
+                return self.left._search(value)
+
+        elif self.right and value > self.item:
+                return self.right._search(value)
+
+        else:
+            return False
+
+
+    def _isLeaf(self):
+        return not self.right and not self.left
+
+
+    def _printPreorder(self):
+        print self.item
+
+        if self.left:
+            self.left._printPreorder()
+
+        if self.right:
+            self.right._printPreorder()
+
+    # Another possibility: use an array (a little bit more expensive):
+    def _preorder_array(self):
+        nodes = []
+        if self.item:
+            nodes.append(self.item)
+        if self.left:
+            nodes.extend(self.left._preorder_array())
+        if self.right:
+            nodes.extend(self.right._preorder_array())
+        return nodes
+
+
+
+
+class BST(object):
+
+    def __init__(self):
+        self.root = None
+
+    def add(self, value):
+        if not self.root:
+            self.root = Node(value)
+        else:
+            self.root._add(value)
+
+    def printPreorder(self):
+        if self.root:
+            self.root._printPreorder()
+
+    def search(self, value):
+        if self.root:
+            return self.root._search(value)
+
+    def preorder_array(self):
+        if self.root:
+            return self.root._preorder_array()
+        else:
+            return 'Tree is empty.'
+
+
+if __name__ == '__main__':
+
+    bst = BST()
+    print "Adding nodes 1 to 10 in the tree..."
+    for i in range(1, 11):
+        bst.add(i)
+
+    print
+    print "Searching for nodes 16 and 6"
+    print bst.search(16)
+    print bst.search(6)
+
+    print
+    print "Printing preorder..."
+    bst.printPreorder()
+
+
+
+
diff --git a/src/trees/binary_tree.py b/src/trees/binary_tree.py
new file mode 100755
index 0000000..796f1cc
--- /dev/null
+++ b/src/trees/binary_tree.py
@@ -0,0 +1,96 @@
+#!/usr/bin/python
+
+__author__ = "bt3"
+
+
+class Node(object):
+
+    def __init__(self, item=None,):
+        self.item = item
+        self.left = None
+        self.right = None
+
+    def __repr__(self):
+        return '{}'.format(self.item)
+
+
+    def _add(self, value):
+        new_node = Node(value)
+
+        if not self.item:
+            self.item = new_node
+        elif not self.left:
+            self.left = new_node
+        elif not self.right:
+            self.right = new_node
+        else:
+            self.left = self.left._add(value)
+
+        return self
+
+
+    def _search(self, value):
+        if self.item == value:
+            return True # or self
+
+        found = False # or None, thats diff from BST
+        if self.left:
+            found = self.left._search(value)
+
+        if self.right:
+            found =  found or self.right._search(value)
+
+        return found
+
+
+    def _isLeaf(self):
+        return not self.right and not self.left
+
+
+    def _preorder(self):
+        print self.item
+        if self.left:
+            self.left._preorder()
+        if self.right:
+            self.right._preorder()
+
+
+
+class BT(object):
+
+    def __init__(self):
+        self.root = None
+
+
+    def add(self, value):
+        if not self.root:
+            self.root = Node(value)
+        else:
+            self.root._add(value)
+
+
+    def search(self, value):
+        if self.root:
+            return self.root._search(value)
+
+
+    def preorder(self):
+        if self.root:
+            return self.root._preorder()
+
+
+if __name__ == '__main__':
+
+    bt = BT()
+    print "Adding nodes 1 to 10 in the tree..."
+    for i in range(1, 11):
+        bt.add(i)
+
+    print
+    print "Searching for nodes 16 and 6"
+    print bt.search(16)
+    print bt.search(6)
+
+    print
+    print "Printing preorder..."
+    bt.preorder()
diff --git a/src/trees/binary_tree_generators.py b/src/trees/binary_tree_generators.py
new file mode 100644
index 0000000..afafa49
--- /dev/null
+++ b/src/trees/binary_tree_generators.py
@@ -0,0 +1,170 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+class Node(object):
+    def __init__(self, value):
+        self.value = value
+        self.right = None
+        self.left = None
+
+    def add(self, value):
+        new_node = Node(value)
+        if not self.value:
+            self.value = new_node
+        elif not self.left:
+            self.left = new_node
+        elif not self. right:
+            self.right = new_node
+        else:
+            self.left = self.left.add(value)
+        return self # without this, it doesn't add!
+
+    def search(self, item):
+        if self.value == item:
+            return True
+        found = False
+        if (self.left and self.left.search(item)) or \
+                (self.right and self.right.search(item)):
+            found = True
+        return found
+
+    def preorder(self):
+        yield self.value
+        if self.left:
+            for node in self.left.preorder():
+                yield node
+        if self.right:
+            for node in self.right.preorder():
+                yield node
+
+    def postorder(self):
+        yield self.value
+        if self.left:
+            for node in self.left.postorder():
+                yield node
+        if self.right:
+            for node in self.right.postorder():
+                yield node
+
+    def inorder(self):
+        yield self.value
+        if self.left:
+            for node in self.left.inorder():
+                yield node
+        if self.right:
+            for node in self.right.inorder():
+                yield node
+
+    # this is the most basic way to write this function
+    def preorder_simple(self):
+        print self.value
+        if self.left:
+            self.left.preorder_simple()
+        if self.right:
+            self.right.preorder_simple()
+
+
+    # Another possibility: use an array (a little bit more expensive):
+    def preorder_array(self):
+        nodes = []
+        if self.value:
+            nodes.append(self.value)
+        if self.left:
+            nodes.extend(self.left.preorder_array())
+        if self.right:
+            nodes.extend(self.right.preorder_array())
+        return nodes
+
+
+
+class BT(object):
+    def __init__(self):
+        self.root = None
+
+    def add(self, value):
+        if not self.root:
+            self.root = Node(value)
+        else:
+            self.root.add(value)
+
+    def search(self, item):
+        if self.root:
+            return self.root.search(item)
+        else:
+            return 'Tree is empty.'
+
+    def preorder(self):
+        if self.root:
+            return self.root.preorder()
+        else:
+            return 'Tree is empty.'
+
+    def inorder(self):
+        if self.root:
+            return self.root.inorder()
+        else:
+            return 'Tree is empty.'
+
+    def postorder(self):
+        if self.root:
+            return self.root.postorder()
+        else:
+            return 'Tree is empty.'
+
+    def preorder_array(self):
+        if self.root:
+            return self.root.preorder_array()
+        else:
+            return 'Tree is empty.'
+
+    def preorder_simple(self):
+        if self.root:
+            return self.root.preorder_simple()
+        else:
+            return 'Tree is empty.'
+
+
+if __name__ == '__main__':
+    tree = BT()
+
+    for i in range(1, 11):
+        tree.add(i)
+
+    print 'Searching for node 4'
+    print tree.search(4)
+
+    print 'Searching for node 1'
+    print tree.search(1)
+
+    print 'Searching for node 12'
+    print tree.search(12)
+
+    print 'Pre-order generator...'
+    getree = tree.preorder()
+    for i in range(10):
+        print next(getree)
+    print
+    print 'Pre-order array...'
+
+    print tree.preorder_array()
+
+    print
+    print 'Pre-order simple...'
+
+    tree.preorder_simple()
+
+    print
+    print 'Inorder...'
+
+    getree = tree.inorder()
+    for i in range(10):
+        print next(getree)
+
+    print
+    print 'Postorder...'
+
+    getree = tree.postorder()
+    for i in range(10):
+        print next(getree)
diff --git a/src/examples_in_my_book/trees/simple_trees/bunchclass.py b/src/trees/bunchclass.py
old mode 100644
new mode 100755
similarity index 86%
rename from src/examples_in_my_book/trees/simple_trees/bunchclass.py
rename to src/trees/bunchclass.py
index 03b3104..6e0b440
--- a/src/examples_in_my_book/trees/simple_trees/bunchclass.py
+++ b/src/trees/bunchclass.py
@@ -1,13 +1,12 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
+__author__ = "bt3"
 
 class BunchClass(dict):
     def __init__(self, *args, **kwds):
         super(BunchClass, self).__init__(*args, **kwds)
         self.__dict__ = self
-		
+
 
 def main():
     ''' {'right': {'right': 'Xander', 'left': 'Willow'}, 'left': {'right': 'Angel', 'left': 'Buffy'}}'''
@@ -20,4 +19,4 @@ def main():
 
 
 
- 
+
diff --git a/src/trees/check_ancestor.py b/src/trees/check_ancestor.py
new file mode 100755
index 0000000..a318958
--- /dev/null
+++ b/src/trees/check_ancestor.py
@@ -0,0 +1,57 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+from binary_search_tree import BST, Node
+
+def find_ancestor(path, low_item, high_item):
+    while path:
+        current_item = path[0]
+
+        if current_item < low_item:
+            try:
+                path = path[2:]
+            except:
+                return current_item
+
+        elif current_item > high_item:
+            try:
+                path = path[1:]
+            except:
+                return current_item
+
+        elif low_item <= current_item <= high_item:
+            return current_item
+
+
+def find_ancestor2(tree, n1, n2):
+    if not tree:
+        return False
+
+    if n1 <= tree.item and n2 >= tree.item or (not tree.left and not tree.right) :
+        return tree.item
+
+    if tree.left and (n1 < tree.item and n2 < tree.item):
+        return find_ancestor(tree.left, n1, n2) or tree.item
+
+    if tree.right and (n1 > tree.item and n2 > tree.item):
+        return find_ancestor(tree.right, n1, n2) or tree.item
+
+
+
+if __name__ == '__main__':
+    bst = BST()
+    l = [10, 5, 6, 3, 8, 2, 1, 11, 9, 4]
+    for i in l:
+        bst.add(i)
+    nodes = bst.preorder_array()
+
+    print 'Original:    ', l
+    print 'Preorder:    ', nodes
+
+    print 'Method 1: '
+    print 'Ancestor for 3, 11:', find_ancestor(nodes, 3, 11)
+
+    print 'Method 2: '
+    print 'Ancestor for 3, 11: ', find_ancestor2(bst.root, 3, 11)
diff --git a/src/trees/check_if_balanced.py b/src/trees/check_if_balanced.py
new file mode 100755
index 0000000..3e6d5fb
--- /dev/null
+++ b/src/trees/check_if_balanced.py
@@ -0,0 +1,31 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+from binary_search_tree import BST, Node
+from binary_tree import BT, Node
+
+
+
+def isBalanced(node, left=0, right=0):
+    if not node:
+        return (left - right) < 2
+
+    return isBalanced(node.left, left+1, right) and \
+        isBalanced(node.right, left, right+1)
+
+
+
+
+if __name__ == '__main__':
+    bt = BST()
+    for i in range(1, 10):
+        bt.add(i)
+
+    assert(isBalanced(bt.root) == True)
+
+    bt = BT()
+    for i in range(1, 10):
+        bt.add(i)
+
+    assert(isBalanced(bt.root) == False)
diff --git a/src/trees/check_if_bst.py b/src/trees/check_if_bst.py
new file mode 100755
index 0000000..792013f
--- /dev/null
+++ b/src/trees/check_if_bst.py
@@ -0,0 +1,64 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+from binary_search_tree import BST, Node
+from binary_tree import BT, Node
+
+
+def isBST(node, min_node=float("-infinity"), maxVal=float("infinity")):
+    if not node:
+        return True
+
+    if not min_node <= node.item <= maxVal:
+        return False
+
+    return isBST(node.left, min_node, node.item) and \
+           isBST(node.right, node.item, maxVal)
+
+
+
+def isBST_other_method(node, max_node=None, min_node=None):
+
+    if not node:
+        return True
+
+    left, right =  True, True
+    min_node = min_node or float('inf')
+    max_node = max_node or -float('inf')
+
+    if node.left:
+        if node.left.item > node.item or node.left.item > max_node:
+            left = False
+        else:
+            max_node = node.item
+            left =  isBST(node.left, max_node, min_node)
+
+    if node.right:
+        if node.right.item < node.item or node.right.item < min_node:
+            rihjt =  False
+        else:
+            min_node = node.item
+            right =  isBST(node.right, max_node, min_node)
+
+    return left and right
+
+
+
+
+
+if __name__ == '__main__':
+    bt = BST()
+    for i in range(1, 10):
+        bt.add(i)
+
+    assert(isBST(bt.root) == True)
+
+    bt = BT()
+    for i in range(1, 10):
+        bt.add(i)
+
+    assert(isBST(bt.root) == False)
+
+
diff --git a/src/trees/check_largest_item.py b/src/trees/check_largest_item.py
new file mode 100755
index 0000000..3428d60
--- /dev/null
+++ b/src/trees/check_largest_item.py
@@ -0,0 +1,23 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+from binary_search_tree import BST, Node
+
+def largest(node):
+
+    if node.right:
+        return largest(node.right)
+    return node.item
+
+
+if __name__ == '__main__':
+
+
+    bst = BST()
+    l = [10, 5, 6, 3, 8, 2, 1, 11, 9, 4]
+    for i in l:
+        bst.add(i)
+
+    print(largest(bst.root))
diff --git a/src/examples_in_my_book/trees/simple_trees/tree.py b/src/trees/simple_tree.py
old mode 100644
new mode 100755
similarity index 70%
rename from src/examples_in_my_book/trees/simple_trees/tree.py
rename to src/trees/simple_tree.py
index e0646a7..90480e2
--- a/src/examples_in_my_book/trees/simple_trees/tree.py
+++ b/src/trees/simple_tree.py
@@ -1,13 +1,17 @@
-#!/usr/bin/python3
-# mari von steinkirch @2013
-# steinkirch at gmail
+#!/usr/bin/env python
 
+__author__ = "bt3"
+
+
+""" A class for a simple tree """
 
 class SimpleTree(object):
-    def __init__(self, value, children = None):
-        if children == None: children = []
+
+    def __init__(self, value=None, children = None):
+        self.value = value
         self.children = children
-        self.value = value       
+        if self.children == None:
+            self.children = []
 
     def __repr__(self, level=0):
         ret = "\t"*level+repr(self.value)+"\n"
@@ -16,6 +20,7 @@ def __repr__(self, level=0):
         return ret
 
 
+
 def main():
     """
     'a'
diff --git a/src/trees/transversal.py b/src/trees/transversal.py
new file mode 100755
index 0000000..d3e3bf2
--- /dev/null
+++ b/src/trees/transversal.py
@@ -0,0 +1,89 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+from collections import deque
+from binary_search_tree import BST, Node
+from binary_tree import BT, Node
+
+
+def BFT(tree):
+    current = tree.root
+    nodes = []
+    queue = deque()
+    queue.append(current)
+
+    while queue:
+        current = queue.popleft()
+        nodes.append(current.item)
+        if current.left:
+            queue.append(current.left)
+        if current.right:
+            queue.append(current.right)
+
+    return nodes
+
+
+def preorder(tree, nodes=None):
+    nodes = nodes or []
+    if tree:
+        nodes.append(tree.item)
+        if tree.left:
+            preorder(tree.left, nodes)
+        if tree.right:
+            preorder(tree.right, nodes)
+    return nodes
+
+
+def postorder(tree, nodes=None):
+    nodes = nodes or []
+    if tree:
+        if tree.left:
+            nodes = postorder(tree.left, nodes)
+        if tree.right:
+            nodes = postorder(tree.right, nodes)
+        nodes.append(tree.item)
+
+    return nodes
+
+
+def inorder(tree, nodes=None):
+    nodes = nodes or []
+    if tree:
+        if tree.left:
+            nodes = inorder(tree.left, nodes)
+        nodes.append(tree.item)
+        if tree.right:
+            nodes = inorder(tree.right, nodes)
+    return nodes
+
+
+if __name__ == '__main__':
+
+
+    # bt
+    bt = BT()
+    l = [10, 5, 6, 3, 8, 2, 1, 11, 9, 4]
+    for i in l:
+        bt.add(i)
+    print 'BT...'
+    print 'Original:    ', l
+    print 'Preorder:    ', preorder(bt.root)
+    print 'Postorder:   ', postorder(bt.root)
+    print 'Inorder:     ', inorder(bt.root)
+    print 'Breath:      ', BFT(bt)
+
+    # bst
+    bst = BST()
+    l = [10, 5, 6, 3, 8, 2, 1, 11, 9, 4]
+    for i in l:
+        bst.add(i)
+
+    print
+    print 'BST ...'
+    print 'Original:    ', l
+    print 'Preorder:    ', preorder(bst.root)
+    print 'Postorder:   ', postorder(bst.root)
+    print 'Inorder:     ', inorder(bst.root)
+    print 'Breath:      ', BFT(bst)
diff --git a/src/trees/trie.py b/src/trees/trie.py
new file mode 100755
index 0000000..a73c531
--- /dev/null
+++ b/src/trees/trie.py
@@ -0,0 +1,65 @@
+#!/usr/bin/env python
+
+__author__ = "bt3"
+
+
+'''
+Implement a trie. (Write the API and code for inserting into a trie).
+'''
+
+def make_trie(*args):
+    trie = {}
+
+    for word in args:
+        temp_trie = trie
+        for letter in word:
+            temp_trie = temp_trie.setdefault(letter, {})
+        temp_trie = temp_trie.setdefault('_end_', '_end_')
+
+    return trie
+
+
+def in_trie(trie, word):
+    temp_trie = trie
+    for letter in word:
+        if letter not in temp_trie:
+            return False
+        temp_trie = temp_trie[letter]
+    return True
+
+
+def remove_from_trie(trie, word, depth):
+    if word and word[depth] not in trie:
+        return False
+
+    if len(word) == depth + 1:
+        del trie[word[depth]]
+        if not trie:
+           return True
+        return False
+    else:
+        temp_trie = trie
+
+        if remove_from_trie(temp_trie[word[depth]], word, depth + 1):
+            if temp_trie:
+                del temp_trie[word[depth]]
+            return not temp_trie
+    return False
+
+
+if __name__ == '__main__':
+    trie = make_trie('hello', 'abc', 'baz', 'bar', 'barz')
+    print 'This is the trie:'
+    print trie
+
+    assert(in_trie(trie, 'hello') == True)
+    assert(in_trie(trie, 'bar') == True)
+    assert(in_trie(trie, 'bab') == False)
+    assert(in_trie(trie, 'zzz') == False)
+
+    remove_from_trie(trie, 'abc', 0)
+    assert(in_trie(trie, 'abc') == False)
+
+
+
+