diff --git a/.idea/.gitignore b/.idea/.gitignore
new file mode 100644
index 0000000..e7e9d11
--- /dev/null
+++ b/.idea/.gitignore
@@ -0,0 +1,2 @@
+# Default ignored files
+/workspace.xml
diff --git a/.idea/algorithm.iml b/.idea/algorithm.iml
new file mode 100644
index 0000000..8b8c395
--- /dev/null
+++ b/.idea/algorithm.iml
@@ -0,0 +1,12 @@
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/.idea/codeStyles/codeStyleConfig.xml b/.idea/codeStyles/codeStyleConfig.xml
new file mode 100644
index 0000000..a55e7a1
--- /dev/null
+++ b/.idea/codeStyles/codeStyleConfig.xml
@@ -0,0 +1,5 @@
+
+
+
+
+
\ No newline at end of file
diff --git a/.idea/dbnavigator.xml b/.idea/dbnavigator.xml
new file mode 100644
index 0000000..51e620f
--- /dev/null
+++ b/.idea/dbnavigator.xml
@@ -0,0 +1,449 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/.idea/encodings.xml b/.idea/encodings.xml
new file mode 100644
index 0000000..15a15b2
--- /dev/null
+++ b/.idea/encodings.xml
@@ -0,0 +1,4 @@
+
+
+
+
\ No newline at end of file
diff --git a/.idea/inspectionProfiles/profiles_settings.xml b/.idea/inspectionProfiles/profiles_settings.xml
new file mode 100644
index 0000000..105ce2d
--- /dev/null
+++ b/.idea/inspectionProfiles/profiles_settings.xml
@@ -0,0 +1,6 @@
+
+
+
+
+
+
\ No newline at end of file
diff --git a/.idea/misc.xml b/.idea/misc.xml
new file mode 100644
index 0000000..d56657a
--- /dev/null
+++ b/.idea/misc.xml
@@ -0,0 +1,4 @@
+
+
+
+
\ No newline at end of file
diff --git a/.idea/vcs.xml b/.idea/vcs.xml
new file mode 100644
index 0000000..94a25f7
--- /dev/null
+++ b/.idea/vcs.xml
@@ -0,0 +1,6 @@
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Bellman_Ford_matrix.py b/Bellman_Ford_matrix.py
index 76739f2..21d547d 100644
--- a/Bellman_Ford_matrix.py
+++ b/Bellman_Ford_matrix.py
@@ -1,4 +1,3 @@
-import numpy as np
def Bellman_Ford_matrix(W, s):
n = W.shape[0]
@@ -11,38 +10,41 @@ def Bellman_Ford_matrix(W, s):
if d[j - 1] > d[i - 1] + W[i - 1, j - 1]:
d[j - 1] = d[i - 1] + W[i - 1, j - 1]
p[j - 1] = i
- print d
- print p
+ print(d)
+ print(p)
return d, p
+
def extend_shortest_paths(L, W):
n = W.shape[0]
LW = [float("Inf")] * n
- for j in range(0, n):
- for k in range(0, n):
+ for j in range(n):
+ for k in range(n):
LW[j] = min(LW[j], L[k] + W[k, j])
return LW
+
def slow_all_pairs_shortest_paths(W, s):
n = W.shape[0]
L = [0] * n
- for i in range(0, n):
+ for i in range(n):
if i + 1 == s:
L[i] = 0
else:
L[i] = float("Inf")
- print L
+ print(L)
for m in range(1, n):
L = extend_shortest_paths(L, W)
- print L
+ print(L)
return L
+
def extend_shortest_paths_with_predecessor_subgraph(s, L, P, W):
n = W.shape[0]
LW = [float("Inf")] * n
- PP = [None] * n
- for j in range(0, n):
- for k in range(0, n):
+ PP = [None] * n
+ for j in range(n):
+ for k in range(n):
if LW[j] > L[k] + W[k, j]:
LW[j] = L[k] + W[k, j]
PP[j] = k + 1
@@ -50,6 +52,7 @@ def extend_shortest_paths_with_predecessor_subgraph(s, L, P, W):
PP[j] = P[j]
return LW, PP
+
def slow_all_pairs_shortest_paths_with_predecessor_subgraph(W, s):
n = W.shape[0]
L = [float("Inf")] * n
@@ -57,10 +60,11 @@ def slow_all_pairs_shortest_paths_with_predecessor_subgraph(W, s):
P = [None] * n
for m in range(1, n):
L, P = extend_shortest_paths_with_predecessor_subgraph(s, L, P, W)
- print L
- print P
+ print(L)
+ print(P)
return L, P
+
def faster_all_pairs_shortest_paths(W):
n = W.shape[0]
L = W
@@ -68,8 +72,6 @@ def faster_all_pairs_shortest_paths(W):
while m < n - 1:
L = extend_shortest_paths(L, L)
m = 2 * m
- print m
- print L
+ print(m)
+ print(L)
return Ld, p
-
-
diff --git a/Bellman_Ford_matrix_test.py b/Bellman_Ford_matrix_test.py
deleted file mode 100644
index 3e4dbdd..0000000
--- a/Bellman_Ford_matrix_test.py
+++ /dev/null
@@ -1,14 +0,0 @@
-from Bellman_Ford_matrix import Bellman_Ford_matrix, slow_all_pairs_shortest_paths
-import unittest
-import numpy
-class TestBellmanFordMatrix(unittest.TestCase):
- def test_Bellman_Ford_matrix(self):
- W = numpy.array([[ float("Inf"), 6., 7., float("Inf"), float("Inf")], [ float("Inf"), float("Inf"), 8., 5., -4.], [ float("Inf"), float("Inf"), float("Inf"), -3., 9.], [ float("Inf"), -2., float("Inf"), float("Inf"), float("Inf")], [ 2., float("Inf"), float("Inf"), 7., float("Inf")]])
- d, p = Bellman_Ford_matrix(W, 1)
- self.assertEquals(d, [0, 2.0, 7.0, 4.0, -2.0])
- self.assertEquals(p, [None, 4, 1, 3, 2])
- def test_slow_all_pairs_shortest_paths(self):
- W = numpy.array([[ 0, 6., 7., float("Inf"), float("Inf")], [ float("Inf"), 0, 8., 5., -4.], [ float("Inf"), float("Inf"), 0, -3., 9.], [ float("Inf"), -2., float("Inf"), 0, float("Inf")], [ 2., float("Inf"), float("Inf"), 7., 0]])
- L = slow_all_pairs_shortest_paths(W, 1)
- print L
- self.assertEquals(L, [0, 2.0, 7.0, 4.0, -2.0])
diff --git a/BinSearch.c b/BinSearch.c
deleted file mode 100644
index e096370..0000000
--- a/BinSearch.c
+++ /dev/null
@@ -1,34 +0,0 @@
-//BinSearch(A, first, end, x)
-// while length >= 0
-// inter = (first + end) / 2
-// if x == A[inter]
-// return inter + 1
-// else if x < A[inter]
-// end = inter - 1
-// else
-// first = inter + 1
-// length = end - first
-// return -1
-
-int BinSearch(int A[], int first, int end, int x) {
- int length = end - first;
- int inter;
-
- while (length >= 0) {
- inter = (first + end) / 2;
- if (x == A[inter] )
- return inter + 1;
- else if (x < A[inter])
- end = inter - 1;
- else
- first = inter + 1;
- length = end - first;
- }
- return -1;
-}
-
-void main() {
- int A[10] = {0,1,2,3,4,5,6,7,8,9};
-
- printf("%d\n", BinSearch(A, 0, 9, 9));
-}
diff --git a/BinaryAdd.c b/BinaryAdd.c
deleted file mode 100644
index b2b7fa1..0000000
--- a/BinaryAdd.c
+++ /dev/null
@@ -1,29 +0,0 @@
-#include
-
-void BinaryAdd(int a[], int b[], int n,int c[]) {
- int promote = 0;
- int i;
- int result;
-
- for (i = n - 1; i >= 0; i--) {
- result = a[i] + b[i] + promote;
- if (result >= 2) {
- result = result - 2;
- promote = 1;
- }
- else
- promote = 0;
- c[i + 1] = result;
- }
- c[0] = promote;
-}
-
-int main() {
- int a[4] = {1,0,1,1};
- int b[4] = {1,1,1,1};
- int c[5];
-
- BinaryAdd(a, b, 4, c);
- printf("%d%d%d%d + %d%d%d%d = %d%d%d%d%d\n", a[0], a[1], a[2], a[3], b[0], b[1], b[2], b[3], c[0], c[1], c[2], c[3], c[4]);
- return 0;
-}
diff --git a/BubbleSort.c b/BubbleSort.c
deleted file mode 100644
index 7ab898a..0000000
--- a/BubbleSort.c
+++ /dev/null
@@ -1,33 +0,0 @@
-//BubbleSort(A)
-//for i = 1 to A.length - 1
-// for j = A.length downto i + 1
-// if A[j] < A[j - 1]
-// swap(A[j], A[j - 1])
-
-#include
-
-void BubbleSort(int A[], int n) {
- int i, j;
-
- for (i = 0; i < n - 1; i++)
- for (j = n - 1; j > i; j--)
- if (A[j] < A[j - 1]) {
- int tmp = A[j];
-
- A[j] = A[j - 1];
- A[j - 1] = tmp;
- }
-}
-
-int main() {
- int a[1000];
- int i;
-
- for (i = 0; i < 1000; i++)
- a[i] = 1000 - i;
- BubbleSort(a, 1000);
- for (i = 0; i < 1000; i++)
- printf("%d\t", a[i]);
- printf("\n");
- return 0;
-}
diff --git a/FengSort.c b/FengSort.c
index 124cb26..c9befcc 100644
--- a/FengSort.c
+++ b/FengSort.c
@@ -31,7 +31,7 @@ int main()
FengSort(a, 0, 8);
printf("%d, %d, %d, %d, %d, %d, %d, %d, %d\n", a[0], a[1], a[2], a[3],
a[4], a[5], a[6], a[7], a[8]);
- FengSort(b, 0, 1);
- printf("%d,%d\n", b[0], b[1]);
- exit(0);
+ FengSort(b, 0, 1);
+ printf("%d,%d\n", b[0], b[1]);
+ exit(0);
}
diff --git a/Fibonacci.c b/Fibonacci.c
deleted file mode 100644
index 181a626..0000000
--- a/Fibonacci.c
+++ /dev/null
@@ -1,22 +0,0 @@
-void swap(int *x, int *y) {
- int temp;
-
- temp = *x;
- *x = *y;
- *y = temp;
-}
-
-/* Compute Fibonacci number fib(n); fib(0) = 1, fib(1); fib(n) = fib(n-1) + fib(n-2); return fib(n) of int type */
-
-int fib(int n) {
- int fib1 = 1, fib2 = 1;
- int i;
-
- for (i = 2; i <= n; i++) {
- fib1 = fib1 + fib2;
- swap(&fib1, &fib2);
- }
- return fib2;
-
-}
-
diff --git a/Horner.c b/Horner.c
deleted file mode 100644
index d814262..0000000
--- a/Horner.c
+++ /dev/null
@@ -1,34 +0,0 @@
-//This procedure implements Horner's rule for evaluating
-//a polynomial
-#include
-#include
-
-void Horner(int A[], int n, int x) {
- int sum = 0;
- int i;
-
- for (i = n; i >= 0; i--)
- sum = A[i] + x * sum;
- printf("%d\n", sum);
-}
-
-//void Horner2(int A[], int n, int x) {
- //int sum = 0;
- //int i;
-//
- //for (i = n; i >= 0; i--)
- //sum = A[i] * pow(x, i) + sum;
- //printf("%d\n", sum);
-//}
-
-int main() {
- int a[10] = {1,2,30,4,5,6,7,8,9,0};
-
- Horner(a, 9, 2);
- //Horner2(a, 9, 2);
- return 0;
-}
-
-
-
-
diff --git a/Horner_rule.py b/Horner_rule.py
new file mode 100644
index 0000000..445940a
--- /dev/null
+++ b/Horner_rule.py
@@ -0,0 +1,13 @@
+#!/usr/bin/env python
+# encoding: utf-8
+import functools
+
+
+def Horner_rule(x, coefficients):
+ """
+ Implements Horner's rule
+ :param x:
+ :param coefficients:
+ :return:
+ """
+ return functools.reduce(lambda accumulate, coefficient: coefficient + accumulate * x, reversed(coefficients), 0)
diff --git a/Ins-Merge.c b/Ins-Merge.c
deleted file mode 100644
index 9710910..0000000
--- a/Ins-Merge.c
+++ /dev/null
@@ -1,98 +0,0 @@
-//* This program uses insertion sort within merge sort when subproblems
-//* become sufficiently small
- // MERGE(A, p, q, r)
- // n1 = q - p + 1
- // n2 = r - q
- // L[1...n1] = A[p...q]
- // R[1...n2] = A[q+1...r]
- // L[n1+1] = ∞
- // R[n2+1] = ∞
- // i = 1
- // j = 1
- // for k = p to r
- // if L[i] <= R[j]
- // A[k] = L[i]
- // i = i + 1
- // else
- // A[k] = R[j]
- // j = j + 1
-#include
-#include
-#include
-
-void InsSort(int a[], int n)
-{
- int i, j;
- int key;
- for (i = 1; i < n; i++)
- {
- key = a[i];
- for (j = i - 1; j >= 0 && a[j] > key; j--)
- {
- a[j + 1] = a[j];
- a[j] = key;
- }
- }
-}
-
-void MERGE(int A[], int first, int inter, int end)
-{
- int len1 = inter - first + 1;
- int len2 = end - inter;
- int i;
- int j;
- int k;
- int *L;
- int *R;
-
- L = (int *)calloc(len1 + 1, sizeof(int));
- R = (int *)calloc(len2 + 1, sizeof(int));
- for (i = 0; i < len1; i++)
- L[i] = A[first + i];
- for (j = 0; j < len2; j++)
- R[j] = A[inter + j + 1];
- L[len1] = INT_MAX;
- R[len2] = INT_MAX;
-
- i = 0;
- j = 0;
- for (k = first; k <= end; k++)
- {
- if (L[i] <= R[j])
- A[k] = L[i++];
- else
- A[k] = R[j++];
- }
- free(L);
- free(R);
-}
-
-void MergeSort(int A[], int n, int length)
-{
- int num = n / length;
- int last_length = n - (num - 1) * length;
- int i;
-
- for (i = 1; i < num; i++)
- {
- InsSort(A + (i - 1) * length, length);
- if (i > 1)
- MERGE(A, 0 , (i - 1) * length - 1, i * length - 1);
- }
- InsSort(A + (i - 1) * length, last_length);
- MERGE(A, 0, (i - 1) * length - 1, n - 1);
-}
-
-int main()
-{
- int a[77];
- int i;
-
- for (i = 0; i < 77; i++)
- a[i] = 77 - i;
- MergeSort(a, 77, 9);
- for (i = 0; i < 77; i++)
- printf("%d\t", a[i]);
- printf("\n");
- return 0;
-}
diff --git a/Ins-Merge2.c b/Ins-Merge2.c
deleted file mode 100644
index d0ce4bc..0000000
--- a/Ins-Merge2.c
+++ /dev/null
@@ -1,94 +0,0 @@
-//* Divide and conquer version of Ins-Merge
- // MERGE(A, p, q, r)
- // n1 = q - p + 1
- // n2 = r - q
- // L[1...n1] = A[p...q]
- // R[1...n2] = A[q+1...r]
- // L[n1+1] = ∞
- // R[n2+1] = ∞
- // i = 1
- // j = 1
- // for k = p to r
- // if L[i] <= R[j]
- // A[k] = L[i]
- // i = i + 1
- // else
- // A[k] = R[j]
- // j = j + 1
-#include
-#include
-#include
-
-void InsSort(int a[], int n)
-{
- int i, j;
- int key;
- for (i = 1; i < n; i++)
- {
- key = a[i];
- for (j = i - 1; j >= 0 && a[j] > key; j--)
- {
- a[j + 1] = a[j];
- a[j] = key;
- }
- }
-}
-
-void MERGE(int A[], int first, int inter, int end)
-{
- int len1 = inter - first + 1;
- int len2 = end - inter;
- int i;
- int j;
- int k;
- int *L;
- int *R;
-
- L = (int *)calloc(len1 + 1, sizeof(int));
- R = (int *)calloc(len2 + 1, sizeof(int));
- for (i = 0; i < len1; i++)
- L[i] = A[first + i];
- for (j = 0; j < len2; j++)
- R[j] = A[inter + j + 1];
- L[len1] = INT_MAX;
- R[len2] = INT_MAX;
-
- i = 0;
- j = 0;
- for (k = first; k <= end; k++)
- {
- if (L[i] <= R[j])
- A[k] = L[i++];
- else
- A[k] = R[j++];
- }
- free(L);
- free(R);
-}
-
-void MergeSort(int A[], int start, int end, int length)
-{
- if ((end - start + 1) > length) {
- int middle = (start + end) / 2;
-
- MergeSort(A, start, middle, length);
- MergeSort(A, middle + 1, end, length);
- MERGE(A, start, middle, end);
- }
- else
- InsSort(A + start, end - start + 1);
-}
-
-int main()
-{
- int a[77];
- int i;
-
- for (i = 0; i < 77; i++)
- a[i] = 77 - i;
- MergeSort(a, 1, 8, 9);
- for (i = 0; i < 77; i++)
- printf("%d\t", a[i]);
- printf("\n");
- return 0;
-}
diff --git a/InsSort-BinSearch.c b/InsSort-BinSearch.c
deleted file mode 100644
index a85159a..0000000
--- a/InsSort-BinSearch.c
+++ /dev/null
@@ -1,51 +0,0 @@
-#include
-
-void swap(int *a, int *b)
-{
- int tmp = *a;
-
- *a = *b;
- *b = tmp;
-}
-//Determine where x should be placed in array A
-int BinSearch(int A[], int first, int end, int x)
-{
- int length = end - first;
- int inter;
-
- while (length >= 0)
- {
- inter = (first + end) / 2;
- if (x == A[inter])
- return inter;
- else if (x < A[inter])
- end = inter - 1;
- else
- first = inter + 1;
- length = end - first;
- }
-// printf("%d, %d\n", first, end);
- return first;
-}
-
-void InsSort(int a[], int n)
-{
- int i, j;
- int pos;
-
- for (i = 1; i < n; i++)
- {
- pos = BinSearch(a, 0, i - 1, a[i]);
- for (j = i; j > pos; j--)
- swap(a + j, a + j - 1);
- }
-}
-
-int main()
-{
- int a[7] = { 31, 101, 59, 26, 0, 61, 58 };
-
- InsSort(a, 7);
- printf("%d,%d,%d,%d,%d,%d,%d\n", a[0], a[1], a[2], a[3], a[4], a[5], a[6]);
- return 0;
-}
diff --git a/InsSort.c b/InsSort.c
deleted file mode 100644
index fee77ba..0000000
--- a/InsSort.c
+++ /dev/null
@@ -1,24 +0,0 @@
-#include
-
-void InsSort(int a[], int n)
-{
- int i, j;
- int key;
- for (i = 1; i < n; i++)
- {
- key = a[i];
- for (j = i - 1; j >= 0 && a[j] > key; j--)
- {
- a[j + 1] = a[j];
- a[j] = key;
- }
- }
-}
-
-void main()
-{
- int a[6] = { 31, 41, 59, 26, 61, 58 };
-
- InsSort(a, 6);
- printf("%d,%d,%d,%d,%d,%d", a[0], a[1], a[2], a[3], a[4], a[5]);
-}
\ No newline at end of file
diff --git a/Johnson.py b/Johnson.py
index c4fa24b..7dfe37f 100644
--- a/Johnson.py
+++ b/Johnson.py
@@ -1,41 +1,53 @@
from graph import min_priority_queue, Vertex, Graph
import numpy as np
+
def Bellman_Ford(self, w, s):
- '''
+ """
The Bellman-Ford algorithm solves the single-source
shortest-paths problem in the general case in which edge
weights may be negative.
- If there is a negative-weight cycle that is reachable from
+ If there is a negative-weight cycle that is reachable from
the source s, this function returns False and indicates that
no solution exists.
If there is no such cycle, this function returns True and produces
the shortest paths and their weights.
- '''
- initialize_signle_source(self, s)
+
+ :param self:
+ :param w:
+ :param s:
+ :return:
+ """
+ initialize_single_source(self, s)
for i in range(1, len(self.vertices)):
- for u,v in self.edges:
- relax(self, u, v, w)
- for u,v in self.edges:
+ for u, v in self.edges:
+ relax(u, v, w)
+ for u, v in self.edges:
if v.d > u.d + w[(u, v)]:
return False
return True
-def initialize_signle_source(self, s):
- for v in self.vertices:
- v.d = float("Inf")
- v.p = None
- s.d = 0
-def relax(self, u, v, w):
+
+
+def initialize_single_source(self, s):
+ for v in self.vertices:
+ v.d = float("Inf")
+ v.p = None
+ s.d = 0
+
+
+def relax(u, v, w):
if v.d > u.d + w[u, v]:
v.d = u.d + w[u, v]
v.p = u
+
+
def Dijkstra(self, w, s):
- '''
+ """
Dijkstra's algorithm solves the single-source shortest-paths problem
on a weighted, directed graph G = (V, E) for the case in which all edge
weights are nonnegative.
- '''
- initialize_signle_source(self, s)
+ """
+ initialize_single_source(self, s)
S = set()
Q = min_priority_queue(self.vertices, 'd')
while Q.heap_size > 1:
@@ -46,26 +58,28 @@ def Dijkstra(self, w, s):
v.d = u.d + w[u, v]
v.p = u
Q.heap_decrease_key(v.index, u.d + w[u, v])
+
+
def Johnson(self, w):
G = self
n = len(G.vertices)
s = Vertex("s")
- GG = Graph(G.vertices.union({s}), G.edges + [(s, v) for v in G.vertices])
+ GG = Graph(G.vertices.union({s}), G.edges | set((s, v) for v in G.vertices))
for v in G.vertices:
w[(s, v)] = 0
- if Bellman_Ford(GG, w, s) == False:
- print "the input graph contains a negative-weight cycle"
+ if not Bellman_Ford(GG, w, s):
+ print("the input graph contains a negative-weight cycle")
else:
h = dict()
for v in GG.vertices:
h[v] = v.d
- #for key,value in h.iteritems():
- # print "h({}) = {}".format(key, value)
+ # for key,value in h.iteritems():
+ # print(( "h({}) = {}".format(key, value)))
ww = dict()
for u, v in GG.edges:
ww[(u, v)] = w[(u, v)] + h[u] - h[v]
- #for key,value in ww.iteritems():
- # print "ww({}) = {}".format(key, value)
+ # for key,value in ww.iteritems():
+ # print(( "ww({}) = {}".format(key, value)))
D = np.empty((n, n))
for u in G.vertices:
Dijkstra(G, ww, u)
diff --git a/MergeSort.c b/MergeSort.c
deleted file mode 100644
index 03ea825..0000000
--- a/MergeSort.c
+++ /dev/null
@@ -1,54 +0,0 @@
-#include
-#include
-
-//A version of merge procedure that stops once either array L or R has had //all its elements copied back to A
-void Combine(int A[], int first, int inter, int end) {
- int len1 = inter - first + 1;
- int len2 = end - inter;
- int i;
- int j;
- int k;
- int *L;
- int *R;
-
- L = (int *) calloc(len1, sizeof(int));
- R = (int *) calloc(len2, sizeof(int));
- for (i = 0; i < len1; i++)
- L[i] = A[first + i];
- for (j = 0; j < len2; j++)
- R[j] = A[inter + j + 1];
-
- i = 0;
- j = 0;
- k = first;
- while (i < len1 && j < len2)
- if (L[i] <= R[j])
- A[k++] = L[i++];
- else
- A[k++] = R[j++];
- if (i == len1)
- while (j < len2)
- A[k++] = R[j++];
- else if (j = len2)
- while (i < len1)
- A[k++] = L[i++];
- free(L);
- free(R);
-}
-
-void MergeSort(int A[], int first, int end) {
- int middle = (first + end) / 2;
-
- if (end == first)
- return;
- MergeSort(A, first, middle);
- MergeSort(A, middle + 1, end);
- Combine(A, first, middle, end);
- return;
-}
-
-void main() {
- int a[8] = {1,3,4,5,2,6,0,10};
- MergeSort(a, 0, 7);
- printf("%d, %d, %d, %d, %d, %d, %d, %d\n", a[0], a[1], a[2], a[3], a[4], a[5], a[6], a[7]);
-}
diff --git a/queue.py b/Queue.py
similarity index 66%
rename from queue.py
rename to Queue.py
index fbbc0f1..41aa7b4 100644
--- a/queue.py
+++ b/Queue.py
@@ -1,34 +1,44 @@
class FullException(Exception):
def __init__(self):
Exception.__init__(self)
+
+
class EmptyException(Exception):
def __init__(self):
Exception.__init__(self)
-class queue(object):
+
+
+class Queue:
def __init__(self, size):
self.data = [0] * size
- self.length = size
+ self.size = size
self.head = 0
self.tail = 0
+
def enqueue(self, x):
if self.full():
- raise FullException()
+ raise FullException()
self.data[self.tail] = x
- if self.tail == self.length - 1:
+ if self.tail == self.size - 1:
self.tail = 0
else:
self.tail = self.tail + 1
+
def dequeue(self):
if self.empty():
- raise EmptyException()
+ raise EmptyException()
x = self.data[self.head]
- if self.head == self.length - 1:
+ if self.head == self.size - 1:
self.head = 0
else:
self.head = self.head + 1
return x
+
def empty(self):
return self.tail == self.head
+
def full(self):
- #print "tail: {}, head: {}, size: {}".format(self.tail, self.head, self.length)
- return (self.tail + 1) % self.length == self.head
+ return (self.tail + 1) % self.size == self.head
+
+ def capacity(self):
+ return self.size - 1
diff --git a/README.md b/README.md
index c4adc91..784d417 100644
--- a/README.md
+++ b/README.md
@@ -1,4 +1,9 @@
# algorithm
implementation of algorithms in CLRS
-test.sh is the shell script to run all the testcases
+## note
+Since python2 is outdated, the original python2.7 code is moved to python2.7 branch.
+The master branch support python3 only.
+
+## test
+Run testcase in tests folder
diff --git a/activity_selection.py b/activity_selection.py
index 95c248a..3369a04 100644
--- a/activity_selection.py
+++ b/activity_selection.py
@@ -1,35 +1,40 @@
from numpy import zeros
+
def activity_selection(s, f, n):
c = zeros((n + 2, n + 2))
activities = zeros((n + 2, n + 2))
s = [float("-Inf")] + s[0:n] + [float("Inf")]
f = [float("-Inf")] + f[0:n] + [float("Inf")]
for l in range(3, n + 3):
- for i in range(0, n + 3 - l):
+ for i in range(n + 3 - l):
j = i + l - 1
- print "i = {}, j = {}".format(i, j)
+ print("i = {}, j = {}".format(i, j))
for k in range(i + 1, j):
- print "k = {}".format(k)
- print "s[{}] = {}, f[{}] = {}".format(k, s[k], k, f[k])
- print "s[{}] = {}, f[{}] = {}".format(j, s[j], i, f[i])
+ print("k = {}".format(k))
+ print("s[{}] = {}, f[{}] = {}".format(k, s[k], k, f[k]))
+ print("s[{}] = {}, f[{}] = {}".format(j, s[j], i, f[i]))
if f[i] <= s[k] and f[k] <= s[j]:
t = c[i, k] + c[k, j] + 1
- print "t = {}, c[{}, {}] = {}".format(t, i, j, c[i, j])
+ print("t = {}, c[{}, {}] = {}".format(t, i, j, c[i, j]))
if t > c[i, j]:
c[i, j] = t
activities[i, j] = k
- return c,activities
+ return c, activities
+
+
def activity_selection_with_weight(s, f, v, n):
- '''This is a modification to the activity-selection problem in which each activity has,
+ """
+ This is a modification to the activity-selection problem in which each activity has,
in addition to a start and finish time, a value v. Now the object is to maximize
- the total value of the activies scheduled. It can be solved by dynamic programming method'''
+ the total value of the activities scheduled. It can be solved by dynamic programming method
+ """
c = zeros((n + 2, n + 2))
activities = zeros((n + 2, n + 2))
s = [float("-Inf")] + s[0:n] + [float("Inf")]
f = [float("-Inf")] + f[0:n] + [float("Inf")]
for l in range(3, n + 3):
- for i in range(0, n + 3 - l):
+ for i in range(n + 3 - l):
j = i + l - 1
for k in range(i + 1, j):
if f[i] <= s[k] and f[k] <= s[j]:
@@ -37,10 +42,14 @@ def activity_selection_with_weight(s, f, v, n):
if t > c[i, j]:
c[i, j] = t
activities[i, j] = k
- return c,activities
+ return c, activities
+
+
def recursive_activity_selector(s, f, n):
f = [float("-Inf")] + f
return recursive_activity_selector_aux(s, f, 0, n)
+
+
def recursive_activity_selector_aux(s, f, k, n):
m = k + 1
while m <= n and s[m - 1] < f[k]:
@@ -49,6 +58,8 @@ def recursive_activity_selector_aux(s, f, k, n):
return {m}.union(recursive_activity_selector_aux(s, f, m, n))
else:
return {}
+
+
def greedy_activity_selector(s, f):
n = len(s)
A = {1}
@@ -58,10 +69,13 @@ def greedy_activity_selector(s, f):
A = A.union({m})
k = m
return A
+
+
def greedy_activity_selector_last(s, f):
- '''Instead of always selecting the first activity to finish,
+ """Instead of always selecting the first activity to finish,
select the last activity to start that is compatible with all
- previously selected activities'''
+ previously selected activities
+ """
n = len(s)
A = {n}
k = n
@@ -70,14 +84,18 @@ def greedy_activity_selector_last(s, f):
A = A.union({m})
k = m
return A
+
+
def print_activity(activities):
m = activities.shape[0] - 1
n = activities.shape[1] - 1
print_activity_aux(activities, 0, n)
+
+
def print_activity_aux(activities, m, n):
a = activities[m, n]
if a == 0:
return
print_activity_aux(activities, m, a)
- print int(a)
+ print(int(a))
print_activity_aux(activities, a, n)
diff --git a/all_pairs_shortest_paths.py b/all_pairs_shortest_paths.py
index 323a572..d6115b3 100644
--- a/all_pairs_shortest_paths.py
+++ b/all_pairs_shortest_paths.py
@@ -1,21 +1,23 @@
import numpy as np
+
def extend_shortest_paths(L, W):
n = L.shape[0]
- LW = np.empty((n, n))
- for i in range(0, n):
- for j in range(0, n):
+ LW = np.empty((n, n))
+ for i in range(n):
+ for j in range(n):
LW[i, j] = float("Inf")
- for k in range(0, n):
+ for k in range(n):
LW[i, j] = min(LW[i, j], L[i, k] + W[k, j])
return LW
+
def slow_all_pairs_shortest_paths(W):
n = W.shape[0]
L = [None] * n
L[0] = np.empty((n, n))
- for i in range(0, n):
- for j in range(0, n):
+ for i in range(n):
+ for j in range(n):
if i == j:
L[0][i, j] = 0
else:
@@ -25,34 +27,36 @@ def slow_all_pairs_shortest_paths(W):
L[m] = extend_shortest_paths(L[m - 1], W)
return L[m]
+
def extend_shortest_paths_with_predecessor_subgraph(L, P, W):
n = W.shape[0]
LW = np.empty((n, n))
PP = np.empty((n, n))
- for i in range(0, n):
- for j in range(0, n):
+ for i in range(n):
+ for j in range(n):
LW[i, j] = float("Inf")
PP[i, j] = None
- for k in range(0, n):
+ for k in range(n):
if LW[i, j] > L[i, k] + W[k, j]:
LW[i, j] = L[i, k] + W[k, j]
PP[i, j] = k + 1
if LW[i, j] == L[i, j]:
PP[i, j] = P[i, j]
-# if j == i:
-# PP[i, j] = None
-# elif j != k:
-# PP[i, j] = k + 1
-# else:
-# PP[i, j] = P[i, j]
+ # if j == i:
+ # PP[i, j] = None
+ # elif j != k:
+ # PP[i, j] = k + 1
+ # else:
+ # PP[i, j] = P[i, j]
return LW, PP
+
def slow_all_pairs_shortest_paths_with_predecessor_subgraph(W):
n = W.shape[0]
L = np.empty((n, n))
P = np.empty((n, n))
- for i in range(0, n):
- for j in range(0, n):
+ for i in range(n):
+ for j in range(n):
if j == i:
L[i, j] = 0
else:
@@ -60,40 +64,43 @@ def slow_all_pairs_shortest_paths_with_predecessor_subgraph(W):
P[i, j] = None
for m in range(1, n):
L, P = extend_shortest_paths_with_predecessor_subgraph(L, P, W)
- print L
- print P
+ print(L)
+ print(P)
return L, P
+
def predecessor(W, L):
n = W.shape[0]
P = np.empty((n, n))
- COMPLETED = np.empty((n, n), dtype = bool)
+ COMPLETED = np.empty((n, n), dtype=bool)
DEPTH = np.empty((n, n))
- for i in range(0, n):
- for j in range(0, n):
+ for i in range(n):
+ for j in range(n):
COMPLETED[i, j] = False
DEPTH[i, j] = None
P[i, j] = None
- for i in range(0, n):
+ for i in range(n):
P[i, i] = None
COMPLETED[i, i] = True
DEPTH[i, i] = 0
for m in range(1, n):
- for i in range(0, n):
- for j in range(0, n):
+ for i in range(n):
+ for j in range(n):
if i == 0:
- print m
- print COMPLETED[i, j]
- print L[m][i]
- print L[n - 1][j]
+ print(m)
+ print(COMPLETED[i, j])
+ print(L[m][i])
+ print(L[n - 1][j])
if COMPLETED[i, j] == False and L[m][i, j] == L[n - 1][i, j]:
- for k in range(0, n):
- if DEPTH[i, k] == m - 1 and L[m][i, j] == L[m -1][i, k] + W[k, j]:
+ for k in range(n):
+ if DEPTH[i, k] == m - 1 and L[m][i, j] == L[m - 1][i, k] + W[k, j]:
DEPTH[i, j] = m
P[i, j] = k + 1
COMPLETED[i, j] = True
break
return P
+
+
def faster_all_pairs_shortest_paths(W):
n = W.shape[0]
L = W
@@ -101,42 +108,48 @@ def faster_all_pairs_shortest_paths(W):
while m < n - 1:
L = extend_shortest_paths(L, L)
m = 2 * m
- print m
- print L
+ print(m)
+ print(L)
return L
+
def negative_weight_cycle(W):
L = faster_all_pairs_shortest_paths(W)
n = W.shape[0]
status = True
- for i in range(0, n):
- for j in range(0, n):
- for k in range(0, n):
+ for i in range(n):
+ for j in range(n):
+ for k in range(n):
if L[i, j] > L[i, k] + W[k, j]:
- print "source {} contains a negative-weight cycle".format(i + 1)
+ print("source {} contains a negative-weight cycle".format(i + 1))
status = False
return status
+
+
def negative_weight_cycle_another(W):
L = faster_all_pairs_shortest_paths(W)
L = extend_shortest_paths(L, W)
- print L
+ print(L)
status = True
n = W.shape[0]
- for i in range(0, n):
+ for i in range(n):
if L[i, i] < 0:
status = False
return status
+
+
def minimum_negative_weight_cycle_edges_number(W):
n = W.shape[0]
L = W
for m in range(2, n + 1):
L = extend_shortest_paths(L, W)
- for i in range(0, n):
+ for i in range(n):
if L[i, i] < 0:
- print "minimum negative weight cycle edges number is {}".format(m)
+ print("minimum negative weight cycle edges number is {}".format(m))
return False
return True
+
def Floyd_Warshall(W):
n = W.shape[0]
D = [None] * (n + 1)
@@ -154,52 +167,57 @@ def Floyd_Warshall(W):
P[k] = np.empty((n, n))
for i in range(n):
for j in range(n):
- D[k][i,j] = min(D[k - 1][i, j], D[k - 1][i, k - 1] + D[k - 1][k - 1, j])
+ D[k][i, j] = min(D[k - 1][i, j], D[k - 1][i, k - 1] + D[k - 1][k - 1, j])
if D[k - 1][i, j] > D[k - 1][i, k - 1] + D[k - 1][k - 1, j]:
P[k][i, j] = P[k - 1][k - 1, j]
else:
P[k][i, j] = P[k - 1][i, j]
return D[n], P[n]
+
+
def Floyd_Warshall_WITH_LI(W):
n = W.shape[0]
D = [None] * (n + 1)
D[0] = W
LI = [None] * (n + 1)
- LI[0] = np.empty((n, n), dtype = np.int32)
+ LI[0] = np.empty((n, n), dtype=np.int32)
for i in range(1, n + 1):
for j in range(1, n + 1):
- LI[0][i - 1, j - 1] = 0
+ LI[0][i - 1, j - 1] = 0
for k in range(1, n + 1):
D[k] = np.empty((n, n))
- LI[k] = np.empty((n, n), dtype = np.int32)
+ LI[k] = np.empty((n, n), dtype=np.int32)
for i in range(n):
for j in range(n):
- D[k][i,j] = min(D[k - 1][i, j], D[k - 1][i, k - 1] + D[k - 1][k - 1, j])
+ D[k][i, j] = min(D[k - 1][i, j], D[k - 1][i, k - 1] + D[k - 1][k - 1, j])
if D[k - 1][i, j] > D[k - 1][i, k - 1] + D[k - 1][k - 1, j]:
LI[k][i, j] = k
else:
LI[k][i, j] = LI[k - 1][i, j]
- print LI[k]
- print D[k]
+ print(LI[k])
+ print(D[k])
return D[n], LI[n]
+
def print_all_pairs_shortest_path(LI, i, j):
global status
status = [False] * LI.shape[0]
print_all_pairs_shortest_path_aux(LI, i, j)
+
+
def print_all_pairs_shortest_path_aux(LI, i, j):
global status
- # print "www: {}, {}, status: {}".format(i, j, status)
+ # print( "www: {}, {}, status: {}".format(i, j, status))
if LI[i - 1, j - 1] == 0:
- if status[i - 1] == False:
+ if not status[i - 1]:
status[i - 1] = True
- print i
- if status[j - 1] == False:
+ print(i)
+ if not status[j - 1]:
status[j - 1] = True
- print j
+ print(j)
else:
print_all_pairs_shortest_path_aux(LI, i, LI[i - 1, j - 1])
- if status[LI[i - 1, j - 1] - 1] == False:
- print LI[i - 1, j - 1]
- status[LI[i - 1, j - 1] - 1] = True
+ if not status[LI[i - 1, j - 1] - 1]:
+ print(LI[i - 1, j - 1])
+ status[LI[i - 1, j - 1] - 1] = True
print_all_pairs_shortest_path_aux(LI, LI[i - 1, j - 1], j)
diff --git a/all_pairs_shortest_paths_test.py b/all_pairs_shortest_paths_test.py
deleted file mode 100644
index 6819906..0000000
--- a/all_pairs_shortest_paths_test.py
+++ /dev/null
@@ -1,23 +0,0 @@
-from all_pairs_shortest_paths import extend_shortest_paths, slow_all_pairs_shortest_paths, faster_all_pairs_shortest_paths
-import unittest
-import numpy as np
-
-class TestAllPairsShortestPaths(unittest.TestCase):
- def test_slow_all_pairs_shortest_paths(self):
- W = np.array([[0, 3, 8, float("Inf"), -4], [float("Inf"), 0, float("Inf"), 1, 7], [float("Inf"), 4, 0, float("Inf"), float("Inf")], [2, float("Inf"), -5, 0, float("Inf")], [float("Inf"), float("Inf"), float("Inf"), 6, 0]])
- R = slow_all_pairs_shortest_paths(W)
- L = np.array([[0, 1, -3, 2, -4], [3, 0, -4, 1, -1], [7, 4, 0, 5, 3], [2, -1, -5, 0, -2], [8, 5, 1, 6, 0]])
- self.assertEquals((R == L).all(), True)
- W = np.array([[0, float("Inf"), float("Inf"), float("Inf"), -1, float("Inf")], [1, 0, float("Inf"), 2, float("Inf"), float("Inf")], [float("Inf"), 2, 0, float("Inf"), float("Inf"), -8], [-4, float("Inf"), float("Inf"), 0, 3, float("Inf")], [float("Inf"), 7, float("Inf"), float("Inf"), 0, float("Inf")], [float("Inf"), 5, 10, float("Inf"), float("Inf"), 0]])
- R = slow_all_pairs_shortest_paths(W)
- L = np.array([[0, 6, float("Inf"), 8, -1, float("Inf")], [-2, 0, float("Inf"), 2, -3, float("Inf")], [-5, -3, 0, -1, -6, -8], [-4, 2, float("Inf"), 0, -5, float("Inf")], [5, 7, float("Inf"), 9, 0, float("Inf")], [3, 5, 10, 7, 2, 0]])
- self.assertEquals((R == L).all(), True)
- def test_faster_all_pairs_shortest_paths(self):
- W = np.array([[0, 3, 8, float("Inf"), -4], [float("Inf"), 0, float("Inf"), 1, 7], [float("Inf"), 4, 0, float("Inf"), float("Inf")], [2, float("Inf"), -5, 0, float("Inf")], [float("Inf"), float("Inf"), float("Inf"), 6, 0]])
- R = faster_all_pairs_shortest_paths(W)
- L = np.array([[0, 1, -3, 2, -4], [3, 0, -4, 1, -1], [7, 4, 0, 5, 3], [2, -1, -5, 0, -2], [8, 5, 1, 6, 0]])
- self.assertEquals((R == L).all(), True)
- W = np.array([[0, float("Inf"), float("Inf"), float("Inf"), -1, float("Inf")], [1, 0, float("Inf"), 2, float("Inf"), float("Inf")], [float("Inf"), 2, 0, float("Inf"), float("Inf"), -8], [-4, float("Inf"), float("Inf"), 0, 3, float("Inf")], [float("Inf"), 7, float("Inf"), float("Inf"), 0, float("Inf")], [float("Inf"), 5, 10, float("Inf"), float("Inf"), 0]])
- R = faster_all_pairs_shortest_paths(W)
- L = np.array([[0, 6, float("Inf"), 8, -1, float("Inf")], [-2, 0, float("Inf"), 2, -3, float("Inf")], [-5, -3, 0, -1, -6, -8], [-4, 2, float("Inf"), 0, -5, float("Inf")], [5, 7, float("Inf"), 9, 0, float("Inf")], [3, 5, 10, 7, 2, 0]])
- self.assertEquals((R == L).all(), True)
diff --git a/any_disks_intersect.py b/any_disks_intersect.py
index 1bbd33d..29a139f 100644
--- a/any_disks_intersect.py
+++ b/any_disks_intersect.py
@@ -1,32 +1,37 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
# we use 0 to mean red, 1 to mean black
from tree import Node, Tree
-from heap import max_heap
+from heap import MaxHeap
+
def comparable(a, b):
- '''Given two disks a and b that are comparable at x, determine whether a is above b or not.'''
+ """Given two disks a and b that are comparable at x, determine whether a is above b or not."""
a_y = a[0][1]
b_y = b[0][1]
- if a_y >= b_y:
- return True
- else:
- return False
+ return a_y >= b_y
+
+
class disk(tuple):
def __init__(self, d):
super(disk, self).__init__(d)
self.pointer = None
+
+
class point(list):
def __init__(self, info, disk):
super(point, self).__init__(info)
self.disk = disk
+
+
class rb_node(Node):
def __init__(self, key, p, left, right, color):
Node.__init__(self, key, p, left, right)
self.color = color
- if key != None:
+ if key is not None:
key.pointer = self
+
def minimum(self, nil):
x = self
y = x
@@ -34,16 +39,21 @@ def minimum(self, nil):
y = x
x = x.left
return y
+
def maximum(self, nil):
x = self
while x.right != nil:
x = x.right
return x
+
+
class rb_tree(Tree):
nil = rb_node(None, None, None, None, 1)
root = nil
+
def __init__(self):
pass
+
def above(self, s):
x = s.pointer
if x.right != self.nil:
@@ -52,6 +62,7 @@ def above(self, s):
while x.p != self.nil and x.p.right == x:
x = x.p
return x.p.key
+
def below(self, s):
x = s.pointer
if x.left != self.nil:
@@ -60,10 +71,13 @@ def below(self, s):
while x.p != self.nil and x.p.left == x:
x = x.p
return x.p.key
+
def minimum(self):
return self.root.minimum(self.nil)
+
def __getitem__(self, key):
return self.iterative_tree_search(key)
+
def left_rotate(self, x):
y = x.right
x.right = y.left
@@ -78,6 +92,7 @@ def left_rotate(self, x):
x.p.right = y
y.left = x
x.p = y
+
def right_rotate(self, y):
x = y.left
y.left = x.right
@@ -92,8 +107,9 @@ def right_rotate(self, y):
y.p.left = x
x.right = y
y.p = x
+
def insert(self, z):
- ''' the disk z will only be inserted when the left endpoint of z is being processed'''
+ """ the disk z will only be inserted when the left endpoint of z is being processed"""
# this is the x_coordinate of the left endpoint of z
x_coordinate = z[0][0]
z = rb_node(z, None, None, None, 0)
@@ -114,8 +130,9 @@ def insert(self, z):
z.p = y
z.left = self.nil
z.right = self.nil
- z.color = 0 #red
+ z.color = 0 # red
self.insert_fixed(z)
+
def insert_fixed(self, z):
while z.p.color == 0:
if z.p.p.left == z.p:
@@ -149,6 +166,7 @@ def insert_fixed(self, z):
z.color = 0
z.p.color = 1
self.root.color = 1
+
def transplant(self, u, v):
if u.p == self.nil:
self.root = v
@@ -157,6 +175,7 @@ def transplant(self, u, v):
else:
u.p.right = v
v.p = u.p
+
def delete(self, z):
z = z.pointer
y = z
@@ -183,6 +202,7 @@ def delete(self, z):
y.color = z.color
if y_original_color == 1:
self.delete_fixup(x)
+
def delete_fixup(self, x):
while x != self.root and x.color == 1:
if x == x.p.left:
@@ -228,8 +248,14 @@ def delete_fixup(self, x):
self.right_rotate(x.p)
x = self.root
x.color = 1
+
+
def any_disks_intersect(S):
- '''This algorithm takes as input a set S of n disks represented by its center point and radius, returning the boolean value TRUE if any pair of disks in S intersects, and FALSE otherwise.'''
+ """
+ This algorithm takes as input a set S of n disks represented by its center point and radius, returning the boolean value TRUE if any pair of disks in S intersects, and FALSE otherwise.
+ :param S:
+ :return:
+ """
T = rb_tree()
point_list = []
disk_list = []
@@ -242,38 +268,37 @@ def any_disks_intersect(S):
y = center_point[1]
point_list.append(point([x - radius, 0, y], s))
point_list.append(point([x + radius, 1, y], s))
- heap_point = max_heap(point_list)
+ heap_point = MaxHeap(point_list)
heap_point.heapsort()
- print heap_point
+ print(heap_point)
for p in heap_point:
if p[1] == 0:
s = p.disk
T.insert(s)
a = T.above(s)
b = T.below(s)
- print "insert: ", a, b
- if (a != None and disks_intersect(a, s)) or (b != None and disks_intersect(b, s)):
+ print("insert: ", a, b)
+ if (a is not None and disks_intersect(a, s)) or (b is not None and disks_intersect(b, s)):
return True
if p[1] == 1:
s = p.disk
a = T.above(s)
b = T.below(s)
- if a != None and b != None and disks_intersect(a, b):
+ if a is not None and b is not None and disks_intersect(a, b):
return True
T.delete(s)
return False
+
+
def disks_intersect(a, b):
- print a
- print b
+ print(a)
+ print(b)
a_x = a[0][0]
a_y = a[0][1]
a_r = a[1]
b_x = b[0][0]
b_y = b[0][1]
b_r = b[1]
- print (a_x - b_x) ** 2 + (a_y - b_y) ** 2
- print (a_r + b_r) ** 2
- if ((a_x - b_x) ** 2 + (a_y - b_y) ** 2) <= ((a_r + b_r) ** 2):
- return True
- else:
- return False
+ print((a_x - b_x) ** 2 + (a_y - b_y) ** 2)
+ print((a_r + b_r) ** 2)
+ return ((a_x - b_x) ** 2 + (a_y - b_y) ** 2) <= ((a_r + b_r) ** 2)
diff --git a/any_segments_intersect.py b/any_segments_intersect.py
index 4fc0d57..38762d4 100644
--- a/any_segments_intersect.py
+++ b/any_segments_intersect.py
@@ -1,15 +1,20 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
# we use 0 to mean red, 1 to mean black
from tree import Node, Tree
-from heap import max_heap
+from heap import MaxHeap
from segment_intersect import segments_intersect
+
def vertical(a):
return a[0][0] == a[1][0]
+
+
def comparable(a, b, x):
- '''Given two segments a and b that are comparable at x, determine whether a is above b or not. Assume that neither segment is vertical '''
+ """
+ Given two segments a and b that are comparable at x, determine whether a is above b or not. Assume that neither segment is vertical
+ """
p1 = a[0]
p2 = a[1]
p3 = b[0]
@@ -17,54 +22,44 @@ def comparable(a, b, x):
x4 = p4[0]
x3 = p3[0]
if vertical(a) and vertical(b):
- if p1[1] >= p3[1]:
- return True
- else:
- return False
+ return p1[1] >= p3[1]
elif vertical(a) and not vertical(b):
v1 = (p4[0] - p3[0], p4[1] - p3[1])
v2 = (p4[0] - p1[0], p4[1] - p1[1])
result = v1[0] * v2[1] - v2[0] * v1[1]
- # a is below b
- if result >= 0:
- return False
- # a is above b
- else:
- return True
+ return result < 0
elif not vertical(a) and vertical(b):
v1 = (p2[0] - p1[0], p2[1] - p1[1])
v2 = (p2[0] - p3[0], p2[1] - p3[1])
result = v1[0] * v2[1] - v2[0] * v1[1]
- # a is above b
- if result >= 0:
- return True
- # a is above b
- else:
- return False
+ return result >= 0
else:
v1 = (p2[0] - p1[0], p2[1] - p1[1])
- v2 = ((x4 - x3) * (p2[0] - p4[0]) + (x4 - x) * (p4[0] - p3[0]), (x4 - x3) * (p2[1] - p4[1]) + (x4 - x) * (p4[1] - p3[1]))
+ v2 = ((x4 - x3) * (p2[0] - p4[0]) + (x4 - x) * (p4[0] - p3[0]),
+ (x4 - x3) * (p2[1] - p4[1]) + (x4 - x) * (p4[1] - p3[1]))
result = v1[0] * v2[1] - v2[0] * v1[1]
- # a is above b
- if result >= 0:
- return True
- # a is below b
- else:
- return False
+ return result >= 0
+
+
class segment(tuple):
def __init__(self, seg):
super(segment, self).__init__(seg)
self.pointer = None
+
+
class point(list):
def __init__(self, info, segment):
super(point, self).__init__(info)
self.segment = segment
+
+
class rb_node(Node):
def __init__(self, key, p, left, right, color):
Node.__init__(self, key, p, left, right)
self.color = color
- if key != None:
+ if key is not None:
key.pointer = self
+
def minimum(self, nil):
x = self
y = x
@@ -72,16 +67,21 @@ def minimum(self, nil):
y = x
x = x.left
return y
+
def maximum(self, nil):
x = self
while x.right != nil:
x = x.right
return x
+
+
class rb_tree(Tree):
nil = rb_node(None, None, None, None, 1)
root = nil
+
def __init__(self):
pass
+
def above(self, s):
x = s.pointer
if x.right != self.nil:
@@ -90,6 +90,7 @@ def above(self, s):
while x.p != self.nil and x.p.right == x:
x = x.p
return x.p.key
+
def below(self, s):
x = s.pointer
if x.left != self.nil:
@@ -98,10 +99,13 @@ def below(self, s):
while x.p != self.nil and x.p.left == x:
x = x.p
return x.p.key
+
def minimum(self):
return self.root.minimum(self.nil)
+
def __getitem__(self, key):
return self.iterative_tree_search(key)
+
def left_rotate(self, x):
y = x.right
x.right = y.left
@@ -116,6 +120,7 @@ def left_rotate(self, x):
x.p.right = y
y.left = x
x.p = y
+
def right_rotate(self, y):
x = y.left
y.left = x.right
@@ -130,8 +135,11 @@ def right_rotate(self, y):
y.p.left = x
x.right = y
y.p = x
+
def insert(self, z):
- ''' the segment z will only be inserted when the left endpoint of z is being processed'''
+ """
+ the segment z will only be inserted when the left endpoint of z is being processed
+ """
# this is the x_coordinate of the left endpoint of z
x_coordinate = z[0][0]
z = rb_node(z, None, None, None, 0)
@@ -152,8 +160,9 @@ def insert(self, z):
z.p = y
z.left = self.nil
z.right = self.nil
- z.color = 0 #red
+ z.color = 0 # red
self.insert_fixed(z)
+
def insert_fixed(self, z):
while z.p.color == 0:
if z.p.p.left == z.p:
@@ -187,6 +196,7 @@ def insert_fixed(self, z):
z.color = 0
z.p.color = 1
self.root.color = 1
+
def transplant(self, u, v):
if u.p == self.nil:
self.root = v
@@ -195,6 +205,7 @@ def transplant(self, u, v):
else:
u.p.right = v
v.p = u.p
+
def delete(self, z):
z = z.pointer
y = z
@@ -221,6 +232,7 @@ def delete(self, z):
y.color = z.color
if y_original_color == 1:
self.delete_fixup(x)
+
def delete_fixup(self, x):
while x != self.root and x.color == 1:
if x == x.p.left:
@@ -266,17 +278,21 @@ def delete_fixup(self, x):
self.right_rotate(x.p)
x = self.root
x.color = 1
+
+
def any_segments_intersect(S):
- '''This algorithm takes as input a set S of n line segments, returning the boolean value TRUE if any pair of segments in S intersects, and FALSE otherwise.'''
+ """
+ This algorithm takes as input a set S of n line segments, returning the boolean value TRUE if any pair of segments in S intersects, and FALSE otherwise.
+ """
T = rb_tree()
segment_list = []
point_list = []
for s in S:
segment_list.append(segment(s))
for s in segment_list:
- point_list.append(point([s[0][0], 0, s[0][1]], s))
- point_list.append(point([s[1][0], 1, s[1][1]], s))
- heap_point = max_heap(point_list)
+ point_list.append(point([s[0][0], 0, s[0][1]], s))
+ point_list.append(point([s[1][0], 1, s[1][1]], s))
+ heap_point = MaxHeap(point_list)
heap_point.heapsort()
for p in heap_point:
if p[1] == 0:
@@ -284,17 +300,18 @@ def any_segments_intersect(S):
T.insert(s)
a = T.above(s)
b = T.below(s)
- if (a != None and segments_intersect(a[0], a[1], s[0], s[1])) or (b != None and segments_intersect(b[0], b[1], s[0], s[1])):
+ if (a is not None and segments_intersect(a[0], a[1], s[0], s[1])) or (
+ b is not None and segments_intersect(b[0], b[1], s[0], s[1])):
return True
if p[1] == 1:
s = p.segment
a = T.above(s)
b = T.below(s)
-# print a
-# print b
-# print type(a)
-# print type(b)
- if a != None and b != None and segments_intersect(a[0], a[1], b[0], b[1]):
+ # print( a)
+ # print( b)
+ # print( type(a))
+ # print( type(b))
+ if a is not None and b is not None and segments_intersect(a[0], a[1], b[0], b[1]):
return True
T.delete(s)
return False
diff --git a/automaton_string_match.py b/automaton_string_match.py
index 08c0d38..7de7ac1 100644
--- a/automaton_string_match.py
+++ b/automaton_string_match.py
@@ -1,4 +1,5 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
+
def finite_automaton_matcher(T, s, m):
n = len(T)
@@ -6,17 +7,21 @@ def finite_automaton_matcher(T, s, m):
for i in range(1, n + 1):
q = s[(q, T[i - 1])]
if q == m:
- print "Pattern occurs with shift {}".format(i - m)
+ print("Pattern occurs with shift {}".format(i - m))
+
+
def compute_transition_function(P, domain):
m = len(P)
s = dict()
for a in domain:
- for q in range(0, m + 1):
+ for q in range(m + 1):
k = min(q + 1, m)
while not (P[0:q] + a).endswith(P[0:k]):
k = k - 1
s[(q, a)] = k
return s
+
+
def automaton_string_match(P, T, domain):
s = compute_transition_function(P, domain)
m = len(P)
diff --git a/b_tree_test.py b/b_tree_example.py
similarity index 69%
rename from b_tree_test.py
rename to b_tree_example.py
index 92f321a..96c3644 100755
--- a/b_tree_test.py
+++ b/b_tree_example.py
@@ -1,32 +1,32 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-import b_tree as bt
+import btree as bt
-a = bt.b_tree_node(3, True, 2)
+a = bt.BTreeNode(3, True, 2)
a.key[0] = 'A'
a.key[1] = 'B'
-b = bt.b_tree_node(3, True, 3)
+b = bt.BTreeNode(3, True, 3)
b.key[0] = 'D'
b.key[1] = 'E'
b.key[2] = 'F'
-c = bt.b_tree_node(3, True, 3)
+c = bt.BTreeNode(3, True, 3)
c.key[0] = 'J'
c.key[1] = 'K'
c.key[2] = 'L'
-d = bt.b_tree_node(3, True, 2)
+d = bt.BTreeNode(3, True, 2)
d.key[0] = 'N'
d.key[1] = 'O'
-x = bt.b_tree_node(3, True, 3)
+x = bt.BTreeNode(3, True, 3)
x.key[0] = 'Q'
x.key[1] = 'R'
x.key[2] = 'S'
-y = bt.b_tree_node(3, True, 2)
+y = bt.BTreeNode(3, True, 2)
y.key[0] = 'U'
y.key[1] = 'V'
-z = bt.b_tree_node(3, True, 2)
+z = bt.BTreeNode(3, True, 2)
z.key[0] = 'Y'
z.key[1] = 'Z'
-e = bt.b_tree_node(3, False, 3)
+e = bt.BTreeNode(3, False, 3)
e.key[0] = 'C'
e.key[1] = 'G'
e.key[2] = 'M'
@@ -34,13 +34,13 @@
e.c[1] = b
e.c[2] = c
e.c[3] = d
-v = bt.b_tree_node(3, False, 2)
+v = bt.BTreeNode(3, False, 2)
v.key[0] = 'T'
v.key[1] = 'X'
v.c[0] = x
v.c[1] = y
v.c[2] = z
-t = bt.b_tree(3)
+t = bt.BTree(3)
t.root.key[0] = 'P'
t.root.c[0] = e
t.root.c[1] = v
@@ -48,25 +48,25 @@
t.root.leaf = False
t.root.delete(t, 'F')
t.root.print_child_first()
-print
+print()
t.root.delete(t, 'M')
t.root.print_child_first()
-print
+print()
t.root.delete(t, 'G')
t.root.print_child_first()
-print
+print()
t.root.delete(t, 'D')
t.root.print_child_first()
-print
+print()
t.root.delete(t, 'B')
t.root.print_child_first()
-print
+print()
t.root.delete(t, 'C')
t.root.print_child_first()
-print
+print()
t.root.delete(t, 'P')
t.root.print_child_first()
-print
+print()
t.root.delete(t, 'V')
t.root.print_child_first()
-print
+print()
diff --git a/bh_tree.py b/bh_tree.py
index 75f5ac2..6bbf5f6 100644
--- a/bh_tree.py
+++ b/bh_tree.py
@@ -1,21 +1,26 @@
# A variant of red black tree that has black_height attribute
-#!/usr/bin/env ipython
+# !/usr/bin/env python
-from rb_tree import rb_node, rb_tree
+from rb_tree import RbNode, RbTree
-class bh_node(rb_node):
+
+class bh_node(RbNode):
def __init__(self, key, p, left, right, color, bh):
- rb_node.__init__(self, key, p, left, right, color)
+ RbNode.__init__(self, key, p, left, right, color)
self.bh = bh
-class bh_tree(rb_tree):
+
+
+class bh_tree(RbTree):
nil = bh_node(None, None, None, None, 1, 0)
root = nil
+
def __init__(self, values):
if isinstance(values, list):
for i in values:
self.insert(bh_node(i, None, None, None, 0, 1))
else:
- print "Not invalid argument"
+ print("Not invalid argument")
+
def insert_fixed(self, z):
while z.p.color == 0:
if z.p.p.left == z.p:
@@ -51,6 +56,7 @@ def insert_fixed(self, z):
z.color = 0
z.p.color = 1
self.root.color = 1
+
def delete_fixup(self, x):
while x != self.root and x.color == 1:
if x == x.p.left:
diff --git a/binary_add.py b/binary_add.py
new file mode 100644
index 0000000..92aabdd
--- /dev/null
+++ b/binary_add.py
@@ -0,0 +1,23 @@
+#!/usr/bin/env python
+# encoding: utf-8
+
+
+def binary_add(array1, array2):
+ """
+ Consider the problem of adding two n-bit binary integers, stored in two n-element arrays A and B,
+ in big-endian order.
+ The sum of the two integers should be stored in binary form in a (n + 1)-element array C.
+ :param array1: n-element array A
+ :param array2: n-element array B
+ :return: (n + 1)-element array C
+ """
+ assert len(array1) == len(array2)
+ n = len(array1)
+ promote = 0
+ array3 = [0] * (n + 1)
+ for i in range(n - 1, -1, -1):
+ result = array1[i] + array2[i] + promote
+ promote = result // 2
+ array3[i + 1] = result % 2
+ array3[0] = promote
+ return array3
diff --git a/binary_search.py b/binary_search.py
new file mode 100644
index 0000000..f61f7b2
--- /dev/null
+++ b/binary_search.py
@@ -0,0 +1,74 @@
+def binary_search(target, array):
+ """
+ find target in sorted array.
+ If found, return the index, otherwise return -1.
+ :param target:
+ :param array: list
+ :return:
+ """
+ low = 0
+ high = len(array) - 1
+ while low <= high:
+ mid = (low + high) // 2
+ if target < array[mid]:
+ high = mid - 1
+ elif target > array[mid]:
+ low = mid + 1
+ else:
+ return mid
+ return -1
+
+
+def bisect_left(array, x, low=0, high=None):
+ """
+ Locate the insertion point for x in a to maintain sorted order.
+ If x is already present in a,
+ the insertion point will be before (to the left of) any existing entries.
+ The return value is suitable for use as the first parameter to list.insert() assuming that a is already sorted.
+ Optional args lo (default 0) and hi (default len(a)) bound the
+ slice of a to be searched.
+
+ :param array: sorted list
+ :param x:
+ :param low:
+ :param high:
+ :return:
+ """
+ if high is None:
+ high = len(array)
+ assert low <= high
+ while low < high:
+ mid = (low + high) // 2
+ if array[mid] < x:
+ low = mid + 1
+ else:
+ high = mid
+ return low
+
+
+def bisect_right(array, x, low=0, high=None):
+ """
+ Return the index where to insert item x in list a, assuming a is sorted.
+
+ The return value i is such that all e in a[:i] have e <= x, and all e in
+ a[i:] have e > x. So if x already appears in the list, a.insert(x) will
+ insert just after the rightmost x already there.
+
+ Optional args lo (default 0) and hi (default len(a)) bound the
+ slice of a to be searched.
+ :param array:
+ :param x:
+ :param low:
+ :param high:
+ :return:
+ """
+ if high is None:
+ high = len(array)
+ assert low <= high
+ while low < high:
+ mid = (low + high) // 2
+ if array[mid] <= x:
+ low = mid + 1
+ else:
+ high = mid
+ return low
diff --git a/binary_counter.py b/binarycounter.py
similarity index 74%
rename from binary_counter.py
rename to binarycounter.py
index b729ccf..e95701a 100644
--- a/binary_counter.py
+++ b/binarycounter.py
@@ -1,7 +1,8 @@
-class binary_counter(list):
+class BinaryCounter(list):
def __init__(self, size):
self.leftmost_1 = -1
- list.__init__(self, [0] * size)
+ super(BinaryCounter, self).__init__([0] * size)
+
def increment(self):
i = 0
while i < len(self) and self[i] == 1:
@@ -13,9 +14,11 @@ def increment(self):
self.leftmost_1 = i
else:
self.leftmost_1 = -1
+
def reset(self):
- for i in range(0, self.leftmost_1 + 1):
+ for i in range(self.leftmost_1 + 1):
self[i] = 0
self.leftmost_1 = -1
+
def print_bits(self):
- print self[::-1]
+ print(self[::-1])
diff --git a/binsearch.c b/binsearch.c
deleted file mode 100644
index 8f9c9f8..0000000
--- a/binsearch.c
+++ /dev/null
@@ -1,25 +0,0 @@
-#include
-/* binsearch: find x in v[0] <= v[1] <= ... <= v[n-1] */
-int binsearch(int x, int v[], int n) {
- int low, high, mid;
-
- low = 0;
- high = n - 1;
- while (low <= high) {
- mid = (high + low)/2;
- if (x < v[mid])
- high = mid - 1;
- else if (x > v[mid])
- low = mid + 1;
- else /* found match */
- return mid;
- }
- return -1; /* no match */
-}
-
-void main() {
- int A[10] = {0,1,2,3,4,5,6,7,8,9};
-
- printf("%d\n", binsearch(9, A, 10));
-}
-
diff --git a/b_tree.py b/btree.py
similarity index 81%
rename from b_tree.py
rename to btree.py
index e181b40..7bd91a1 100644
--- a/b_tree.py
+++ b/btree.py
@@ -1,16 +1,18 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-class b_tree_node(object):
+
+class BTreeNode:
def __init__(self, t, leaf, n):
self.leaf = leaf
self.n = n
self.t = t
self.key = [0] * (2 * t - 1)
self.c = [0] * (2 * t)
+
def split_child(self, i):
y = self.c[i - 1]
t = y.t
- z = b_tree_node(t, y.leaf, t - 1)
+ z = BTreeNode(t, y.leaf, t - 1)
for j in range(1, t):
z.key[j - 1] = y.key[j + t - 1]
if not y.leaf:
@@ -21,9 +23,10 @@ def split_child(self, i):
self.c[j] = self.c[j - 1]
self.c[i] = z
for j in range(self.n, i - 1, -1):
- self.key[j] = self.key[j -1]
+ self.key[j] = self.key[j - 1]
self.key[i - 1] = y.key[t - 1]
self.n = self.n + 1
+
def insert_nonfull(self, k):
i = self.n
t = self.t
@@ -42,31 +45,35 @@ def insert_nonfull(self, k):
if k > self.key[i - 1]:
i = i + 1
self.c[i - 1].insert_nonfull(k)
+
def search(self, k):
i = 1
while i <= self.n and k > self.key[i - 1]:
i = i + 1
if i <= self.n and k == self.key[i - 1]:
- return (self, i)
+ return self, i
elif self.leaf:
return None
else:
return self.c[i - 1].search(k)
+
def print_inorder(self):
if self.leaf:
for i in range(1, self.n + 1):
- print self.key[i - 1],
+ print(self.key[i - 1], )
else:
for i in range(1, self.n + 1):
self.c[i - 1].print_inorder()
- print self.key[i - 1],
+ print(self.key[i - 1], )
self.c[self.n].print_inorder()
+
def print_child_first(self):
if not self.leaf:
for i in range(1, self.n + 2):
self.c[i - 1].print_child_first()
for i in range(1, self.n + 1):
- print self.key[i - 1],
+ print(self.key[i - 1], )
+
def delete(self, tree, k):
t = self.t
i = 1
@@ -133,7 +140,8 @@ def delete(self, tree, k):
self.merge(tree, i - 1)
self.c[i - 2].delete(tree, k)
else:
- self.c[i - 1].delete(tree, k)
+ self.c[i - 1].delete(tree, k)
+
def merge(self, tree, i):
y = self.c[i - 1]
z = self.c[i]
@@ -154,49 +162,54 @@ def merge(self, tree, i):
self.n = self.n - 1
if tree.root == self and self.n == 0:
tree.root = y
-class b_tree(object):
+
+
+class BTree:
def __init__(self, t):
self.t = t
- self.root = b_tree_node(t, True, 0)
+ self.root = BTreeNode(t, True, 0)
+
def insert(self, k):
r = self.root
t = self.t
if r.n == 2 * t - 1:
- s = b_tree_node(t, False, 0)
+ s = BTreeNode(t, False, 0)
self.root = s
s.c[0] = r
s.split_child(1)
s.insert_nonfull(k)
else:
r.insert_nonfull(k)
+
def print_b_tree(self):
r = self.root
r.print_inorder()
-# def predecessor(self, k):
-# m = []
-# x = self.root
-# while not x.leaf:
-# i = 1
-# while i <= x.n and k > x.key[i - 1]:
-# i = i + 1
-# if i <= x.n and k == x.key[i - 1]:
-# x = x.c[i - 1]
-# while not x.leaf:
-# x = x.c[x.n]
-# return x.key[x.n - 1]
-# else:
-# x = x.c[i - 1]
-# if i > 1:
-# m.append(x.key[i - 1])
-# i = 1
-# while i <= x.n and k != x.key[i - 1]:
-# i = i + 1
-# if i > x.n or len(m) == 0:
-# return None
-# elif i > 1:
-# return x.key[i - 2]
-# else:
-# return max(m)
+
+ # def predecessor(self, k):
+ # m = []
+ # x = self.root
+ # while not x.leaf:
+ # i = 1
+ # while i <= x.n and k > x.key[i - 1]:
+ # i = i + 1
+ # if i <= x.n and k == x.key[i - 1]:
+ # x = x.c[i - 1]
+ # while not x.leaf:
+ # x = x.c[x.n]
+ # return x.key[x.n - 1]
+ # else:
+ # x = x.c[i - 1]
+ # if i > 1:
+ # m.append(x.key[i - 1])
+ # i = 1
+ # while i <= x.n and k != x.key[i - 1]:
+ # i = i + 1
+ # if i > x.n or len(m) == 0:
+ # return None
+ # elif i > 1:
+ # return x.key[i - 2]
+ # else:
+ # return max(m)
def predecessor(self, k):
s = []
x = self.root
diff --git a/bubble_sort.py b/bubble_sort.py
new file mode 100644
index 0000000..f9d6ae6
--- /dev/null
+++ b/bubble_sort.py
@@ -0,0 +1,11 @@
+def bubble_sort(array):
+ """
+ O(n ^ 2) inplace sort
+ :param array: list
+ :return:
+ """
+ n = len(array)
+ for i in range(n):
+ for j in range(n - 1, i, -1):
+ if array[j] < array[j - 1]:
+ array[j], array[j - 1] = array[j - 1], array[j]
diff --git a/closest_points.py b/closest_points.py
index e61bccb..2ad5163 100644
--- a/closest_points.py
+++ b/closest_points.py
@@ -1,35 +1,46 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
from math import ceil, sqrt
-from heap import max_heap
+from heap import MaxHeap
+
def x_sort(S):
- X = max_heap(S)
+ X = MaxHeap(S)
X.heapsort()
return X
+
+
def y_sort(S):
Y = []
for p in S:
Y.append((p[1], p[0]))
- YY = max_heap(Y)
+ YY = MaxHeap(Y)
YY.heapsort()
Y = []
- for i in range(0, len(YY)):
+ for i in range(len(YY)):
Y.append((YY[i][1], YY[i][0]))
return Y
+
+
def distance(p1, p2):
return sqrt((p1[0] - p2[0]) ** 2 + (p1[1] - p2[1]) ** 2)
+
+
def brute_force(P):
P = list(P)
d = float("Inf")
- for i in range(0, len(P)):
+ for i in range(len(P)):
for j in range(i + 1, len(P)):
d = min(d, distance(P[i], P[j]))
return d
+
+
def closest_points(S):
X = x_sort(S)
Y = y_sort(S)
return closest_points_aux(S, X, Y)
+
+
def closest_points_aux(P, X, Y):
length = len(P)
half = int(ceil(length / 2))
@@ -42,7 +53,7 @@ def closest_points_aux(P, X, Y):
l = X[half - 1][0]
YL = []
YR = []
- for i in range(0, len(Y)):
+ for i in range(len(Y)):
if Y[i] in PL:
YL.append(Y[i])
else:
@@ -51,11 +62,11 @@ def closest_points_aux(P, X, Y):
dr = closest_points_aux(PR, XR, YR)
d1 = min(dl, dr)
YY = []
- for i in range(0, len(Y)):
+ for i in range(len(Y)):
if abs(Y[i][0] - l) < d1:
YY.append(Y[i])
d2 = float("Inf")
- for i in range(0, len(YY)):
+ for i in range(len(YY)):
for j in range(1, 10):
if i + j < len(YY):
d2 = min(distance(YY[i], YY[i + j]), d2)
diff --git a/closest_points_l1_distance.py b/closest_points_l1_distance.py
index 25361d5..35b8817 100644
--- a/closest_points_l1_distance.py
+++ b/closest_points_l1_distance.py
@@ -1,35 +1,46 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
from math import ceil, sqrt
-from heap import max_heap
+from heap import MaxHeap
+
def x_sort(S):
- X = max_heap(S)
+ X = MaxHeap(S)
X.heapsort()
return X
+
+
def y_sort(S):
Y = []
for p in S:
Y.append((p[1], p[0]))
- YY = max_heap(Y)
+ YY = MaxHeap(Y)
YY.heapsort()
Y = []
- for i in range(0, len(YY)):
+ for i in range(len(YY)):
Y.append((YY[i][1], YY[i][0]))
return Y
+
+
def distance(p1, p2):
return abs(p1[0] - p2[0]) + abs(p1[1] - p2[1])
+
+
def brute_force(P):
P = list(P)
d = float("Inf")
- for i in range(0, len(P)):
+ for i in range(len(P)):
for j in range(i + 1, len(P)):
d = min(d, distance(P[i], P[j]))
return d
+
+
def closest_points(S):
X = x_sort(S)
Y = y_sort(S)
return closest_points_aux(S, X, Y)
+
+
def closest_points_aux(P, X, Y):
length = len(P)
half = int(ceil(length / 2))
@@ -42,7 +53,7 @@ def closest_points_aux(P, X, Y):
l = X[half - 1][0]
YL = []
YR = []
- for i in range(0, len(Y)):
+ for i in range(len(Y)):
if Y[i] in PL:
YL.append(Y[i])
else:
@@ -51,11 +62,11 @@ def closest_points_aux(P, X, Y):
dr = closest_points_aux(PR, XR, YR)
d1 = min(dl, dr)
YY = []
- for i in range(0, len(Y)):
+ for i in range(len(Y)):
if abs(Y[i][0] - l) < d1:
YY.append(Y[i])
d2 = float("Inf")
- for i in range(0, len(YY)):
+ for i in range(len(YY)):
for j in range(1, 10):
if i + j < len(YY):
d2 = min(distance(YY[i], YY[i + j]), d2)
diff --git a/closest_points_l_infinite_distance.py b/closest_points_l_infinite_distance.py
index 0b1e1fc..a99b692 100644
--- a/closest_points_l_infinite_distance.py
+++ b/closest_points_l_infinite_distance.py
@@ -1,35 +1,46 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
from math import ceil, sqrt
-from heap import max_heap
+from heap import MaxHeap
+
def x_sort(S):
- X = max_heap(S)
+ X = MaxHeap(S)
X.heapsort()
return X
+
+
def y_sort(S):
Y = []
for p in S:
Y.append((p[1], p[0]))
- YY = max_heap(Y)
+ YY = MaxHeap(Y)
YY.heapsort()
Y = []
- for i in range(0, len(YY)):
+ for i in range(len(YY)):
Y.append((YY[i][1], YY[i][0]))
return Y
+
+
def distance(p1, p2):
return max(abs(p1[0] - p2[0]), abs(p1[1] - p2[1]))
+
+
def brute_force(P):
P = list(P)
d = float("Inf")
- for i in range(0, len(P)):
+ for i in range(len(P)):
for j in range(i + 1, len(P)):
d = min(d, distance(P[i], P[j]))
return d
+
+
def closest_points(S):
X = x_sort(S)
Y = y_sort(S)
return closest_points_aux(S, X, Y)
+
+
def closest_points_aux(P, X, Y):
length = len(P)
half = int(ceil(length / 2))
@@ -42,7 +53,7 @@ def closest_points_aux(P, X, Y):
l = X[half - 1][0]
YL = []
YR = []
- for i in range(0, len(Y)):
+ for i in range(len(Y)):
if Y[i] in PL:
YL.append(Y[i])
else:
@@ -51,11 +62,11 @@ def closest_points_aux(P, X, Y):
dr = closest_points_aux(PR, XR, YR)
d1 = min(dl, dr)
YY = []
- for i in range(0, len(Y)):
+ for i in range(len(Y)):
if abs(Y[i][0] - l) < d1:
YY.append(Y[i])
d2 = float("Inf")
- for i in range(0, len(YY)):
+ for i in range(len(YY)):
for j in range(1, 7):
if i + j < len(YY):
d2 = min(distance(YY[i], YY[i + j]), d2)
diff --git a/common-matrix-multiply-Strassen.py b/common-matrix-multiply-Strassen.py
index 74effb5..61a0424 100644
--- a/common-matrix-multiply-Strassen.py
+++ b/common-matrix-multiply-Strassen.py
@@ -6,15 +6,17 @@
# EMAIL: cntqrxj@gmail.com
from numpy import *
+from square_matrix_multiply_Strassen import square_matrix_multiply
+
def common_matrix_multiply(A, B):
- if (A.shape[1] != B.shape[0]):
- print "The width of matrix A not equal the height of matrix B.\nHence no matrix multiplication allowed"
+ if A.shape[1] != B.shape[0]:
+ print("The width of matrix A not equal the height of matrix B.\nHence no matrix multiplication allowed")
return
- shape = (A.shape[0], B.shape[1])
- #shape = A.shape
- #length = shape[0]
- #half = length / 2
+ shape = A.shape[0], B.shape[1]
+ # shape = A.shape
+ length = shape[0]
+ half = length / 2
A_width = A.shape[1]
B_width = B.shape[1]
A_height = A.shape[0]
@@ -23,32 +25,32 @@ def common_matrix_multiply(A, B):
half_A_height = A_height / 2
half_B_width = B_width / 2
half_B_height = B_height / 2
-
- C = zeros(shape, dtype = int64)
+
+ C = zeros(shape, dtype=int64)
if A_height == 1 or B_width == 1:
- C = dot(A, B)
- #if length == 1:
+ C = dot(A, B)
+ # if length == 1:
# C[0, 0] = A[0, 0] * B[0, 0]
# return C
-
- S1 = zeros((half, half), dtype = int64)
- S2 = zeros((half, half), dtype = int64)
- S3 = zeros((half, half), dtype = int64)
- S4 = zeros((half, half), dtype = int64)
- S5 = zeros((half, half), dtype = int64)
- S6 = zeros((half, half), dtype = int64)
- S7 = zeros((half, half), dtype = int64)
- S8 = zeros((half, half), dtype = int64)
- S9 = zeros((half, half), dtype = int64)
- S10 = zeros((half, half), dtype = int64)
- P1 = zeros((half, half), dtype = int64)
- P2 = zeros((half, half), dtype = int64)
- P3 = zeros((half, half), dtype = int64)
- P4 = zeros((half, half), dtype = int64)
- P5 = zeros((half, half), dtype = int64)
- P6 = zeros((half, half), dtype = int64)
- P7 = zeros((half, half), dtype = int64)
+ S1 = zeros((half, half), dtype=int64)
+ S2 = zeros((half, half), dtype=int64)
+ S3 = zeros((half, half), dtype=int64)
+ S4 = zeros((half, half), dtype=int64)
+ S5 = zeros((half, half), dtype=int64)
+ S6 = zeros((half, half), dtype=int64)
+ S7 = zeros((half, half), dtype=int64)
+ S8 = zeros((half, half), dtype=int64)
+ S9 = zeros((half, half), dtype=int64)
+ S10 = zeros((half, half), dtype=int64)
+
+ P1 = zeros((half, half), dtype=int64)
+ P2 = zeros((half, half), dtype=int64)
+ P3 = zeros((half, half), dtype=int64)
+ P4 = zeros((half, half), dtype=int64)
+ P5 = zeros((half, half), dtype=int64)
+ P6 = zeros((half, half), dtype=int64)
+ P7 = zeros((half, half), dtype=int64)
S1 = B[0:half, half:length] - B[half:length, half:length]
S2 = A[0:half, 0:half] + A[0:half, half:length]
@@ -68,22 +70,22 @@ def common_matrix_multiply(A, B):
P5 = square_matrix_multiply(S5, S6)
P6 = square_matrix_multiply(S7, S8)
P7 = square_matrix_multiply(S9, S10)
-
+
C[0:half, 0:half] = P5 + P4 - P2 + P6
C[0:half, half:length] = P1 + P2
C[half:length, 0:half] = P3 + P4
C[half:length, half:length] = P5 + P1 - P3 - P7
-
- return C
-#A = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
-#B = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
-#A = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
-#B = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
+ return C
+
+
+# A = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
+# B = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
+# A = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
+# B = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
A = array([[1, 3], [7, 5]])
B = array([[6, 8], [4, 2]])
-#A = array([[1, 2, 3], [4, 5, 6]])
-#B = array([[1, 2], [4, 5]])
-print square_matrix_multiply(A, B)
-#print dot(A, B)
-
+# A = array([[1, 2, 3], [4, 5, 6]])
+# B = array([[1, 2], [4, 5]])
+print(square_matrix_multiply(A, B))
+# print( dot(A, B))
diff --git a/common-matrix-multiply-recursive.py b/common-matrix-multiply-recursive.py
index 11ea7f6..534e534 100755
--- a/common-matrix-multiply-recursive.py
+++ b/common-matrix-multiply-recursive.py
@@ -1,18 +1,14 @@
#! /usr/bin/python2.7
-# AUTHOR: WangQiang
-# CREATE DATE: 20140528
-# LAST UPDATE DATE: 20140603
-# EMAIL: cntqrxj@gmail.com
-
from numpy import *
+
def common_matrix_multiply(A, B):
- if (A.shape[1] != B.shape[0]):
- print "The width of matrix A not equal the height of matrix B.\nHence no matrix multiplication allowed"
+ if A.shape[1] != B.shape[0]:
+ print("The width of matrix A not equal the height of matrix B.\nHence no matrix multiplication allowed")
return
shape = (A.shape[0], B.shape[1])
- C = zeros(shape, dtype = int64)
+ C = zeros(shape, dtype=int64)
A_width = A.shape[1]
B_width = B.shape[1]
A_height = A.shape[0]
@@ -22,20 +18,33 @@ def common_matrix_multiply(A, B):
half_B_width = B_width / 2
half_B_height = B_height / 2
if A_height == 1 or B_width == 1:
- C = dot(A, B)
-# else if
+ C = dot(A, B)
+ # else if
else:
- C[0:half_A_height, 0:half_B_width] = common_matrix_multiply(A[0:half_A_height, 0:half_A_width], B[0:half_B_height, 0:half_B_width]) + common_matrix_multiply(A[0:half_A_height, half_A_width:A_width], B[half_B_height:B_height, 0:half_B_width])
- C[0:half_A_height, half_B_width:B_width] = common_matrix_multiply(A[0:half_A_height, 0:half_A_width], B[0:half_B_height, half_B_width:B_width]) + common_matrix_multiply(A[0:half_A_height, half_A_width:A_width], B[half_B_height:B_height, half_B_width:B_width])
- C[half_A_height:A_height, 0:half_B_width] = common_matrix_multiply(A[half_A_height:A_height, 0:half_A_width], B[0:half_B_height, 0:half_B_width]) + common_matrix_multiply(A[half_A_height:A_height, half_A_width:A_width], B[half_B_height:B_height, 0:half_B_width])
- C[half_A_height:A_height, half_B_width:B_width] = common_matrix_multiply(A[half_A_height:A_height, 0:half_A_width], B[0:half_B_height,half_B_width:B_width]) + common_matrix_multiply(A[half_A_height:A_height, half_A_width:A_width], B[half_B_height:B_height, half_B_width:B_width])
+ C[0:half_A_height, 0:half_B_width] = common_matrix_multiply(A[0:half_A_height, 0:half_A_width],
+ B[0:half_B_height,
+ 0:half_B_width]) + common_matrix_multiply(
+ A[0:half_A_height, half_A_width:A_width], B[half_B_height:B_height, 0:half_B_width])
+ C[0:half_A_height, half_B_width:B_width] = common_matrix_multiply(A[0:half_A_height, 0:half_A_width],
+ B[0:half_B_height,
+ half_B_width:B_width]) + common_matrix_multiply(
+ A[0:half_A_height, half_A_width:A_width], B[half_B_height:B_height, half_B_width:B_width])
+ C[half_A_height:A_height, 0:half_B_width] = common_matrix_multiply(A[half_A_height:A_height, 0:half_A_width],
+ B[0:half_B_height,
+ 0:half_B_width]) + common_matrix_multiply(
+ A[half_A_height:A_height, half_A_width:A_width], B[half_B_height:B_height, 0:half_B_width])
+ C[half_A_height:A_height, half_B_width:B_width] = common_matrix_multiply(
+ A[half_A_height:A_height, 0:half_A_width],
+ B[0:half_B_height, half_B_width:B_width]) + common_matrix_multiply(
+ A[half_A_height:A_height, half_A_width:A_width], B[half_B_height:B_height, half_B_width:B_width])
return C
-
+
+
A = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
B = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
-#A = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
-#B = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
-#A = array([[1, 2, 3], [4, 5, 6]])
-#B = array([[1, 2], [4, 5]])
-print common_matrix_multiply(A, B)
-#print dot(A, B)
+# A = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
+# B = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
+# A = array([[1, 2, 3], [4, 5, 6]])
+# B = array([[1, 2], [4, 5]])
+print(common_matrix_multiply(A, B))
+# print( dot(A, B))
diff --git a/comparable.py b/comparable.py
index 85998b8..87307e1 100644
--- a/comparable.py
+++ b/comparable.py
@@ -1,7 +1,9 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
def comparable(a, b, x):
- '''Given two segments a and b that are comparable at x, determine whether a is above b or not. Assume that neither segment is vertical '''
+ """
+ Given two segments a and b that are comparable at x, determine whether a is above b or not. Assume that neither segment is vertical
+ """
p1 = a[0]
p2 = a[1]
@@ -10,11 +12,13 @@ def comparable(a, b, x):
x4 = p4[0]
x3 = p3[0]
v1 = (p2[0] - p1[0], p2[1] - p1[1])
- v2 = ((x4 - x3) * (p2[0] - p4[0]) + (x4 - x) * (p4[0] - p3[0]), (x4 - x3) * (p2[1] - p4[1]) + (x4 - x) * (p4[1] - p3[1]))
+ v2 = (
+ (x4 - x3) * (p2[0] - p4[0]) + (x4 - x) * (p4[0] - p3[0]),
+ (x4 - x3) * (p2[1] - p4[1]) + (x4 - x) * (p4[1] - p3[1]))
result = v1[0] * v2[1] - v2[0] * v1[1]
if result == 0:
- print "a intersects b at the vertical line"
+ print("a intersects b at the vertical line")
elif result > 0:
- print "a is above b"
+ print("a is above b")
else:
- print "b is above a"
+ print("b is above a")
diff --git a/constraints.py b/constraints.py
index 631dd6e..3bd6d6c 100644
--- a/constraints.py
+++ b/constraints.py
@@ -1,35 +1,40 @@
from graph import Vertex, Graph
from random import sample
+
def Bellman_Ford(G, w, s):
- '''A variant to the original Bellman_Ford algorithm
+ """A variant to the original Bellman_Ford algorithm
that we use to solve a system of difference constraints
with m inequalities on n unknowns. The running time is
O(nm), faster than O(n * n + nm) of the original Bellman-Ford
algorithm.
- '''
+ """
edges = G.edges - set([(s, v) for v in G.adj[s]])
G.initialize_signle_source(s)
j = 1
for i in range(1, len(G.vertices)):
if j == 1:
- for u,v in G.edges:
+ for u, v in G.edges:
G.relax(u, v, w)
else:
- for u,v in edges:
+ for u, v in edges:
G.relax(u, v, w)
j = j + 1
- for u,v in G.edges:
+ for u, v in G.edges:
if v.d > u.d + w(u, v):
return False
return True
+
+
def initialize_signle_source(self, s):
for v in self.vertices:
v.d = float("Inf")
v.p = None
s.d = 0
+
+
def difference_constraints(A, b):
- '''A algorithm to solve a system of difference constraints Ax <= b
+ """A algorithm to solve a system of difference constraints Ax <= b
by solving a single-source shortest-paths problem using Bellman-Ford
algorithm. Each row of the linear-programming matrix A contains
one 1 and one 1, and all other entries of A are 0.
@@ -37,7 +42,7 @@ def difference_constraints(A, b):
Calling convention: A is a two-dimensional list, b is a list.
Return value: This function returns a list representing x if
there exists feasible solution; otherwise, this function returns None.
- '''
+ """
row = len(A)
col = len(A[0])
@@ -45,14 +50,14 @@ def difference_constraints(A, b):
vertices = []
edges = []
weights = dict()
- for i in range(0, vertices_num + 1):
+ for i in range(vertices_num + 1):
vertices.append(Vertex(i))
for i in range(1, vertices_num + 1):
edges.append((vertices[0], vertices[i]))
weights[(vertices[0], vertices[i])] = 0
- for i in range(0, row):
- u = A[i].index(-1) + 1
- v = A[i].index(1) + 1
+ for i in range(row):
+ u = A[i].index(-1) + 1
+ v = A[i].index(1) + 1
edges.append((vertices[u], vertices[v]))
weights[(vertices[u], vertices[v])] = b[i]
G = Graph(vertices, edges)
@@ -60,26 +65,28 @@ def difference_constraints(A, b):
return [v.d for v in vertices[1:]]
else:
return None
+
+
def difference_constraints_with_arbitrary_weight(A, b):
- ''' An variant to the above difference constraints function
+ """ An variant to the above difference constraints function
that the weight of the edge from the auxiliary vertex to any
other vertex can be arbitrary value.
- '''
+ """
row = len(A)
col = len(A[0])
vertices_num = col
vertices = []
edges = []
weights = dict()
- distribute = sample(xrange(-10, 10), vertices_num)
- for i in range(0, vertices_num + 1):
+ distribute = sample(range(-10, 10), vertices_num)
+ for i in range(vertices_num + 1):
vertices.append(Vertex(i))
for i in range(1, vertices_num + 1):
edges.append((vertices[0], vertices[i]))
weights[(vertices[0], vertices[i])] = distribute[i - 1]
- for i in range(0, row):
- u = A[i].index(-1) + 1
- v = A[i].index(1) + 1
+ for i in range(row):
+ u = A[i].index(-1) + 1
+ v = A[i].index(1) + 1
edges.append((vertices[u], vertices[v]))
weights[(vertices[u], vertices[v])] = b[i]
G = Graph(vertices, edges)
@@ -87,6 +94,8 @@ def difference_constraints_with_arbitrary_weight(A, b):
return [v.d for v in vertices[1:]]
else:
return None
+
+
def equality_constraints(A, b):
row = len(A)
col = len(A[0])
@@ -94,14 +103,14 @@ def equality_constraints(A, b):
vertices = []
edges = []
weights = dict()
- for i in range(0, vertices_num + 1):
+ for i in range(vertices_num + 1):
vertices.append(Vertex(i))
for i in range(1, vertices_num + 1):
edges.append((vertices[0], vertices[i]))
weights[(vertices[0], vertices[i])] = 0
- for i in range(0, row):
- u = A[i].index(-1) + 1
- v = A[i].index(1) + 1
+ for i in range(row):
+ u = A[i].index(-1) + 1
+ v = A[i].index(1) + 1
edges.append((vertices[u], vertices[v]))
weights[(vertices[u], vertices[v])] = b[i]
edges.append((vertices[v], vertices[u]))
@@ -111,6 +120,8 @@ def equality_constraints(A, b):
return [v.d for v in vertices[1:]]
else:
return None
+
+
def difference_constraints_without_aux_vertex(A, b):
row = len(A)
col = len(A[0])
@@ -120,9 +131,9 @@ def difference_constraints_without_aux_vertex(A, b):
weights = dict()
for i in range(vertices_num):
vertices.append(Vertex(i + 1))
- for i in range(0, row):
- u = A[i].index(-1)
- v = A[i].index(1)
+ for i in range(row):
+ u = A[i].index(-1)
+ v = A[i].index(1)
edges.append((vertices[u], vertices[v]))
weights[(vertices[u], vertices[v])] = b[i]
G = Graph(vertices, edges)
@@ -130,19 +141,25 @@ def difference_constraints_without_aux_vertex(A, b):
return [v.d for v in vertices]
else:
return None
+
+
def Bellman_Ford_without_aux_vertex(G, w):
initialize_signle_source_without_aux_vertex(G)
for i in range(1, len(G.vertices)):
- for u,v in G.edges:
+ for u, v in G.edges:
G.relax(u, v, w)
- for u,v in G.edges:
+ for u, v in G.edges:
if v.d > u.d + w(u, v):
return False
return True
+
+
def initialize_signle_source_without_aux_vertex(G):
for v in G.vertices:
v.d = 0
v.p = None
+
+
def single_variable_constraints(A, b):
row = len(A)
col = len(A[0])
@@ -150,10 +167,10 @@ def single_variable_constraints(A, b):
vertices = []
edges = []
weights = dict()
- for i in range(0, vertices_num + 1):
+ for i in range(vertices_num + 1):
vertices.append(Vertex(i))
- for i in range(0, row):
- for j in range(0, len(A[i])):
+ for i in range(row):
+ for j in range(len(A[i])):
if A[i][j] == 1:
edges.append((vertices[0], vertices[j + 1]))
weights[(vertices[0], vertices[j + 1])] = b[i]
diff --git a/constraints_test.py b/constraints_test.py
deleted file mode 100644
index 7a129a2..0000000
--- a/constraints_test.py
+++ /dev/null
@@ -1,61 +0,0 @@
-from constraints import difference_constraints, equality_constraints, difference_constraints_without_aux_vertex, single_variable_constraints, difference_constraints_with_arbitrary_weight
-import unittest
-from math import floor
-
-class TestConstraints(unittest.TestCase):
- def test_difference_constraints(self):
- A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, 0, -1], [-1, 0, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
- b = [0, -1, 1, 5, 4, -1, -3, -3]
- self.assertEquals(difference_constraints(A, b), [-5, -3, 0, -1, -4])
- A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1], [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
- b = [1, -4, 2, 7, 5, 10, 2, -1, 3, -8]
- self.assertEquals(difference_constraints(A, b), [-5, -3, 0, -1, -6, -8])
- A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, -1, 0], [0, -1, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, 0, 1, -1], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
- b = [4, 5, -6, 1, 3, 5, 10, -4, 8]
- self.assertEquals(difference_constraints(A, b), None)
- A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1], [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
- b = [1, -4, 2, 7.3, 5, 10.1, 2.9, -1.11, 3, -8.6]
- c = [int(floor(i)) for i in b]
- print difference_constraints(A, c)
-
- def test_equality_constraints(self):
- A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, 0, -1], [-1, 0, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
- b = [0, -1, 1, 5, 4, -1, -3, -3]
- self.assertEquals(equality_constraints(A, b), None)
- A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1], [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
- b = [1, -4, 2, 7, 5, 10, 2, -1, 3, -8]
- self.assertEquals(equality_constraints(A, b), None)
- A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, -1, 0], [0, -1, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, 0, 1, -1], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
- b = [4, 5, -6, 1, 3, 5, 10, -4, 8]
- self.assertEquals(equality_constraints(A, b), None)
- A = [[-1, 1, 0], [0, -1, 1], [-1, 0, 1]]
- b = [1, 1, 2]
- self.assertEquals(equality_constraints(A, b), [-2, -1, 0])
- def test_difference_constraints_without_aux_vertex(self):
- A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, 0, -1], [-1, 0, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
- b = [0, -1, 1, 5, 4, -1, -3, -3]
- self.assertEquals(difference_constraints_without_aux_vertex(A, b), [-5, -3, 0, -1, -4])
- A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1], [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
- b = [1, -4, 2, 7, 5, 10, 2, -1, 3, -8]
- self.assertEquals(difference_constraints_without_aux_vertex(A, b), [-5, -3, 0, -1, -6, -8])
- A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, -1, 0], [0, -1, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, 0, 1, -1], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
- b = [4, 5, -6, 1, 3, 5, 10, -4, 8]
- self.assertEquals(difference_constraints_without_aux_vertex(A, b), None)
- def test_single_variable_constraints(self):
- A = [[1, 0], [0, 1], [-1, 0], [0, -1], [1, 0]]
- b = [3, 1, 5, -1, 2]
- self.assertEquals(single_variable_constraints(A, b), [2, 1])
- A = [[1, 0], [0, 1], [-1, 0], [0, -1], [1, 0]]
- b = [3, -1, 5, -1, 2]
- self.assertEquals(single_variable_constraints(A, b), None)
-# def test_difference_constraints_with_arbitrary_weight(self):
-# A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, 0, -1], [-1, 0, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
-# b = [0, -1, 1, 5, 4, -1, -3, -3]
-# self.assertEquals(difference_constraints_with_arbitrary_weight(A, b), [-5, -3, 0, -1, -4])
-# A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1], [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
-# b = [1, -4, 2, 7, 5, 10, 2, -1, 3, -8]
-# self.assertEquals(difference_constraints_with_arbitrary_weight(A, b), [-5, -3, 0, -1, -6, -8])
-# A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, -1, 0], [0, -1, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, 0, 1, -1], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
-# b = [4, 5, -6, 1, 3, 5, 10, -4, 8]
-# self.assertEquals(difference_constraints_with_arbitrary_weight(A, b), None)
-
diff --git a/contains.py b/contains.py
index 816e910..87b3fa4 100644
--- a/contains.py
+++ b/contains.py
@@ -1,12 +1,17 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
def contains(x, n):
- '''CLRS Exercise 16.2-5
+ """
+ CLRS Exercise 16.2-5
An algorithm that, given a set {x1, x2, ... ,xn} of points on the
real line, determines the smallest set of unit-length closed intervals that contains
- all of the given points.'''
+ all of the given points.
+ :param x:
+ :param n:
+ :return:
+ """
x.sort()
- print x
+ print(x)
i = 0
a = float("-Inf")
S = set()
@@ -15,5 +20,5 @@ def contains(x, n):
S = S.union({(x[i], x[i] + 1)})
a = x[i] + 1
i = i + 1
- print S
+ print(S)
return S
diff --git a/contains_test.py b/contains_test.py
deleted file mode 100644
index 55d405f..0000000
--- a/contains_test.py
+++ /dev/null
@@ -1,12 +0,0 @@
-#!/usr/bin/env ipython
-
-import unittest
-from contains import contains
-
-class TestContains(unittest.TestCase):
- def test_contains(self):
- x = [1, 1.5, 3.5, 2.3, 10.01]
- self.assertEquals(contains(x, 5), {(1, 2), (2.3, 3.3), (3.5, 4.5), (10.01, 11.01)})
- x = [3.5, 5.2, -1.1, -4, -12, -11.33]
- self.assertEquals(contains(x, 6), {(-12, -11), (-4, -3), (-1.1, -0.10000000000000009), (3.5, 4.5), (5.2, 6.2)})
-
diff --git a/counting_sort.py b/counting_sort.py
index 922ab3d..1d71762 100644
--- a/counting_sort.py
+++ b/counting_sort.py
@@ -1,8 +1,8 @@
def counting_sort(A, B, k):
C = []
- for i in range(0, k + 1):
+ for i in range(k + 1):
C.append(0)
- for j in range(0, len(A)):
+ for j in range(len(A)):
C[A[j]] = C[A[j]] + 1
for i in range(1, k + 1):
C[i] = C[i] + C[i - 1]
diff --git a/cut_rod.py b/cut_rod.py
index 1c7473f..2689136 100644
--- a/cut_rod.py
+++ b/cut_rod.py
@@ -5,7 +5,9 @@ def bottom_up_cut_rod(p, n):
for i in range(1, j + 1):
q = max(q, p[i - 1] + r[j - i])
r[j] = q
- return r[n]
+ return r[n]
+
+
def bottom_up_cut_rod_two_subproblem(p, n):
r = [0] * (n + 1)
for i in range(1, n + 1):
@@ -15,10 +17,14 @@ def bottom_up_cut_rod_two_subproblem(p, n):
for i in range(1, j + 1):
q = max(q, r[i] + r[j - i])
r[j] = q
- return r[n]
+ return r[n]
+
+
def memoized_cut_rod(p, n):
r = [float("-Inf")] * n
return memoized_cut_rod_aux(p, n, r)
+
+
def memoized_cut_rod_aux(p, n, r):
if n == 0:
return 0
@@ -29,6 +35,8 @@ def memoized_cut_rod_aux(p, n, r):
q = max(q, p[i - 1] + memoized_cut_rod_aux(p, n - i, r))
r[n - 1] = q
return q
+
+
def extended_bottom_up_cut_rod(p, n):
r = [0] * (n + 1)
s = [0] * (n + 1)
@@ -39,12 +47,16 @@ def extended_bottom_up_cut_rod(p, n):
q = p[i - 1] + r[j - i]
s[j] = i
r[j] = q
- return r,s
+ return r, s
+
+
def print_cut_rod_solution(p, n, cut):
- r,s = cut(p, n)
+ r, s = cut(p, n)
while n != 0:
- print s[n]
+ print(s[n])
n = n - s[n]
+
+
def bottom_up_cut_rod_with_fixed_cut_cost(p, n, c):
r = [0] * (n + 1)
for j in range(1, n + 1):
@@ -53,12 +65,16 @@ def bottom_up_cut_rod_with_fixed_cut_cost(p, n, c):
q = max(q, r[i] + r[j - i] - c)
q = max(q, p[j - 1])
r[j] = q
- return r[n]
+ return r[n]
+
+
def extended_memoized_cut_rod(p, n):
r = [float("-Inf")] * n
s = [0] * (n + 1)
extended_memoized_cut_rod_aux(p, n, r, s)
- return r,s
+ return r, s
+
+
def extended_memoized_cut_rod_aux(p, n, r, s):
if n == 0:
return 0
@@ -66,7 +82,7 @@ def extended_memoized_cut_rod_aux(p, n, r, s):
return r[n - 1]
q = float("-Inf")
for i in range(1, n + 1):
- value = p[i - 1] + extended_memoized_cut_rod_aux(p, n -i, r, s)
+ value = p[i - 1] + extended_memoized_cut_rod_aux(p, n - i, r, s)
if q < value:
q = value
s[n] = i
diff --git a/cut_rod_test.py b/cut_rod_test.py
deleted file mode 100755
index 13a9d6a..0000000
--- a/cut_rod_test.py
+++ /dev/null
@@ -1,33 +0,0 @@
-#!/usr/bin/env ipython
-import unittest
-
-from cut_rod import bottom_up_cut_rod, bottom_up_cut_rod_two_subproblem, memoized_cut_rod, print_cut_rod_solution, bottom_up_cut_rod_with_fixed_cut_cost, extended_memoized_cut_rod
-
-class TestCutRod(unittest.TestCase):
- def test_bottom_up_cut_rod(self):
- p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
- values = [1, 1, 2, 5, 3, 8, 4, 10, 5, 13, 6, 17, 7, 18, 8, 22, 9, 25, 10, 30]
- for i in range(0, len(values), 2):
- self.assertEquals(bottom_up_cut_rod(p, values[i]), values[i + 1])
- def test_bottom_up_cut_rod_two_subproblem(self):
- p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
- values = [1, 1, 2, 5, 3, 8, 4, 10, 5, 13, 6, 17, 7, 18, 8, 22, 9, 25, 10, 30]
- for i in range(0, len(values), 2):
- self.assertEquals(bottom_up_cut_rod_two_subproblem(p, values[i]), values[i + 1])
- def test_memoized_cut_rod(self):
- p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
- values = [1, 1, 2, 5, 3, 8, 4, 10, 5, 13, 6, 17, 7, 18, 8, 22, 9, 25, 10, 30]
- for i in range(0, len(values), 2):
- self.assertEquals(memoized_cut_rod(p, values[i]), values[i + 1])
- def test_bottom_up_cut_rod_with_fixed_cut_cost(self):
- p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
- values = [1, 1, 2, 5, 3, 8, 4, 9, 5, 11, 6, 17, 7, 17, 8, 20, 9, 24, 10, 30]
- for i in range(0, len(values), 2):
- self.assertEquals(bottom_up_cut_rod_with_fixed_cut_cost(p, values[i], 2), values[i + 1])
- values = [1, 1, 2, 5, 3, 8, 4, 9, 5, 11.5, 6, 17, 7, 17, 8, 20.5, 9, 24, 10, 30]
- for i in range(0, len(values), 2):
- self.assertEquals(bottom_up_cut_rod_with_fixed_cut_cost(p, values[i], 1.5), values[i + 1])
- def test_print_rod_solution(self):
- p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
- values = [1, 1, 2, 5, 3, 8, 4, 10, 5, 13, 6, 17, 7, 18, 8, 22, 9, 25, 10, 30]
- print_cut_rod_solution(p, 9, extended_memoized_cut_rod)
diff --git a/depth_tree.py b/depth_tree.py
index 4440928..72e2107 100644
--- a/depth_tree.py
+++ b/depth_tree.py
@@ -1,27 +1,33 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
# A variant of red black tree that has depth attribute
-from rb_tree import rb_node, rb_tree
+from rb_tree import RbNode, RbTree
-class depth_node(rb_node):
+
+class depth_node(RbNode):
def __init__(self, key, p, left, right, color, depth):
- rb_node.__init__(self, key, p, left, right, color)
+ RbNode.__init__(self, key, p, left, right, color)
self.depth = depth
+
def update_depth_whole_tree(self, amount):
if self.depth != -1:
self.left.update_depth_whole_tree(amount)
self.depth = self.depth + amount
self.right.update_depth_whole_tree(amount)
-class depth_tree(rb_tree):
+
+
+class depth_tree(RbTree):
nil = depth_node(None, None, None, None, 1, -1)
root = nil
+
def __init__(self, values):
if isinstance(values, list):
for i in values:
self.insert(depth_node(i, None, None, None, 0, 0))
else:
- print "Not invalid argument"
+ print("Not invalid argument")
+
def left_rotate(self, x):
y = x.right
x.right = y.left
@@ -40,6 +46,7 @@ def left_rotate(self, x):
y.depth = y.depth - 1
x.left.update_depth_whole_tree(1)
y.right.update_depth_whole_tree(-1)
+
def right_rotate(self, y):
x = y.left
y.left = x.right
@@ -58,6 +65,7 @@ def right_rotate(self, y):
y.depth = y.depth + 1
x.left.update_depth_whole_tree(-1)
y.right.update_depth_whole_tree(1)
+
def insert(self, z):
y = self.nil
x = self.root
@@ -79,8 +87,9 @@ def insert(self, z):
z.p = y
z.left = self.nil
z.right = self.nil
- z.color = 0 #red
+ z.color = 0 # red
self.insert_fixed(z)
+
def delete(self, z):
y = z
y_original_color = y.color
diff --git a/deque.py b/deque.py
index 61509a4..0391352 100644
--- a/deque.py
+++ b/deque.py
@@ -1,32 +1,38 @@
-from queue import queue, FullException, EmptyException
-
-def deque(queue):
- '''
- whereas a queue allows insertion at one end and deletion at the other end, a deque(double-ended queue allows insertion and deletion at both ends
- '''
- def __init__(self, size):
- super(deque, self).__init__(size)
- def enqueue_tail(self, x):
- self.enqueue(x)
- def dequeue_head(self):
- return self.dequeue()
- def enqueue_head(self, x):
- if self.full():
- raise FullException("This double-ended queue is full")
- else:
- if self.head == 0:
- self.head = self.length - 1
- else:
- self.head = self.head - 1
- self[self.head] = x
- def dequeue_tail(self):
- if self.emtpy():
- raise EmptyException("This double-ended queue is empty")
- else:
- if self.tail == 0:
- self.tail = self.length - 1
- else:
- self.tail = self.tail - 1
-
- return self[self.tail]
+from Queue import Queue, FullException, EmptyException
+
+class Deque(Queue):
+ """
+ whereas a Queue allows insertion at one end and deletion at the other end,
+ a Deque(double-ended Queue) allows insertion and deletion at both ends
+ """
+
+ def __init__(self, size):
+ super().__init__(size)
+
+ def enqueue_tail(self, x):
+ self.enqueue(x)
+
+ def dequeue_head(self):
+ return self.dequeue()
+
+ def enqueue_head(self, x):
+ if self.full():
+ raise FullException()
+ else:
+ if self.head == 0:
+ self.head = self.size - 1
+ else:
+ self.head = self.head - 1
+ self.data[self.head] = x
+
+ def dequeue_tail(self):
+ if self.empty():
+ raise EmptyException()
+ else:
+ if self.tail == 0:
+ self.tail = self.size - 1
+ else:
+ self.tail = self.tail - 1
+
+ return self.data[self.tail]
diff --git a/disjoint_sets_forest.py b/disjoint_sets_forest.py
index 09ff777..20f20a6 100644
--- a/disjoint_sets_forest.py
+++ b/disjoint_sets_forest.py
@@ -1,24 +1,28 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-class node(object):
+
+class node:
def __init__(self, key):
self.key = key
- #key.index = self
+ # key.index = self
self.p = self
self.rank = 0
self.child = []
+
def union(self, y):
self.find_set().link(y.find_set())
+
def link(self, y):
x = self
if x.rank > y.rank:
- x.child.append(y)
+ x.child.append(y)
y.p = x
else:
- y.child.append(x)
+ y.child.append(x)
x.p = y
if x.rank == y.rank:
y.rank = y.rank + 1
+
def find_set(self):
y = self
x = self
@@ -28,15 +32,17 @@ def find_set(self):
z = x
x = x.p
z.p = y
-# print y.key
+ # print( y.key)
return y
+
def print_set(self):
x = self
while x != x.p:
x = x.p
x.print_set_aux()
+
def print_set_aux(self):
- print self.key
+ print(self.key)
if len(self.child) == 0:
return
for child in self.child:
diff --git a/disjoint_sets_linked_list.py b/disjoint_sets_linked_list.py
index af279c0..ea1895b 100644
--- a/disjoint_sets_linked_list.py
+++ b/disjoint_sets_linked_list.py
@@ -1,12 +1,14 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-class node(object):
+class node:
def __init__(self, key):
self.key = key
self.set = None
self.next = None
+
def find_set(self):
return self.set.head
+
def union(self, y):
if self.set.length < y.set.length:
x = y
@@ -23,12 +25,16 @@ def union(self, y):
xs.tail = ys.tail
xs.length = xs.length + ys.length
return x
-class header(object):
+
+
+class header:
def __init__(self, element):
self.length = 1
self.head = element
element.set = self
self.tail = self.head
+
+
class node_notail(node):
def union(self, y):
if self.set.length < y.set.length:
@@ -47,7 +53,9 @@ def union(self, y):
xs.head = ys.head
xs.length = xs.length + ys.length
return y
-class header_notail(object):
+
+
+class header_notail:
def __init__(self, element):
self.length = 1
self.head = element
diff --git a/dynamic_array.py b/dynamic_array.py
new file mode 100644
index 0000000..2defc73
--- /dev/null
+++ b/dynamic_array.py
@@ -0,0 +1,21 @@
+class DynamicArray:
+ def __init__(self, capacity):
+ assert capacity > 0
+ self._capacity = capacity
+ self._size = 0
+ self._data = [None] * capacity
+
+ def add(self, element):
+ if self._size == self._capacity:
+ temp = self._data
+ self._data = [None] * (self._capacity * 2)
+ self._data[:self._capacity] = temp[:]
+ self._capacity *= 2
+ self._data[self._size] = element
+ self._size += 1
+
+ def size(self):
+ return self._size
+
+ def get(self, index):
+ return self._data[index]
diff --git a/eight_queen.py b/eight_queen.py
new file mode 100644
index 0000000..6c4f155
--- /dev/null
+++ b/eight_queen.py
@@ -0,0 +1,37 @@
+N = 8
+counter = 0
+
+
+def print_solution(chess_board):
+ for row in range(N):
+ for col in range(N):
+ if chess_board[row] != col:
+ print('-', end=' ')
+ else:
+ print('X', end=' ')
+ print('\n')
+ print('\n')
+
+
+def isplaceok(chess_board, row, col):
+ return not any(
+ (chess_board[i] == col) or (chess_board[i] - col == row - i) or (chess_board[i] - col == i - row) for i in
+ range(row))
+
+
+def add_queen(chess_board, row):
+ global counter
+ if row >= N:
+ print_solution(chess_board)
+ counter += 1
+ else:
+ for col in range(N):
+ if isplaceok(chess_board, row, col):
+ chess_board[row] = col
+ add_queen(chess_board, row + 1)
+
+
+if __name__ == "__main__":
+ chess_board = [-1] * N
+ add_queen(chess_board, 0)
+ print(counter)
diff --git a/euclid.py b/euclid.py
index e5f97bc..3d81b24 100644
--- a/euclid.py
+++ b/euclid.py
@@ -1,15 +1,17 @@
#!/usr/bin/env python
# coding=utf-8
+
def euclid(a, b):
if b == 0:
return a
else:
return euclid(b, a % b)
+
def extended_euclid(a, b):
if b == 0:
- return (a, 1, 0)
+ return a, 1, 0
else:
d, x, y = extended_euclid(b, a % b)
return d, y, x - (a / b) * y
diff --git a/extended_bottom_up_cut_rod.py b/extended_bottom_up_cut_rod.py
index ff4bdb2..316e42a 100644
--- a/extended_bottom_up_cut_rod.py
+++ b/extended_bottom_up_cut_rod.py
@@ -8,10 +8,11 @@ def extended_bottom_up_cut_rod(p, n):
q = p[i - 1] + r[j - i]
s[j] = i
r[j] = q
- return r, s
+ return r, s
+
def print_cut_rod_solution(p, n):
- r,s = extended_bottom_up_cut_rod(p, n)
+ r, s = extended_bottom_up_cut_rod(p, n)
while n > 0:
- print s[n]
+ print(s[n])
n = n - s[n]
diff --git a/fft.py b/fft.py
index dd5ee18..e90b743 100644
--- a/fft.py
+++ b/fft.py
@@ -1,7 +1,8 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import math
+
def recursive_fft(a):
n = len(a)
if n == 1:
@@ -13,16 +14,19 @@ def recursive_fft(a):
y0 = recursive_fft(a0)
y1 = recursive_fft(a1)
y = [0.0] * n
- for k in range(0, n / 2):
+ for k in range(n // 2):
y[k] = y0[k] + w * y1[k]
- y[k + n / 2] = y0[k] - w * y1[k]
+ y[k + n // 2] = y0[k] - w * y1[k]
w = w * wn
return y
+
def recursive_inverse_fft(y):
n = len(y)
result = recursive_inverse_fft_aux(y)
- return [result[i] / n for i in range(0, n)]
+ return [result[i] / n for i in range(n)]
+
+
def recursive_inverse_fft_aux(y):
n = len(y)
if n == 1:
@@ -34,8 +38,8 @@ def recursive_inverse_fft_aux(y):
a0 = recursive_inverse_fft_aux(y0)
a1 = recursive_inverse_fft_aux(y1)
a = [0.0] * n
- for k in range(0, n / 2):
+ for k in range(n // 2):
a[k] = (a0[k] + w * a1[k])
- a[k + n / 2] = (a0[k] - w * a1[k])
+ a[k + n // 2] = (a0[k] - w * a1[k])
w = w * wn
return a
diff --git a/fibonacci_heap.py b/fibonacciheap.py
similarity index 73%
rename from fibonacci_heap.py
rename to fibonacciheap.py
index 53739b8..778ddcc 100644
--- a/fibonacci_heap.py
+++ b/fibonacciheap.py
@@ -1,17 +1,21 @@
-class fibonacci_node(object):
+class FibonacciNode:
degree = 0
p = None
child = None
mark = False
left = None
right = None
+
def __init__(self, k):
self.key = k
+
def __iter__(self):
- '''generate a list of children of the node for iteration'''
+ """
+ generate a list of children of the node for iteration
+ """
self.children = []
self.index = 0
- if self.child != None:
+ if self.child is not None:
child = self.child
while True:
self.children.append(child)
@@ -20,39 +24,53 @@ def __iter__(self):
else:
break
return self
+
def next(self):
if self.index < len(self.children):
self.index = self.index + 1
return self.children[self.index - 1]
else:
raise StopIteration
+
def insert(self, x):
- '''insert x to the left of node'''
+ """
+ insert x to the left of node
+ :param x:
+ :return:
+ """
x.left = self.left
x.right = self
self.left.right = x
- self.left = x
+ self.left = x
+
def concatenate(self, x):
- '''concatenate two lists represented by the node and x,
- x mustn't be None'''
+ """
+ concatenate two lists represented by the node and x,
+ x mustn't be None
+ :param x:
+ :return:
+ """
self.left.right = x.right
x.right.left = self.left
self.left = x
x.right = self
+
def remove(self):
- self.left.right = self.right
+ self.left.right = self.right
self.right.left = self.left
+
def add_child(self, y):
self.degree = self.degree + 1
y.mark = False
y.p = self
- if self.child == None:
+ if self.child is None:
self.child = y
y.left = y
y.right = y
else:
- self.child.insert(y)
- print "y.left.key = {}, y.right.key = {}".format(y.left.key, y.right.key)
+ self.child.insert(y)
+ print("y.left.key = {}, y.right.key = {}".format(y.left.key, y.right.key))
+
def remove_child(self, y):
self.degree = self.degree - 1
if y.right == y:
@@ -62,15 +80,21 @@ def remove_child(self, y):
y.remove()
else:
y.remove()
-class fibonacci_heap(object):
+
+
+class FibonacciHeap:
def __init__(self):
self.n = 0
self.minimum = None
+
def __iter__(self):
- '''generate a list of children of the node for iteration'''
+ """
+ generate a list of children of the node for iteration
+ :return:
+ """
self.root_list = []
self.index = 0
- if self.minimum != None:
+ if self.minimum is not None:
root = self.minimum
while True:
self.root_list.append(root)
@@ -79,18 +103,20 @@ def __iter__(self):
else:
break
return self
+
def next(self):
if self.index < len(self.root_list):
self.index = self.index + 1
return self.root_list[self.index - 1]
else:
raise StopIteration
+
def __repr__(self):
s = ''
x = self.minimum
- if x != None:
+ if x is not None:
while True:
- s = s + '\t' + str(x.key)
+ s = s + '\t' + str(x.key)
if x == self.minimum.left:
break
else:
@@ -98,10 +124,15 @@ def __repr__(self):
return s
else:
return ''
+
def insert(self, x):
- '''insert the node x into the root list of fibonacci heap'''
+ """
+ insert the node x into the root list of fibonacci heap
+ :param x:
+ :return:
+ """
x.p = None
- if self.minimum == None:
+ if self.minimum is None:
self.minimum = x
x.left = x
x.right = x
@@ -110,13 +141,15 @@ def insert(self, x):
if x.key < self.minimum.key:
self.minimum = x
self.n = self.n + 1
+
def minimum(self):
return self.minimum
+
def union(self, h):
- cat = fibonacci_heap()
- if self.minimum == None:
+ cat = FibonacciHeap()
+ if self.minimum is None:
return h
- elif h.minimum == None:
+ elif h.minimum is None:
return self
else:
self.minimum.concatenate(h.minimum)
@@ -126,9 +159,10 @@ def union(self, h):
cat.minimum = h.minimum
cat.n = self.n + h.n
return cat
+
def extract_min(self):
z = self.minimum
- if z != None:
+ if z is not None:
for child in z:
self.insert(child)
z.remove()
@@ -139,54 +173,61 @@ def extract_min(self):
self.consolidate()
self.n = self.n - 1
return z
+
def consolidate(self):
- D = self.n / 2
+ D = self.n // 2
A = [None] * (D + 1)
left = self.minimum.left
w = self.minimum
for w in self:
x = w
d = x.degree
- print 'w.key = {}'.format(w.key)
- print 'w.degree = {}'.format(w.degree)
- while A[d] != None:
+ print('w.key = {}'.format(w.key))
+ print('w.degree = {}'.format(w.degree))
+ while A[d] is not None:
y = A[d]
if x.key > y.key:
- x,y = y,x
+ x, y = y, x
self.link(y, x)
A[d] = None
d = d + 1
A[d] = x
self.minimum = None
for i in A:
- if i != None:
+ if i is not None:
self.insert(i)
- def link(self, y, x):
+
+ @staticmethod
+ def link(y, x):
y.remove()
x.add_child(y)
+
def decrease_key(self, x, k):
if k > x.key:
- print "new key is greater than current key"
+ print("new key is greater than current key")
return
x.key = k
y = x.p
- if y != None and x.key < y.key:
+ if y is not None and x.key < y.key:
self.cut(x, y)
self.cascading_cut(y)
if x.key < self.minimum.key:
self.minimum = x
+
def cut(self, x, y):
y.remove_child(x)
x.mark = False
self.insert(x)
+
def cascading_cut(self, y):
z = y.p
- if z != None:
- if y.mark == False:
+ if z is not None:
+ if y.mark is False:
y.mark = True
else:
self.cut(y, z)
self.cascading_cut(z)
+
def delete(self, x):
self.decrease_key(x, float("-Inf"))
self.extract_min()
diff --git a/gcd.c b/gcd.c
deleted file mode 100644
index 8dd5f52..0000000
--- a/gcd.c
+++ /dev/null
@@ -1,21 +0,0 @@
-#include
-
-/* gcd: compute the greatest common divisor of m and n;
- return value: gcd */
- unsigned gcd(unsigned m, unsigned n) {
- unsigned rem;
-
- while (n > 0)
- {
- rem = m % n;
- m = n;
- n = rem;
- }
- return m;
-}
-
-int main() {
- printf("%u\n", gcd(63 - 1194 + 1387, 1387));
- printf("%u\n", gcd(1273, 1387));
- return 0;
-}
diff --git a/gcd.py b/gcd.py
new file mode 100644
index 0000000..ca4e42e
--- /dev/null
+++ b/gcd.py
@@ -0,0 +1,16 @@
+#!/usr/bin/env python
+# encoding: utf-8
+
+
+def gcd(m: int, n: int):
+ """
+ compute the greatest common divisor of m and n;
+ :param m:
+ :param n:
+ :return:
+ """
+ while n > 0:
+ rem = m % n
+ m = n
+ n = rem
+ return m
diff --git a/graph.py b/graph.py
index d1a019d..004e05a 100644
--- a/graph.py
+++ b/graph.py
@@ -1,150 +1,150 @@
-from queue import queue
+from queue import Queue
import disjoint_sets_forest as dsf
import sys
+from typing import Iterable, Optional, Tuple, Set, Dict
+from enum import Enum
-class Vertex(object):
+Color = Enum('Color', ('WHITE', 'GREY', 'BLACK'))
+
+
+class Vertex:
def __init__(self, key):
self.key = key
def __repr__(self):
- return str(self.key)
+ return f"Vertex({self.key})"
def print_path(self, v):
- '''print out the vertices on a shortest path from s to
- v, assuming that BFS has already computed a breadth-first tree'''
+ """
+ print out the vertices on a shortest path from s to
+ v, assuming that BFS has already computed a breadth-first tree
+ """
if self == v:
- print self,
- elif v.p == None:
- print "No path from {} to {} exists".format(self.key, v.key)
+ print(self)
+ elif v.p is None:
+ print("No path from {} to {} exists".format(self.key, v.key))
else:
self.print_path(v.p)
- print v,
-
-class Graph(object):
- def __init__(self, vertices = tuple(), edges = tuple(), directed = True):
- self.directed = directed
- self.vertices = set(vertices)
- self.edges = set()
- self.adj = dict()
- for u in vertices:
+ print(v)
+
+
+Vertices = Optional[Iterable[Vertex]]
+Edge = Tuple[Vertex, Vertex]
+Edges = Optional[Iterable[Edge]]
+
+
+class Graph:
+ def __init__(self, vertices: Optional[Vertices] = None,
+ edges: Optional[Edges] = None, directed: bool = True):
+ self.directed: bool = directed
+ self.vertices: Set[Vertex] = set() if vertices is None else set(vertices)
+ self.edges: Set[Edge] = set()
+ self.adj: Dict[Vertex, Set[Vertex]] = dict()
+ self._time: int = 0
+ for u in self.vertices:
self.adj[u] = set()
- for u, v in edges:
- self._addEdge(u, v)
-
- def __eq__(self, G2):
- G1 = self
- if G1.directed != G2.directed:
- return False
- elif G1.vertices != G2.vertices:
- return False
- elif G1.edges != G2.edges:
- return False
- else:
- for u in G1.vertices:
- if G1.adj[u] != G2.adj[u]:
- return False
- return True
+ if edges is not None:
+ for u, v in edges:
+ self._add_edge(u, v)
+
+ def __eq__(self, graph2: 'Graph'):
+ graph1 = self
+ return (graph1.directed == graph2.directed) and (graph1.vertices == graph2.vertices) and (
+ graph1.edges == graph2.edges)
- def _addEdge(self, u, v):
+ def _add_edge(self, u: Vertex, v: Vertex):
if self.directed:
self.adj[u].add(v)
self.edges.add((u, v))
- elif u != v: # undirected graph does not allow self loop
+ elif u != v: # undirected graph does not allow self loop
self.adj[u].add(v)
self.edges.add((u, v))
self.adj[v].add(u)
self.edges.add((v, u))
- def _addVertex(self, u, edges = tuple()):
- self.vertices.add(u)
- for u, v in edges:
- self._addEdge(u, v)
+ def _add_vertex(self, u: Vertex, edges: Optional[Edges] = None):
+ self.vertices.add(u)
+ if edges is not None:
+ for u, v in edges:
+ self._add_edge(u, v)
def copy(self):
return Graph(self.vertices, self.edges, self.directed)
def transpose(self):
- t = Graph(self.vertices)
- for u in self.vertices:
- for v in self.adj[u]:
- t._addEdge(v, u)
- return t
+ return Graph(self.vertices, [(v, u) for u, v in self.edges], self.directed)
- def bfs(self, s):
+ def bfs(self, s: Vertex):
for u in self.vertices:
- u.d = float("Inf")
- u.color = 0
- u.p = None
- s.color = 1
- s.d = 0
- s.p = None
- q = queue(2 * len(self.vertices))
- q.enqueue(s)
- while not q.empty():
- u = q.dequeue()
+ u.distance = float("Inf")
+ u.color = Color.WHITE
+ u.parent = None
+ s.color = Color.GREY
+ s.distance = 0
+ s.parent = None
+ queue = Queue()
+ queue.put(s)
+ while not queue.empty():
+ u = queue.get()
for v in self.adj[u]:
- if v.color == 0:
- v.color = 1
- v.d = u.d + 1
- v.p = u
- q.enqueue(v)
- u.color = 2
+ if v.color == Color.WHITE:
+ v.color = Color.GREY
+ v.distance = u.distance + 1
+ v.parent = u
+ queue.put(v)
+ u.color = Color.BLACK
def dfs(self):
- global time
+ self._time = 0
for u in self.vertices:
- u.color = 0
+ u.color = Color.WHITE
u.p = None
- time = 0
for u in self.vertices:
- if u.color == 0:
+ if u.color == Color.WHITE:
self._dfs_visit(u)
- def _dfs_visit(self, u):
- global time
- time = time + 1
- u.d = time
- u.color = 1
+ def _dfs_visit(self, u: Vertex):
+ self._time += 1
+ u.d = self._time
+ u.color = Color.GREY
for v in self.adj[u]:
- if v.color == 0:
+ if v.color == Color.WHITE:
v.p = u
self._dfs_visit(v)
- u.color = 2
- time = time + 1
- u.f = time
+ u.color = Color.BLACK
+ self._time += 1
+ u.f = self._time
- def isCyclic(self):
- global time
+ def is_cyclic(self):
for u in self.vertices:
- u.color = 0
- u.p = None
- time = 0
+ u.color = Color.WHITE
for u in self.vertices:
- if u.color == 0:
+ if u.color == Color.WHITE:
if self._is_cyclic_aux(u):
return True
return False
def _is_cyclic_aux(self, u):
- global time
- time = time + 1
- u.d = time
- u.color = 1
+ u.color = Color.GREY
for v in self.adj[u]:
- if v.color == 0:
- v.p = u
+ if v.color == Color.WHITE:
if self._is_cyclic_aux(v):
return True
- elif v.color == 1:
+ elif v.color == Color.GREY:
return True
- u.color = 2
- time = time + 1
- u.f = time
+ u.color = Color.BLACK
return False
def topological_sort(self):
+ """
+ Perform topological sort for dag
+
+ A topological sort of a dag(directed acyclic graph) G = (V, E) is a linear ordering of all the vertices
+ such that if G contains an edge (u, v), then u appears before v in the ordering.
+ """
+ assert (not self.is_cyclic()) and self.directed
self.dfs()
- return sorted(self.vertices, key = lambda x: x.f, reverse = True)
+ return sorted(self.vertices, key=lambda x: x.f, reverse=True)
def print_all_edges(self):
s = next(iter(self.vertices))
@@ -154,15 +154,16 @@ def print_all_edges(self):
def _print_all_edges_aux(self, u):
for v in self.adj[u]:
if u == v.p:
- print (u, v)
+ print((u, v))
self._print_all_edges_aux(v)
- print (v, u)
+ print((v, u))
else:
pass
+
def printAllEdges(self):
self.status = dict()
s = next(iter(self.vertices))
- print "key of s is {}".format(s.key)
+ print("key of s is {}".format(s.key))
self.printAllEdges_aux(s)
def printAllEdges_aux(self, u):
@@ -172,16 +173,16 @@ def printAllEdges_aux(self, u):
except KeyError:
self.status[(u, v)] = 1
self.status[(v, u)] = 1
- print (u, v)
+ print((u, v))
self.printAllEdges_aux(v)
- print (v, u)
+ print((v, u))
def path_num(self, s, t):
- '''
+ """
A linear-time algorithm that takes as input a directed acyclic graph
G = (V, E) and two vertices s and t, and returns the number of simple
paths from s to t in G.
- '''
+ """
for u in self.vertices:
u.color = 0
u.num = 0
@@ -208,7 +209,7 @@ def strongly_connected_components(self):
u.p = None
time = 0
cc = 0
- for u in sorted(self.vertices, key = lambda u: u.f, reverse = True):
+ for u in sorted(self.vertices, key=lambda u: u.f, reverse=True):
if u.color == 0:
cc = cc + 1
t.strongly_connected_components_dfs_visit(u)
@@ -226,13 +227,17 @@ def strongly_connected_components_dfs_visit(self, u):
u.color = 2
time = time + 1
u.f = time
+
def simplified(self):
- '''create a simplified graph that has the same strong
+ """
+ create a simplified graph that has the same strong
connected components and component graph as G and that is as small
- as possible'''
+ as possible
+ """
self.dfs()
t = self.transpose()
return t.simplified_dfs()
+
def simplified_dfs(self):
global time, cc, status
status = dict()
@@ -242,16 +247,17 @@ def simplified_dfs(self):
u.p = None
time = 0
cc = 0
- for u in sorted(self.vertices, key = lambda u: u.f, reverse = True):
+ for u in sorted(self.vertices, key=lambda u: u.f, reverse=True):
if u.color == 0:
stack = []
cc = cc + 1
self.simplified_dfs_visit(u, stack, s)
- for i in range(0, len(stack) - 1):
- s._addEdge(stack[i], stack[i + 1])
+ for i in range(len(stack) - 1):
+ s._add_edge(stack[i], stack[i + 1])
if len(stack) > 1:
- s._addEdge(stack[len(stack) - 1], stack[0])
+ s._add_edge(stack[len(stack) - 1], stack[0])
return s
+
def simplified_dfs_visit(self, u, stack, s):
global time, cc, status
stack.append(u)
@@ -267,18 +273,22 @@ def simplified_dfs_visit(self, u, stack, s):
try:
st = status[(v.cc, u.cc)]
except KeyError:
- status[(v.cc, u.cc)] = 1
- s._addEdge(v, u)
+ status[(v.cc, u.cc)] = 1
+ s._add_edge(v, u)
u.color = 2
time = time + 1
u.f = time
+
def component_graph(self):
- '''compute the component graph of a directed graph
- there is at most one edge between two vertices in the component graph'''
- global time, cc, cg, status, vertices_list
+ """
+ compute the component graph of a directed graph
+ there is at most one edge between two vertices in the component graph
+ :return:
+ """
+ global time, cc, cg, status, vertices_list
self.dfs()
- t = self.transpose()
- for u in t.vertices:
+ t = self.transpose()
+ for u in t.vertices:
u.color = 0
u.p = None
time = 0
@@ -286,13 +296,14 @@ def component_graph(self):
status = dict()
vertices_list = list()
cg = Graph()
- for u in sorted(self.vertices, key = lambda u: u.f, reverse = True):
+ for u in sorted(self.vertices, key=lambda u: u.f, reverse=True):
if u.color == 0:
cc = cc + 1
vertices_list.append(Vertex(cc))
- cg._addVertex(vertices_list[cc - 1])
+ cg._add_vertex(vertices_list[cc - 1])
t.component_graph_dfs_visit(u)
return cg
+
def component_graph_dfs_visit(self, u):
global time, cc, cg, vertices_list
u.cc = cc
@@ -307,23 +318,29 @@ def component_graph_dfs_visit(self, u):
try:
st = status[(v.cc, u.cc)]
except KeyError:
- status[(v.cc, u.cc)] = 1
- cg._addEdge(vertices_list[v.cc - 1], vertices_list[u.cc - 1])
+ status[(v.cc, u.cc)] = 1
+ cg._add_edge(
+ vertices_list[v.cc - 1],
+ vertices_list[u.cc - 1])
u.color = 2
time = time + 1
u.f = time
+
def semiconnected(self):
cg = self.component_graph()
- vertices_list = sorted(cg.vertices, key = lambda u: u.key, reverse = False)
- for i in range(0, len(vertices_list) - 1):
+ vertices_list = sorted(cg.vertices, key=lambda u: u.key, reverse=False)
+ for i in range(len(vertices_list) - 1):
if vertices_list[i + 1] not in cg.adj[vertices_list[i]]:
return False
return True
+
def cut(self, x, y, w):
- '''For a given edge (x, y) contained in some minimum spanning tree,
+ """
+ For a given edge (x, y) contained in some minimum spanning tree,
form a minimum spanning tree that contains (x, y) using a method like Prim's algorithm,
and construct a cut (S, V - S) such that (x, y) is the light edge crossing
- the cut, S = {u: u.root = x}'''
+ the cut, S = {u: u.root = x}
+ """
for v in self.vertices:
v.weight = float("Inf")
v.p = None
@@ -340,6 +357,7 @@ def cut(self, x, y, w):
v.root = u.root
q.heap_decrease_key(v.index, w(u, v))
v.p = u
+
def alledges_undirected_dfs(self):
global time, l
for u in self.vertices:
@@ -351,6 +369,7 @@ def alledges_undirected_dfs(self):
if u.color == 0:
self.alledges_undirected_dfs_visit(u)
return l
+
def alledges_undirected_dfs_visit(self, u):
global time, l
time = time + 1
@@ -362,24 +381,28 @@ def alledges_undirected_dfs_visit(self, u):
v.p = u
self.alledges_undirected_dfs_visit(v)
elif v.color == 1 and u.p != v:
- l.append((u, v))
+ l.append((u, v))
u.color = 2
time = time + 1
u.f = time
+
def Kruskal(self, w):
A = set()
for v in self.vertices:
- dsf_node(v)
-# ls = self.alledges_undirected_dfs()
- for u,v in sorted(self.edges, key=lambda x: w(x[0], x[1]), reverse = False):
+ DfsNode(v)
+ # ls = self.alledges_undirected_dfs()
+ for u, v in sorted(self.edges, key=lambda x: w(x[0], x[1]), reverse=False):
if u.index.find_set() != v.index.find_set():
- A = A.union({(u,v)})
+ A = A.union({(u, v)})
u.index.union(v.index)
return A
+
def Prim(self, w, r):
- '''G.Prim(weight, root) -- Given weight function
+ """
+ G.Prim(weight, root) -- Given weight function
and an arbitrary vertex root of the graph G,
- compute minimum spanning tree using Prim's algorithm'''
+ compute minimum spanning tree using Prim's algorithm
+ """
for v in self.vertices:
v.weight = float("Inf")
v.p = None
@@ -391,28 +414,29 @@ def Prim(self, w, r):
if v in q and w(u, v) < v.weight:
v.p = u
q.heap_decrease_key(v.index, w(u, v))
-# def Prim_vEB(self, w, r, bound):
-# '''G.Prim(weight, root) -- Given weight function
-# and an arbitrary vertex root of the graph G,
-# compute minimum spanning tree using Prim's algorithm'''
-# for v in self.vertices:
-# v.weight = bound - 1
-# v.p = None
-# r.weight = 0
-# t = vEB_node(bound)
-# for u in self.vertices:
-# t.insert(u)
-# while t.size > 0:
-# u = t.minimum()
-# t.delete(u)
-# for v in self.adj[u]:
-# if t.member(v) and w(u, v) < v.weight:
-# v.p = u
-# t.delete(v)
-# v.weight = w(u, v)
-# t.insert(v)
+
+ # def Prim_vEB(self, w, r, bound):
+ # """G.Prim(weight, root) -- Given weight function
+ # and an arbitrary vertex root of the graph G,
+ # compute minimum spanning tree using Prim's algorithm"""
+ # for v in self.vertices:
+ # v.weight = bound - 1
+ # v.p = None
+ # r.weight = 0
+ # t = vEB_node(bound)
+ # for u in self.vertices:
+ # t.insert(u)
+ # while t.size > 0:
+ # u = t.minimum()
+ # t.delete(u)
+ # for v in self.adj[u]:
+ # if t.member(v) and w(u, v) < v.weight:
+ # v.p = u
+ # t.delete(v)
+ # v.weight = w(u, v)
+ # t.insert(v)
def Bellman_Ford(self, w, s):
- '''
+ """
The Bellman-Ford algorithm solves the single-source
shortest-paths problem in the general case in which edge
weights may be negative.
@@ -421,49 +445,53 @@ def Bellman_Ford(self, w, s):
no solution exists.
If there is no such cycle, this function returns True and produces
the shortest paths and their weights.
- '''
+ """
self.initialize_signle_source(s)
for i in range(1, len(self.vertices)):
- for u,v in self.edges:
+ for u, v in self.edges:
self.relax(u, v, w)
- for u,v in self.edges:
+ for u, v in self.edges:
if v.d > u.d + w(u, v):
return False
return True
+
def initialize_signle_source(self, s):
for v in self.vertices:
v.d = float("Inf")
v.p = None
s.d = 0
+
def relax(self, u, v, w):
if v.d > u.d + w(u, v):
v.d = u.d + w(u, v)
v.p = u
+
def Bellman_Ford_modified(self, w, s):
- '''
+ """
Given a weighted, directed graph G = (V, E) with
no negative-weight cycles, let m be the maximum
over all vertices v of the minimum number of edges
in a shortest path from the source s to v. This variant to
the Bellman-Ford algorithm terminates in m + 1 passes, even
if m is not known in advance.
- '''
+ """
modified = True
number = 0
self.initialize_signle_source(s)
for i in range(1, len(self.vertices)):
if modified:
- for u,v in self.edges:
+ for u, v in self.edges:
number = self.relax_modified(u, v, w) + number
if number == 0:
modified = False
number = 0
else:
break
- for u,v in self.edges:
+ for u, v in self.edges:
if v.d > u.d + w(u, v):
return False
return True
+
def relax_modified(self, u, v, w):
if v.d > u.d + w(u, v):
v.d = u.d + w(u, v)
@@ -471,18 +499,20 @@ def relax_modified(self, u, v, w):
return 1
else:
return 0
+
def dag_shortest_paths(self, w, s):
- '''
+ """
compute shortest paths from a single source
s for a directed acyclic graph with a weight function w
- '''
+ """
l = self.topological_sort()
self.initialize_signle_source(s)
for u in l:
for v in self.adj[u]:
self.relax(u, v, w)
+
def dag_shortest_paths_modified(self, s):
- '''
+ """
In the PERT chart analysis, vertices repre
sent jobs and edges represent sequencing
contraints; that is, edge (u, v) would
@@ -496,28 +526,30 @@ def dag_shortest_paths_modified(self, s):
vertices in linear time.
This function return a list of vertices in
a longest path
- '''
+ """
sink = Vertex("sink")
vertices = self.vertices.union({sink})
edges = self.edges.union(set([(v, sink) for v in G.vertices]))
Ga = Graph(vertices, edges)
Ga.dag_shortest_paths(lambda u, v: -u.weight, s)
u = sink
- l = []
- while u.p != None:
- l.append(u.p)
+ l = []
+ while u.p is not None:
+ l.append(u.p)
u = u.p
return l[::-1]
+
def total_path_number(self):
- '''
+ """
A algorithm to count the total number of paths in
a directed acyclic graph
- '''
+ """
number = 0
self._total_path_number_dfs()
for v in self.vertices:
number = number + v.num
return number
+
def _total_path_number_dfs(self):
global time
for u in self.vertices:
@@ -528,6 +560,7 @@ def _total_path_number_dfs(self):
for u in self.vertices:
if u.color == 0:
self._total_path_number_dfs_visit(u)
+
def _total_path_number_dfs_visit(self, u):
global time
time = time + 1
@@ -541,12 +574,13 @@ def _total_path_number_dfs_visit(self, u):
u.color = 2
time = time + 1
u.f = time
+
def Dijkstra(self, w, s):
- '''
+ """
Dijkstra's algorithm solves the single-source shortest-paths problem
on a weighted, directed graph G = (V, E) for the case in which all edge
weights are nonnegative.
- '''
+ """
self.initialize_signle_source(s)
S = set()
Q = min_priority_queue(self.vertices, 'd')
@@ -558,15 +592,16 @@ def Dijkstra(self, w, s):
v.d = u.d + w(u, v)
v.p = u
Q.heap_decrease_key(v.index, u.d + w(u, v))
+
def Dijkstra_modified(self, w, s, W):
- '''
+ """
A algorithm to the the case when the values of
the weight function w is in the range {0, 1, ..., W}
for some nonnegative integer W.
- '''
+ """
self.initialize_signle_source(s)
A = []
- for i in range(0, W * len(self.vertices) + 1):
+ for i in range(W * len(self.vertices) + 1):
A.append(set())
A[0].add(s)
i = 0
@@ -576,10 +611,10 @@ def Dijkstra_modified(self, w, s, W):
i = i + 1
if i > W * len(self.vertices):
break
- print "i = {}".format(i)
+ print("i = {}".format(i))
u = A[i].pop()
- print u
- print A[i]
+ print(u)
+ print(A[i])
S.add(u)
for v in self.adj[u]:
if v.d > u.d + w(u, v):
@@ -590,63 +625,64 @@ def Dijkstra_modified(self, w, s, W):
v.p = u
def single_edge(self):
- '''
+ """
An algorithm that given an adjacency-list representation
of a multigraph G = (V, E), compute the adjacency-list
representation of the "equivalent" undirected graph
G2 = (V, E2), where E2 consists of
the edges in E with all multiple edges between two vertices
replaced by a single edge and with all self-loops removed
- '''
- return Graph(self.vertices, self.edges, directed = False)
+ """
+ return Graph(self.vertices, self.edges, directed=False)
def union(self, G2):
if self.directed != G2.directed:
- print "The two graphs must be either both directed graphs or both undirected graphs"
+ print("The two graphs must be either both directed graphs or both undirected graphs")
return None
vertices = self.vertices | G2.vertices
edges = self.edges | G2.edges
- return Graph(vertices, edges, directed = self.directed)
+ return Graph(vertices, edges, directed=self.directed)
def square(self):
- '''
+ """
The square of a directed graph G = (V, E) is the graph
G^2 = (V, E^2) such that (u, v) belongs to E^2
if and only if G contains a path with at most
two edges between u and v.
- '''
+ """
sqrt = self.copy()
for u in self.vertices:
for v in self.adj[u]:
for w in self.adj[v]:
- sqrt._addEdge(u, w)
+ sqrt._add_edge(u, w)
return sqrt
def height(self, u):
maximum = 0
- print u.key
+ print(u.key)
for v in self.adj[u]:
if v.p == u:
maximum = max(maximum, self.height(v) + 1)
u.h = maximum
- print u.key, u.h
+ print(u.key, u.h)
return u.h
+
def mht(self):
s = next(iter(self.vertices))
self.bfs(s)
self.height(s)
s.mh = s.h
for u in self.adj[s]:
- self.mhtAux(u)
-
- def mhtAux(self, u):
+ self._mht_aux(u)
+
+ def _mht_aux(self, u):
u.mh = max(u.h, u.p.mh + 1)
for v in self.adj[u]:
if v.p == u:
- self.mhtAux(v)
-
+ self._mht_aux(v)
+
-class dsf_node(dsf.node):
+class DfsNode(dsf.node):
def __init__(self, key):
self.key = key
key.index = self
@@ -654,23 +690,29 @@ def __init__(self, key):
self.rank = 0
self.child = []
+
class max_heap(list):
def __init__(self, data, attr):
list.__init__(self, data)
- for i in range(0, len(data)):
+ for i in range(len(data)):
self[i].index = i
self.length = len(data)
self.attr = attr
self.heap_size = self.length
self.build_max_heap()
+
def __contains__(self, y):
return y in self[0:self.heap_size]
+
def left(self, i):
return 2 * i + 1
+
def right(self, i):
return 2 * i + 2
+
def parent(self, i):
- return (i - 1) / 2
+ return (i - 1) // 2
+
def max_heapify(self, i):
l = self.left(i)
r = self.right(i)
@@ -680,19 +722,22 @@ def max_heapify(self, i):
largest = i
if (r <= (self.heap_size - 1)) and (self[r].__dict__[self.attr] > self[largest].__dict__[self.attr]):
largest = r
- if largest != i:
- self[i],self[largest] = self[largest],self[i]
+ if largest != i:
+ self[i], self[largest] = self[largest], self[i]
self[i].index = i
self[largest].index = largest
self.max_heapify(largest)
+
def build_max_heap(self):
self.heap_size = self.length
- for i in range(self.length / 2 - 1, -1, -1):
+ for i in range(self.length // 2 - 1, -1, -1):
self.max_heapify(i)
+
class max_priority_queue(max_heap):
def heap_maximum(self):
return self[0]
+
def heap_extract_max(self):
if self.heap_size < 1:
sys.exit("heap underflow")
@@ -702,46 +747,54 @@ def heap_extract_max(self):
self.heap_size = self.heap_size - 1
self.max_heapify(0)
return maximum
+
def heap_increase_key(self, i, key):
if key < self[i].__dict__[self.attr]:
sys.exit("new key is smaller than current key")
self[i].__dict__[self.attr] = key
while i > 0 and self[self.parent(i)].__dict__[self.attr] < self[i].__dict__[self.attr]:
- self[i],self[self.parent(i)] = self[self.parent(i)], self[i]
+ self[i], self[self.parent(i)] = self[self.parent(i)], self[i]
self[i].index = i
self[self.parent(i)].index = self.parent(i)
i = self.parent(i)
+
def max_heap_insert(self, element):
if self.heap_size >= self.length:
sys.exit("heap overflow")
self.heap_size = self.heap_size + 1
self[self.heap_size - 1] = element
element.index = self.heap_size - 1
- key = element.__dict__[self.attr]
+ key = element.__dict__[self.attr]
element.__dict__[self.attr] = float("-Inf")
self.heap_increase_key(self.heap_size - 1, key)
+
class min_heap(list):
def __init__(self, data, attr):
- '''
+ """
data: input data for heap
attr: the attribute of input date used as compare key
- '''
+ """
list.__init__(self, data)
- for i in range(0, len(data)):
+ for i in range(len(data)):
self[i].index = i
self.attr = attr
self.length = len(data)
self.heap_size = self.length
self.build_min_heap()
+
def __contains__(self, y):
return y in self[0:self.heap_size]
+
def left(self, i):
return 2 * i + 1
+
def right(self, i):
return 2 * i + 2
+
def parent(self, i):
- return (i - 1) / 2
+ return (i - 1) // 2
+
def min_heapify(self, i):
l = self.left(i)
r = self.right(i)
@@ -751,19 +804,22 @@ def min_heapify(self, i):
smallest = i
if (r <= (self.heap_size - 1)) and (self[r].__dict__[self.attr] < self[smallest].__dict__[self.attr]):
smallest = r
- if smallest != i:
- self[i],self[smallest] = self[smallest],self[i]
+ if smallest != i:
+ self[i], self[smallest] = self[smallest], self[i]
self[i].index = i
self[smallest].index = smallest
self.min_heapify(smallest)
+
def build_min_heap(self):
self.heap_size = self.length
- for i in range(self.length / 2 - 1, -1, -1):
+ for i in range(self.length // 2 - 1, -1, -1):
self.min_heapify(i)
+
class min_priority_queue(min_heap):
def heap_minimum(self):
return self[0]
+
def heap_extract_min(self):
if self.heap_size < 1:
sys.exit("heap underflow")
@@ -773,15 +829,17 @@ def heap_extract_min(self):
self.heap_size = self.heap_size - 1
self.min_heapify(0)
return minimum
+
def heap_decrease_key(self, i, key):
if key > self[i].__dict__[self.attr]:
sys.exit("new key is larger than current key")
self[i].__dict__[self.attr] = key
while i > 0 and self[self.parent(i)].__dict__[self.attr] > self[i].__dict__[self.attr]:
- self[i],self[self.parent(i)] = self[self.parent(i)], self[i]
+ self[i], self[self.parent(i)] = self[self.parent(i)], self[i]
self[i].index = i
self[self.parent(i)].index = self.parent(i)
i = self.parent(i)
+
def min_heap_insert(self, element):
if self.heap_size >= self.length:
sys.exit("heap overflow")
@@ -791,4 +849,3 @@ def min_heap_insert(self, element):
key = element.__dict__[self.attr]
element.__dict__[self.attr] = float("Inf")
self.heap_decrease_key(self.heap_size - 1, key)
-
diff --git a/graph_test.py b/graph_test.py
deleted file mode 100644
index 215e941..0000000
--- a/graph_test.py
+++ /dev/null
@@ -1,651 +0,0 @@
-#!/usr/bin/env ipython
-import unittest
-from graph import Vertex, Graph
-
-class TestGraph(unittest.TestCase):
- def setUp(self):
- self.graphs = []
- v1 = Vertex(1)
- v2 = Vertex(2)
- v3 = Vertex(3)
- v4 = Vertex(4)
- v5 = Vertex(5)
- v6 = Vertex(6)
- self.v1 = v1
- self.v2 = v2
- self.v3 = v3
- self.v4 = v4
- self.v5 = v5
- self.v6 = v6
- vertices = [v1,v2,v3,v4,v5,v6]
- edges = [(v1, v2), (v1, v3), (v2, v3), (v2, v4), (v2, v5), (v3, v4), (v3, v6), (v4, v5), (v5, v6)]
- self.graphs.append(Graph(vertices, edges))
- edges = [(v1, v2), (v2, v3), (v3, v4), (v4, v2), (v3, v5), (v2, v4), (v4, v3)]
- self.graphs.append(Graph([v1, v2, v3, v4, v5], edges))
-
- def tearDown(self):
- pass
-
- def _buildGraph(self, keys, pairs, directed):
- d = dict()
- vertices = [None] * len(keys)
- edges = [None] * len(pairs)
- for i in range(len(vertices)):
- vertices[i] = Vertex(keys[i])
- d[keys[i]] = vertices[i]
-
- for i in range(len(edges)):
- w1, w2 = pairs[i]
- edges[i] = (d[w1], d[w2])
- return Graph(vertices, edges, directed)
-
- def testBfs(self):
- s = Vertex('s')
- r = Vertex('r')
- v = Vertex('v')
- w = Vertex('w')
- t = Vertex('t')
- x = Vertex('x')
- u = Vertex('u')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [v,r,s,w,t,x,u,y,z]
- edges = [(s, r), (s, w), (r, v), (r, s), (v, r), (w, s), (w, t), (w, x), (t, w), (t, x), (t, u), (u, t), (u, x), (u, y), (x, w), (x, t), (x, u), (x, y), (y, x), (y, u)]
- g = Graph(vertices, edges)
- #g.printAllEdges()
- #for i in g.vertices:
- # i.printEdge()
- # print
- g.bfs(s)
- # g.printVertices()
- self.assertEquals(s.d, 0)
- self.assertEquals(r.d, 1)
- self.assertEquals(v.d, 2)
- self.assertEquals(w.d, 1)
- self.assertEquals(t.d, 2)
- self.assertEquals(x.d, 2)
- self.assertEquals(u.d, 3)
- self.assertEquals(y.d, 3)
- def testDfs(self):
- s = Vertex('s')
- v = Vertex('v')
- z = Vertex('z')
- w = Vertex('w')
- y = Vertex('y')
- x = Vertex('x')
- t = Vertex('t')
- u = Vertex('u')
- #edges_list = [(z, w), (s, w), (y, w), (x, ), (x, ), (z, ), (v, u), (v, t)]
- #vertices = (s, v, z, w, y, x, t, u)
- #map(lambda vertex, edges: map(lambda vertex, edge: vertex.addEdge(edge), zip([vertex] * len(edges) , edges)), zip(vertices, edges_list))
- vertices = [s, v, z, w, y, x, t, u]
- edges = [(y, x), (x, z), (z, y), (z, w), (w, x), (s, z), (s, w), (v, w), (v, s), (t, v), (t, u), (u, v), (u, t)]
- g = Graph(vertices, edges)
- g.dfs()
- vertices = (s, v, z, w, y, x, t, u)
-# for u in vertices:
-# print u, u.d, u.f
- #df = [(1, 10), (12, 13), (2, 9), (7, 8), (3, 6), (4, 5), (11, 16), (14, 15)]
- #edges_list = [(z, w), (s, w), (y, w), (x, ), (x, ), (z, ), (v, u), (v, t)]
- def testPathNum(self):
- m = Vertex('m')
- n = Vertex('n')
- o = Vertex('o')
- p = Vertex('p')
- q = Vertex('q')
- r = Vertex('r')
- s = Vertex('s')
- t = Vertex('t')
- u = Vertex('u')
- v = Vertex('v')
- w = Vertex('w')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [m, n, o, p, q, r, s, t, u, v, w, x, y, z]
- edges = [(m, q), (m, r), (m, x), (n, q), (n, o), (n, u), (o, r), (o, s), (o, v), (p, o), (p, s), (p, z), (q, t), (r, u), (r, y), (s, r), (u, t), (v, w), (v, x), (w, z), (y, v)]
- g = Graph(vertices, edges)
- self.assertEquals(g.path_num(m, v), 1)
- self.assertEquals(g.path_num(n, v), 3)
- self.assertEquals(g.path_num(o, v), 3)
- self.assertEquals(g.path_num(p, v), 4)
- self.assertEquals(g.path_num(q, v), 0)
- self.assertEquals(g.path_num(r, v), 1)
- self.assertEquals(g.path_num(s, v), 1)
- self.assertEquals(g.path_num(t, v), 0)
- self.assertEquals(g.path_num(u, v), 0)
- self.assertEquals(g.path_num(v, v), 1)
- self.assertEquals(g.path_num(w, v), 0)
- self.assertEquals(g.path_num(x, v), 0)
- self.assertEquals(g.path_num(y, v), 1)
- self.assertEquals(g.path_num(z, v), 0)
-
- g = self.graphs[0]
- self.assertEquals(g.path_num(self.v1, self.v2), 1)
- self.assertEquals(g.path_num(self.v1, self.v3), 2)
- self.assertEquals(g.path_num(self.v1, self.v4), 3)
- self.assertEquals(g.path_num(self.v1, self.v5), 4)
- self.assertEquals(g.path_num(self.v1, self.v6), 6)
- self.assertEquals(g.path_num(self.v2, self.v1), 0)
- self.assertEquals(g.path_num(self.v2, self.v3), 1)
- self.assertEquals(g.path_num(self.v2, self.v4), 2)
- self.assertEquals(g.path_num(self.v2, self.v5), 3)
- self.assertEquals(g.path_num(self.v2, self.v6), 4)
- g = self.graphs[1]
- self.assertEquals(g.path_num(self.v1, self.v5), 1)
-
- def testSCC(self):
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- g = Vertex('g')
- h = Vertex('h')
- vertices = [a, b, c, d, e, f, g, h]
- edges = [(e, a), (a, b), (b, c), (d, c), (c, d), (b, e), (e, f), (b, f), (g, f), (f, g), (c, g), (g, h), (h, h)]
- G = Graph(vertices, edges)
- G.strongly_connected_components()
- self.assertEquals(a.cc, 1)
- self.assertEquals(b.cc, 1)
- self.assertEquals(c.cc, 2)
- self.assertEquals(d.cc, 2)
- self.assertEquals(e.cc, 1)
- self.assertEquals(f.cc, 3)
- self.assertEquals(g.cc, 3)
- self.assertEquals(h.cc, 4)
- def testSimplified(self):
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- g = Vertex('g')
- h = Vertex('h')
- vertices = [a, b, c, d, e, f, g, h]
- #edges = [(a, c), (b, a), (d, h), (d, f), (e, a), (a, b), (b, c), (d, c), (c, d), (b, e), (e, f), (b, f), (g, f), (f, g), (c, g), (g, h), (h, h)]
- edges = [(e, a), (a, b), (b, c), (d, c), (c, d), (b, e), (e, f), (b, f), (g, f), (f, g), (c, g), (g, h), (h, h)]
- G = Graph(vertices, edges)
- s = G.simplified()
-# for u in s.vertices:
-# print "u.key: {}, u.cc: {}".format(u.key, u.cc)
-# s.printEdge(u)
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- vertices = [a, b, c, d, e, f]
- edges = [(a, b), (b, a), (b, c), (b, d), (c, b), (d, b), (c, e), (b, e), (d, f), (e, f), (f, e)]
- G = Graph(vertices, edges)
- s = G.simplified()
- #for u in s.vertices:
- # print "u.key: {}, u.cc: {}".format(u.key, u.cc)
- # s.printEdge(u)
- def testComponentGraph(self):
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- g = Vertex('g')
- h = Vertex('h')
- vertices = [a, b, c, d, e, f, g, h]
- edges = [(e, a), (a, b), (b, c), (d, c), (c, d), (d, h), (b, e), (e, f), (b, f), (g, f), (f, g), (c, g), (g, h), (h, h)]
- G = Graph(vertices, edges)
- cg = G.component_graph()
-# print
-# for u in cg.vertices:
-# print "u.key: {}".format(u.key)
-# cg.printEdge(u)
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- vertices = [a, b, c, d, e, f]
- edges = [(a, b), (b, a), (b, c), (b, d), (c, b), (d, b), (c, e), (b, e), (d, f), (e, f), (f, e)]
- G = Graph(vertices, edges)
- cg = G.component_graph()
-# print "www"
-# print
-# for u in cg.vertices:
-# print "u.key: {}".format(u.key)
-# cg.printEdge(u)
- def testSemiconnected(self):
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- g = Vertex('g')
- h = Vertex('h')
- vertices = [a, b, c, d, e, f, g, h]
- edges = [(e, a), (a, b), (b, c), (d, c), (c, d), (d, h), (b, e), (e, f), (b, f), (g, f), (f, g), (c, g), (g, h), (h, h)]
- G = Graph(vertices, edges)
- self.assertEquals(G.semiconnected(), True)
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- vertices = [a, b, c, d, e, f]
- edges = [(a, b), (b, a), (b, c), (b, d), (c, b), (d, b), (c, e), (b, e), (d, f), (e, f), (f, e)]
- G = Graph(vertices, edges)
- self.assertEquals(G.semiconnected(), True)
- edges = [(a, b), (b, a), (b, c), (b, d), (c, b), (d, b), (e, f)]
- G = Graph(vertices, edges)
- self.assertEquals(G.semiconnected(), False)
- abe = Vertex('abe')
- cd = Vertex('cd')
- fg = Vertex('fg')
- h = Vertex('h')
- vertices = [abe, cd, fg, h]
- edges = [(abe, fg), (abe, cd), (fg, h), (cd, h), (cd, fg)]
- G = Graph(vertices, edges)
- self.assertEquals(G.semiconnected(), True)
- edges = [(abe, fg), (abe, cd), (fg, h), (cd, h)]
- G = Graph(vertices, edges)
- self.assertEquals(G.semiconnected(), False)
- edges = [(abe, fg), (abe, cd), (cd, h), (cd, fg)]
- G = Graph(vertices, edges)
- self.assertEquals(G.semiconnected(), False)
- edges = [(abe, fg), (abe, cd), (fg, h), (cd, fg)]
- G = Graph(vertices, edges)
- self.assertEquals(G.semiconnected(), True)
- edges = [(abe, cd), (fg, h), (cd, fg)]
- G = Graph(vertices, edges)
- self.assertEquals(G.semiconnected(), True)
- def testCut(self):
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- g = Vertex('g')
- h = Vertex('h')
- i = Vertex('i')
- vertices = [a, b, c, d, e, f, g, h, i]
- edges = [(a, b), (b, c), (b, h), (c, i), (d, c), (e, d), (f, d), (f, e), (f, c), (g, f), (g, h), (g, i), (h, a), (h, i)]
- G = Graph(vertices, edges, directed = False)
- #weight = [4, 8, 11, 2, 7, 9, 14, 10, 4, 2, 2, 1, 8, 7]
- weight = [4, 8, 11, 2, 7, 9, 14, 10, 4, 2, 1, 6, 8, 7]
- z = dict()
- for x,y in zip(edges, weight):
- z[x] = y
- z[(x[1], x[0])] = y
- def w(x, y):
- return z[(x, y)]
- G.cut(a, h, w)
- r1 = set()
- r2 = set()
- for u in G.vertices:
- if u.root == a:
- r1.add(u)
- else:
- r2.add(u)
- self.assertEquals(r1, set([a, b]))
- self.assertEquals(r2, set([h, i, g, c, f, d, e]))
-# for u in G.vertices:
-# print "u.key: {}, u.root = {}".format(u.key, u.root)
- def testKruskal(self):
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- g = Vertex('g')
- h = Vertex('h')
- i = Vertex('i')
- vertices = [a, b, c, d, e, f, g, h, i]
- edges = [(a, b), (a, h), (b, a), (b, c), (b, h), (c, b), (c, i), (c, f), (c, d), (d, c), (d, e), (d, f), (e, d), (e, f), (f, d), (f, e), (f, c), (f, g), (g, f), (g, h), (g, i), (h, a), (h, b), (h, i), (h, g), (i, c), (i, h), (i, g)]
- G = Graph(vertices, edges)
- weight = [4, 8, 4, 8, 11, 8, 2, 4, 7, 7, 9, 14, 9, 10, 14, 10, 4, 2, 2, 1, 6, 8, 11, 7, 1, 2, 7, 6]
- z = dict()
- for x,y in zip(edges, weight):
- z[x] = y
- print "{}: {}".format(x, y)
- def w(x, y):
- return z[(x, y)]
- ls = G.Kruskal(w)
- print ls
- def testPrim(self):
- a = Vertex('a')
- b = Vertex('b')
- c = Vertex('c')
- d = Vertex('d')
- e = Vertex('e')
- f = Vertex('f')
- g = Vertex('g')
- h = Vertex('h')
- i = Vertex('i')
- vertices = [a, b, c, d, e, f, g, h, i]
- #edges = [(a, b), (a, h), (b, a), (b, c), (b, h), (c, b), (c, i), (c, f), (c, d), (d, c), (d, e), (d, f), (e, d), (e, f), (f, d), (f, e), (f, c), (f, g), (g, f), (g, h), (g, i), (h, a), (h, b), (h, i), (h, g), (i, c), (i, h), (i, g)]
- #weight = [4, 8, 4, 8, 11, 8, 2, 4, 7, 7, 9, 14, 9, 10, 14, 10, 4, 2, 2, 1, 6, 8, 11, 7, 1, 2, 7, 6]
- edges = [(a, b), (b, c), (b, h), (c, i), (d, c), (e, d), (f, d), (f, e), (f, c), (g, f), (g, h), (g, i), (h, a), (h, i)]
- weight = [4, 8, 11, 2, 7, 9, 14, 10, 4, 2, 1, 6, 8, 7]
- G = Graph(vertices, edges, False)
- z = dict()
- for x,y in zip(edges, weight):
- z[x] = y
- z[(x[1], x[0])] = y
- #print "Prim edges: {}, weight: {}".format(x, y)
- def w(x, y):
- return z[(x, y)]
- G.Prim(w, i)
- s = set()
- for u in G.vertices:
- s.add((u.p, u))
-# self.assertEquals(s, set([(g, h), (f, g), (None, i), (c, d), (c, f), (i, c), (h, a), (d, e), (a, b)]))
- def testBellmanFord(self):
- s = Vertex('s')
- t = Vertex('t')
- y = Vertex('y')
- x = Vertex('x')
- z = Vertex('z')
- vertices = [s, t, y, x, z]
- edges = [(s, t), (s, y), (t, y), (t, x), (t, z), (y, x), (y, z), (x, t), (z, s), (z, x)]
- weight = [6, 7, 8, 5, -4, -3, 9, -2, 2, 7]
- G = Graph(vertices, edges)
- we = dict()
- for x,y in zip(edges, weight):
- we[x] = y
- def w(x, y):
- return we[(x, y)]
- G.Bellman_Ford(w, z)
- def testBellmanFordModified(self):
- s = Vertex('s')
- t = Vertex('t')
- u = Vertex('u')
- v = Vertex('v')
- x = Vertex('x')
- y = Vertex('y')
- vertices = [s, t, u, v, x, y]
- edges = [(s, t), (s, v), (s, x), (s, y), (t, u), (v, u)]
- weight = [1, 0, 3, 4, 2, 6]
- G = Graph(vertices, edges)
- we = dict()
- for i,j in zip(edges, weight):
- we[i] = j
- def w(x, y):
- return we[(x, y)]
-# G.Bellman_Ford(w, s)
- G.Bellman_Ford_modified(w, s)
- self.assertEquals([i.p for i in vertices], [None, s, t, s, s, s])
- self.assertEquals([i.d for i in vertices], [0, 1, 3, 0, 3, 4])
- r = Vertex('r')
- s = Vertex('s')
- t = Vertex('t')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [r, s, t, x, y, z]
- edges = [(r, s), (r, t), (s, t), (s, x), (t, x), (t, y), (t, z), (x, y), (x, z), (y, z)]
- weight = [5, 3, 2, 6, 7, 4, 2, -1, 1, -2]
- G = Graph(vertices, edges)
- we = dict()
- for i,j in zip(edges, weight):
- we[i] = j
- def w(x, y):
- return we[(x, y)]
- G.Bellman_Ford_modified(w, s)
- self.assertEquals([i.p for i in vertices], [None, None, s, s, x, y])
- self.assertEquals([i.d for i in vertices], [float("Inf"), 0, 2, 6, 5, 3])
- def testTopologicalSort(self):
- r = Vertex('r')
- s = Vertex('s')
- t = Vertex('t')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [r, s, t, x, y, z]
- edges = [(r, s), (r, t), (s, t), (s, x), (t, x), (t, y), (t, z), (x, y), (x, z), (y, z)]
- G = Graph(vertices, edges)
- l = G.topological_sort()
- self.assertEquals(l, [r, s, t, x, y, z])
-
- result = []
- l = [self.v1, self.v2, self.v3, self.v4, self.v5, self.v6]
- result.append(l)
- for i in range(len(self.graphs)):
- self.assertEquals(self.graphs[i].topological_sort(), result[i])
-
- def testDagShortestPaths(self):
- r = Vertex('r')
- s = Vertex('s')
- t = Vertex('t')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [r, s, t, x, y, z]
- edges = [(r, s), (r, t), (s, t), (s, x), (t, x), (t, y), (t, z), (x, y), (x, z), (y, z)]
- weight = [5, 3, 2, 6, 7, 4, 2, -1, 1, -2]
- G = Graph(vertices, edges)
- we = dict()
- for i,j in zip(edges, weight):
- we[i] = j
- def w(x, y):
- return we[(x, y)]
- G.dag_shortest_paths(w, s)
- self.assertEquals([i.p for i in vertices], [None, None, s, s, x, y])
- self.assertEquals([i.d for i in vertices], [float("Inf"), 0, 2, 6, 5, 3])
- G.dag_shortest_paths(w, r)
- self.assertEquals([i.p for i in vertices], [None, r, r, t, t, t])
- self.assertEquals([i.d for i in vertices], [0, 5, 3, 10, 7, 5])
- def TestDagShortestPathsModified(self):
- u = Vertex('u')
- v = Vertex('v')
- w = Vertex('w')
- z = Vertex('z')
- u.weight = 1
- v.weight = 2
- w.weight = 3
- z.weight = 4
- vertices = [u, v, w, z]
- edges = [(u, v), (v, w), (v, z)]
- G = Graph(vertices, edges)
- self.assertEquals(dag_shortest_paths_modified(G, u), [u, v, z])
- def testTotalPathNumber(self):
- r = Vertex('r')
- s = Vertex('s')
- t = Vertex('t')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [r, s, t, x, y, z]
- edges = [(r, s), (r, t), (s, t), (s, x), (t, x), (t, y), (t, z), (x, y), (x, z), (y, z)]
- weight = [5, 3, 2, 6, 7, 4, 2, -1, 1, -2]
- G = Graph(vertices, edges)
- number = G.total_path_number()
- self.assertEquals([i.num for i in vertices], [21, 12, 7, 3, 1, 0])
- self.assertEquals(number, 44)
- def testDijkstra(self):
- s = Vertex('s')
- t = Vertex('t')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [s, t, x, y, z]
- edges = [(s, t), (s, y), (t, x), (t, y), (x, z), (y, t), (y, x), (y, z), (z, s), (z, x)]
- g = Graph(vertices, edges)
- weight = [10, 5, 1, 2, 4, 3, 9, 2, 7, 6]
- we = dict()
- for i,j in zip(edges, weight):
- we[i] = j
- def w(x, y):
- return we[(x, y)]
- g.Dijkstra(w, s)
- self.assertEquals([i.p for i in vertices], [None, y, t, s, y])
- self.assertEquals([i.d for i in vertices], [0, 8, 9, 5, 7])
- s = Vertex('s')
- t = Vertex('t')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [s, t, x, y, z]
- edges = [(s, t), (s, y), (t, x), (t, y), (x, z), (y, t), (y, x), (y, z), (z, s), (z, x)]
- g = Graph(vertices, edges)
- weight = [3, 5, 6, 2, 2, 1, 4, 6, 3, 7]
- we = dict()
- for i,j in zip(edges, weight):
- we[i] = j
- def w(x, y):
- return we[(x, y)]
- g.Dijkstra(w, s)
- self.assertEquals([i.p for i in vertices], [None, s, t, s, y])
- self.assertEquals([i.d for i in vertices], [0, 3, 9, 5, 11])
- g.Dijkstra(w, z)
- self.assertEquals([i.p for i in vertices], [z, s, z, s, None])
- self.assertEquals([i.d for i in vertices], [3, 6, 7, 8, 0])
- def testDijkstraModified(self):
- s = Vertex('s')
- t = Vertex('t')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [s, t, x, y, z]
- edges = [(s, t), (s, y), (t, x), (t, y), (x, z), (y, t), (y, x), (y, z), (z, s), (z, x)]
- g = Graph(vertices, edges)
- weight = [10, 5, 1, 2, 4, 3, 9, 2, 7, 6]
- we = dict()
- for i,j in zip(edges, weight):
- we[i] = j
- def w(x, y):
- return we[(x, y)]
- g.Dijkstra_modified(w, s, 10)
- self.assertEquals([i.p for i in vertices], [None, y, t, s, y])
- self.assertEquals([i.d for i in vertices], [0, 8, 9, 5, 7])
- s = Vertex('s')
- t = Vertex('t')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
- vertices = [s, t, x, y, z]
- edges = [(s, t), (s, y), (t, x), (t, y), (x, z), (y, t), (y, x), (y, z), (z, s), (z, x)]
- g = Graph(vertices, edges)
- weight = [3, 5, 6, 2, 2, 1, 4, 6, 3, 7]
- we = dict()
- for i,j in zip(edges, weight):
- we[i] = j
- def w(x, y):
- return we[(x, y)]
- g.Dijkstra_modified(w, s, 7)
- self.assertEquals([i.p for i in vertices], [None, s, t, s, y])
- self.assertEquals([i.d for i in vertices], [0, 3, 9, 5, 11])
- g.Dijkstra_modified(w, z, 7)
- self.assertEquals([i.p for i in vertices], [z, s, z, s, None])
- self.assertEquals([i.d for i in vertices], [3, 6, 7, 8, 0])
-
- def testSingleEdge(self):
- a = Vertex(1)
- b = Vertex(2)
- c = Vertex(3)
- d = Vertex(4)
- vertices = [a, b, c, d]
- edges = [(a, b), (b, a), (a, c), (d, d)]
- G = Graph(vertices, edges)
- G2 = G.single_edge()
- edges = set([(a, b), (b, a), (a, c), (c, a)])
- vertices = set(vertices)
- self.assertEquals(G2.vertices, vertices)
- self.assertEquals(G2.edges, edges)
- self.assertEquals(G2.adj[a], {b, c})
- self.assertEquals(G2.adj[b], {a})
- self.assertEquals(G2.adj[c], {a})
- self.assertEquals(G2.adj[d], set())
-
- def testUnion(self):
- a = Vertex(1)
- b = Vertex(2)
- c = Vertex(3)
- d = Vertex(4)
- G1 = Graph([a, b, c], [(a, b), (a, c)])
- G2 = Graph([c, d], [(c, d)])
- G3 = G1.union(G2)
- self.assertEquals(G3.vertices, {a, b, c, d})
- self.assertEquals(G3.edges, {(a, b), (a, c), (c, d)})
- self.assertEquals(G3.adj[a], {b, c})
- self.assertEquals(G3.adj[b], set())
- self.assertEquals(G3.adj[c], {d})
- self.assertEquals(G3.adj[d], set())
- G1 = Graph([a, b, c], [(a, b), (a, c)], directed = False)
- G2 = Graph([c, d], [(c, d)], directed = False)
- G3 = G1.union(G2)
- self.assertEquals(G3.vertices, {a, b, c, d})
- self.assertEquals(G3.edges, {(a, b), (b, a), (a, c), (c, a), (c, d), (d, c)})
- self.assertEquals(G3.adj[a], {b, c})
- self.assertEquals(G3.adj[b], {a})
- self.assertEquals(G3.adj[c], {d, a})
- self.assertEquals(G3.adj[d], {c})
-
- def testCopy(self):
- a = Vertex(1)
- b = Vertex(2)
- c = Vertex(3)
- G1 = Graph([a, b, c], [(a, b), (a, c)])
- G2 = G1.copy()
- self.assertEquals(G1, G2)
-
- def testSquareGraph(self):
- a = Vertex(1)
- b = Vertex(2)
- c = Vertex(3)
- d = Vertex(4)
- G = Graph([a, b, c, d], [(a, b), (a, c), (c, d)])
- sqrt = G.square()
- self.assertEquals(sqrt.vertices, {a, b, c, d})
- self.assertEquals(sqrt.edges, {(a, b), (a, c), (a, d), (c, d)})
- self.assertEquals(sqrt.adj[a], {b, c, d})
- self.assertEquals(sqrt.adj[b], set())
- self.assertEquals(sqrt.adj[c], {d})
- self.assertEquals(sqrt.adj[d], set())
- a = Vertex(1)
- b = Vertex(2)
- c = Vertex(3)
- G = Graph([a, b, c], [(a, b), (b, c), (a, c)])
- sqrt = G.square()
- self.assertEquals(G, sqrt)
-
- def testMht(self):
- print "start mht"
- g = self.graphs[0]
- g.mht()
- print "height"
- print self.v1.h
- print self.v2.h
- print self.v3.h
- print self.v4.h
- print self.v5.h
- print self.v6.h
- print "height"
- print self.v1.mh
- print self.v2.mh
- print self.v3.mh
- print self.v4.mh
- print self.v5.mh
- print self.v6.mh
-# def testJohnson(self):
-# a1 = Vertex(1)
-# a2 = Vertex(2)
-# a3 = Vertex(3)
-# a4 = Vertex(4)
-# a5 = Vertex(5)
-# vertices = [a1, a2, a3, a4, a5]
-# edges = [(a1, a2), (a1, a3), (a1, a5), (a2, a4), (a2, a5), (a3, a2), (a4, a1), (a4, a3), (a5, a4)]
-# g = Graph(vertices, edges)
-# weight = [3, 8, -4, 1, 7, 4, 2, -5, 6]
-# we = dict()
-# for i,j in zip(edges, weight):
-# we[i] = j
-# def w(x, y):
-# return we[(x, y)]
-# g.Johnson(w)
diff --git a/hamiltonian_path.py b/hamiltonian_path.py
index 019db66..568c6a7 100644
--- a/hamiltonian_path.py
+++ b/hamiltonian_path.py
@@ -1,14 +1,16 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
+
def hamiltonian_path(G, u, v):
- '''An algorithm to the hamiltonian-path problem on directed acyclic graphs'''
+ """
+ An algorithm to the hamiltonian-path problem on directed acyclic graphs
+ """
we = dict()
for i in G.edges:
- we[i] = -1
+ we[i] = -1
+
def w(x, y):
- return we[(x, y)]
+ return we[(x, y)]
+
G.dag_shortest_paths(w, u)
- if abs(v.d) == len(G.vertices) - 1:
- return True
- else:
- return False
+ return abs(v.d) == len(G.vertices) - 1
diff --git a/hash.py b/hash.py
index 93f79a4..31a2505 100755
--- a/hash.py
+++ b/hash.py
@@ -1,26 +1,36 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
+
def hash_insert(T, k, h):
i = 0
while i < len(T):
j = h(k, i)
- if T[j] == None:
+ if T[j] is None:
T[j] = k
return j
else:
i = i + 1
+
+
def linear_probe(k, i):
return (aux(k) + i) % len(T)
+
+
def quad_probe(k, i):
return (aux(k) + i + 3 * i * i) % len(T)
+
+
def aux(k):
return k
+
+
def double_hashing(k, i):
return (k + i * (1 + k % (len(T) - 1))) % len(T)
-T = [None for i in range(0, 11)]
-print "length of T is ", len(T)
+
+T = [None] * 11
+print("length of T is ", len(T))
for i in 10, 22, 31, 4, 15, 28, 17, 88, 59:
- hash_insert(T, i, double_hashing)
+ hash_insert(T, i, double_hashing)
-print T
+print(T)
diff --git a/heap.py b/heap.py
index 04f5db1..c69b0fc 100644
--- a/heap.py
+++ b/heap.py
@@ -1,52 +1,70 @@
-class max_heap(list):
+class MaxHeap(list):
def __init__(self, data):
- list.__init__(self, data)
- self.length = len(data)
+ super().__init__(data)
+ self.length = len(self)
self.heap_size = self.length
self.build_max_heap()
- def left(self, i):
+
+ @staticmethod
+ def left(i):
return 2 * i + 1
- def right(self, i):
+
+ @staticmethod
+ def right(i):
return 2 * i + 2
- def parent(self, i):
- return (i - 1) / 2
+
+ @staticmethod
+ def parent(i):
+ return (i - 1) // 2
+
def max_heapify(self, i):
- l = self.left(i)
- r = self.right(i)
- if (l <= (self.heap_size - 1)) and (self[l] > self[i]):
- largest = l
+ left = self.left(i)
+ right = self.right(i)
+ if left < self.heap_size and self[left] > self[i]:
+ largest = left
else:
largest = i
- if (r <= (self.heap_size - 1)) and (self[r] > self[largest]):
- largest = r
- if largest != i:
- self[i],self[largest] = self[largest],self[i]
+ if right < self.heap_size and self[right] > self[largest]:
+ largest = right
+ if largest != i:
+ self[i], self[largest] = self[largest], self[i]
self.max_heapify(largest)
+
def build_max_heap(self):
self.heap_size = self.length
- for i in range(self.length / 2 - 1, -1, -1):
+ for i in range(self.length // 2 - 1, -1, -1):
self.max_heapify(i)
+
def heapsort(self):
self.build_max_heap()
for i in range(self.length - 1, 0, -1):
- self[0],self[i] = self[i],self[0]
+ self[0], self[i] = self[i], self[0]
self.heap_size = self.heap_size - 1
self.max_heapify(0)
-# print self
-class min_heap(list):
+
+
+class MinHeap(list):
def __init__(self, data):
- list.__init__(self, data)
- self.length = len(data)
+ super().__init__(data)
+ self.length = len(self)
self.heap_size = self.length
self.build_min_heap()
+
def __contains__(self, y):
- return y in self[0:self.heap_size]
- def left(self, i):
+ return y in self[:self.heap_size]
+
+ @staticmethod
+ def left(i):
return 2 * i + 1
- def right(self, i):
+
+ @staticmethod
+ def right(i):
return 2 * i + 2
- def parent(self, i):
- return (i - 1) / 2
+
+ @staticmethod
+ def parent(i):
+ return (i - 1) // 2
+
def min_heapify(self, i):
l = self.left(i)
r = self.right(i)
@@ -56,10 +74,11 @@ def min_heapify(self, i):
smallest = i
if (r <= (self.heap_size - 1)) and (self[r] < self[smallest]):
smallest = r
- if smallest != i:
- self[i],self[smallest] = self[smallest],self[i]
+ if smallest != i:
+ self[i], self[smallest] = self[smallest], self[i]
self.min_heapify(smallest)
+
def build_min_heap(self):
self.heap_size = self.length
- for i in range(self.length / 2 - 1, -1, -1):
+ for i in range(self.length // 2 - 1, -1, -1):
self.min_heapify(i)
diff --git a/heap_test.py b/heap_test.py
deleted file mode 100644
index 9c16baa..0000000
--- a/heap_test.py
+++ /dev/null
@@ -1,34 +0,0 @@
-import unittest
-from heap import max_heap, min_heap
-
-class TestHeap(unittest.TestCase):
-# def test_init(self):
-# a = heap([4, 1, 3, 2, 16, 9, 10, 14, 8, 7])
-# self.assertEquals(a.__heap, a)
-# self.assertEquals(a.__length, 10)
-# self.assertEquals(a.__heap_size, 10)
- def test_max_heapify(self):
- a = [16, 4, 10, 14, 7, 9, 3, 2, 8, 1]
- h = max_heap(a)
- h.max_heapify(1)
- self.assertEquals(h, [16, 14, 10, 8, 7, 9, 3, 2, 4, 1])
- def test_build_max_heap(self):
- a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
- h = max_heap(a)
- h.build_max_heap()
- self.assertEquals(h, [16, 14, 10, 8, 7, 9, 3, 2, 4, 1])
- def test_heapsort(self):
- a = [4, 1, 3, 3, 16, 9, 10, 14, 8, 7]
- h = max_heap(a)
- h.heapsort()
- self.assertEquals(h, [1, 3, 3, 4, 7, 8, 9, 10, 14, 16])
- def test_min_heapify(self):
- a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
- h = min_heap(a)
- h.min_heapify(1)
- self.assertEquals(h, [1, 2, 3, 4, 7, 8, 9, 10, 14, 16])
- def test_build_min_heap(self):
- a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
- h = min_heap(a)
- h.build_min_heap()
- self.assertEquals(h, [1, 2, 3, 4, 7, 8, 9, 10, 14, 16])
diff --git a/huffman.py b/huffman.py
index 90857b7..6b89cbb 100644
--- a/huffman.py
+++ b/huffman.py
@@ -1,104 +1,125 @@
-from priority_queue import min_priority_queue
-class Min_priority_queue(min_priority_queue):
+from priority_queue import MinPriorityQueue
+import sys
+
+
+class Min_priority_queue(MinPriorityQueue):
def min_heap_insert(self, key):
if self.heap_size >= self.length:
sys.exit("heap overflow")
self.heap_size = self.heap_size + 1
self.heap[self.heap_size - 1] = node(None, None, float("Inf"))
self.heap_decrease_key(self.heap_size - 1, key)
-class character(object):
- def __init__(self, char, freq, sibling = None):
+
+
+class character:
+ def __init__(self, char, freq, sibling=None):
self.char = char
self.freq = freq
self.sibling = sibling
+
def __eq__(self, y):
- if self.freq == y.freq:
- return True
+ return self.freq == y.freq
+
def __gt__(self, y):
- if self.freq > y.freq:
- return True
+ return self.freq > y.freq
+
def __ge__(self, y):
- if self.freq >= y.freq:
- return True
+ return self.freq >= y.freq
+
def __le__(self, y):
- if self.freq <= y.freq:
- return True
+ return self.freq <= y.freq
+
def __lt__(self, y):
- if self.freq < y.freq:
- return True
-class node(object):
+ return self.freq < y.freq
+
+
+class node:
def __init__(self, left, right, freq):
self.left = left
- self.right =right
+ self.right = right
self.freq = freq
+
def __eq__(self, y):
- if self.freq == y.freq:
- return True
+ return self.freq == y.freq
+
def __gt__(self, y):
- if self.freq > y.freq:
- return True
+ return self.freq > y.freq
+
def __ge__(self, y):
- if self.freq >= y.freq:
- return True
+ return self.freq >= y.freq
+
def __le__(self, y):
- if self.freq <= y.freq:
- return True
+ return self.freq <= y.freq
+
def __lt__(self, y):
- if self.freq < y.freq:
- return True
-class tenary_node(object):
- def __init__(self, freq, child = None, sibling = None):
+ return self.freq < y.freq
+
+
+class tenary_node:
+ def __init__(self, freq, child=None, sibling=None):
self.freq = freq
self.child = child
self.sibling = sibling
+
def __eq__(self, y):
- if self.freq == y.freq:
- return True
+ return self.freq == y.freq
+
def __gt__(self, y):
- if self.freq > y.freq:
- return True
+ return self.freq > y.freq
+
def __ge__(self, y):
- if self.freq >= y.freq:
- return True
+ return self.freq >= y.freq
+
def __le__(self, y):
- if self.freq <= y.freq:
- return True
+ return self.freq <= y.freq
+
def __lt__(self, y):
- if self.freq < y.freq:
- return True
+ return self.freq < y.freq
+
+
def huffman(chars, freqs):
n = len(chars)
c = [0] * n
- for i in range(0, n):
+ for i in range(n):
c[i] = character(chars[i], freqs[i])
q = Min_priority_queue(c)
- for i in range(0, n - 1):
+ for i in range(n - 1):
x = q.heap_extract_min()
y = q.heap_extract_min()
q.min_heap_insert(node(x, y, x.freq + y.freq))
return q.heap_extract_min()
+
+
def print_code(root):
print_code_aux(root, '')
+
+
def print_code_aux(node, s):
if hasattr(node, "left"):
- print_code_aux(node.left, s + '0')
print_code_aux(node.right, s + '1')
+ print_code_aux(node.left, s + '0')
else:
- print "character: {}\tfrequency: {}\tcode: {}".format(node.char, node.freq, s)
+ print("character: {}\tfrequency: {}\tcode: {}".format(node.char, node.freq, s))
+
+
def compact_store_prefix_code(root):
store = []
compact_store_prefix_code_aux(root, store, '')
return store
+
+
def compact_store_prefix_code_aux(node, store, string):
if hasattr(node, "left"):
compact_store_prefix_code_aux(node.left, store, string + '0')
compact_store_prefix_code_aux(node.right, store, '1')
else:
store.append((node.char, string))
+
+
def decode_compact_prefix_code(store):
code = ''
pos = 0
- for i in range(0, len(store)):
+ for i in range(len(store)):
last_len = len(code)
char = store[i][1][0]
for pos in range(last_len - 1, -1, -1):
@@ -108,14 +129,18 @@ def decode_compact_prefix_code(store):
code = store[i][1]
else:
code = code[0:pos] + store[i][1]
- print "char: {}, code: {}".format(store[i][0], code)
+ print("char: {}, code: {}".format(store[i][0], code))
+
+
def huffman_tenary(chars, freqs, m):
- ''' generalize Huffman's algorithm to tenary codewords
+ """
+ generalize Huffman's algorithm to tenary codewords
the parameter m is the number of symbols we use, eg, in
- original huffman algorithm, we use 0 and 1, so m = 2'''
+ original huffman algorithm, we use 0 and 1, so m = 2
+ """
n = len(chars)
c = [0] * n
- for i in range(0, n):
+ for i in range(n):
c[i] = character(chars[i], freqs[i])
q = Min_priority_queue(c)
while q.heap_size >= m:
@@ -131,19 +156,23 @@ def huffman_tenary(chars, freqs, m):
return q.heap_extract_min()
x = q.heap_extract_min()
z = tenary_node(x.freq, x)
- while q.heap_size > 0:
+ while q.heap_size > 0:
y = q.heap_extract_min()
x.sibling = y
z.freq = z.freq + y.freq
x = y
q.min_heap_insert(z)
return q.heap_extract_min()
+
+
def print_huffman_tenary(root):
print_huffman_tenary_aux(root, '', '')
+
+
def print_huffman_tenary_aux(node, string, sibling):
if hasattr(node, "child"):
- print_huffman_tenary_aux(node.child, string + str(sibling), 0)
+ print_huffman_tenary_aux(node.child, string + str(sibling), 0)
else:
- print "character: {}\tfrequency: {}\tcode: {}".format(node.char, node.freq, string + str(sibling))
- if node.sibling != None:
+ print("character: {}\tfrequency: {}\tcode: {}".format(node.char, node.freq, string + str(sibling)))
+ if node.sibling:
print_huffman_tenary_aux(node.sibling, string, sibling + 1)
diff --git a/insertion-sort-noninc.c b/insertion-sort-noninc.c
deleted file mode 100644
index 5056843..0000000
--- a/insertion-sort-noninc.c
+++ /dev/null
@@ -1,16 +0,0 @@
-#include
-//Sort into nonincreasing order
-void insertionsort(int s[], int length) {
- int j, i;
- int key;
-
- for (j = 1; j < length; j++) {
- key = s[j];
- for (i = j - 1; i >= 0 && s[i] < key; i--)
- s[i+1] = s[i];
- s[i+1] = key;
- for (i = 0; i < length; i++)
- printf("%d ", s[i]);
- printf("\n");
- }
-}
diff --git a/insertion-sort-rec.c b/insertion-sort-rec.c
deleted file mode 100644
index cd91cde..0000000
--- a/insertion-sort-rec.c
+++ /dev/null
@@ -1,48 +0,0 @@
-#include
-// recursive version of insertion sort
-
-void swap(int *a, int *b)
-{
- int tmp = *a;
-
- *a = *b;
- *b = tmp;
-}
-
-void Insert(int A[], int n)
-{
- int i;
-
- for (i = n - 1; i >= 0; i--)
- if (A[i] > A[i + 1])
- swap(A + i, A + i + 1);
- else
- return;
-}
-
-void InsSort(int A[], int n)
-{
- if (n > 1)
- {
- InsSort(A, n - 1);
- Insert(A, n);
- }
- else if (n == 1)
- {
- if (A[0] > A[1])
- swap(A, A + 1);
- return;
- }
- else if (n == 0)
- return;
-}
-
-int main()
-{
- int a[8] = { 8, 8, 3, 65, 500, 3, -1, 3 };
-
- InsSort(a, 7);
- printf("%d,%d,%d,%d,%d,%d,%d, %d\n", a[0], a[1], a[2], a[3], a[4], a[5],
- a[6], a[7]);
- return 0;
-}
diff --git a/insertion-sort.c b/insertion-sort.c
deleted file mode 100644
index 870d9ff..0000000
--- a/insertion-sort.c
+++ /dev/null
@@ -1,26 +0,0 @@
-#include
-//INSERTION-SORT(A)
- //for j = 2 to A.length
- //key = A[j]
- ////Insert A[j] into the sorted sequence A[1..j - 1].
- //i = j - 1
- //while i > 0 and A[i] > key
- //A[i + 1] = A[i]
- //i = i - 1
- //A[i + 1] = key
-
-//Sort into nondecreasing order
-void insertionsort(int s[], int length) {
- int j, i;
- int key;
-
- for (j = 1; j < length; j++) {
- key = s[j];
- for (i = j - 1; i >= 0 && s[i] > key; i--)
- s[i+1] = s[i];
- s[i+1] = key;
-// for (i = 0; i < length; i++)
-// printf("%d ", s[i]);
-// printf("\n");
- }
-}
diff --git a/insertion_sort.py b/insertion_sort.py
index 75b9716..25e1cf4 100644
--- a/insertion_sort.py
+++ b/insertion_sort.py
@@ -1,9 +1,64 @@
-def insertion_sort(A):
- for j in range(1, len(A)):
- key = A[j]
- i = j - 1
- while i >= 0 and key < A[i]:
- A[i + 1] = A[i]
- i = i - 1
- A[i + 1] = key
+from binary_search import bisect_right
+
+def insert_with_linear_search(array, left_index, right_index):
+ """
+ Use linear search to find a position in already sorted array[left_index...right_index-1] to insert array[right_index] into,
+ making array[left_index...right_index] a sorted array.
+ :param array:
+ :param left_index:
+ :param right_index: right_index > 0
+ :return:
+ """
+ key = array[right_index]
+ i = right_index - 1
+ while i >= left_index and key < array[i]:
+ array[i + 1] = array[i]
+ i = i - 1
+ array[i + 1] = key
+
+
+def insert_with_binary_search(array, left_index, right_index):
+ """
+ Use binary search to find a position in already sorted array[left_index...right_index-1] to insert array[right_index] into,
+ making array[left_index...right_index] a sorted array.
+ :param array:
+ :param left_index:
+ :param right_index: right_index > 0
+ :return:
+ """
+ x = array[right_index]
+ index = bisect_right(array, x, left_index, right_index)
+ array[index + 1: right_index + 1] = array[index: right_index]
+ array[index] = x
+
+
+def insertion_sort(array, left=0, right=None, insert_method=insert_with_linear_search):
+ """
+ inplace sort O(n ^ 2) sort
+ :param array:
+ :param left:
+ :param right:
+ :param insert_method:
+ :return:
+ """
+ if right is None:
+ right = len(array) - 1
+ for j in range(left, right + 1):
+ insert_method(array, 0, j)
+
+
+def _insertion_sort_recursive(array, length, insert_method):
+ if length > 1:
+ _insertion_sort_recursive(array, length - 1, insert_method)
+ insert_method(array, 0, length - 1)
+
+
+def insertion_sort_recursive(array, insert_method=insert_with_linear_search):
+ """
+ recursive version of insertion sort
+ :param array:
+ :param insert_method:
+ :return:
+ """
+ _insertion_sort_recursive(array, len(array), insert_method)
diff --git a/interpolation.py b/interpolation.py
index 5c228bc..9003511 100644
--- a/interpolation.py
+++ b/interpolation.py
@@ -1,7 +1,8 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import synthetic_division as di
+
def roots_interpolation(roots, n):
A = [0] * (n + 1)
if n == 1:
@@ -17,21 +18,22 @@ def roots_interpolation(roots, n):
A[0] = -1 * x * B[0]
return A
+
def Lagrange_interpolation(X, Y, n):
R = roots_interpolation(X, n)
-# print "length of R is {}".format(len(R))
+ # print( "length of R is {}".format(len(R)))
A = [0] * n
- for k in range(0, n):
+ for k in range(n):
q, re = di.synthetic_division(R, n + 1, X[k])
-# print q
- # print "length of q is {}".format(len(q))
+ # print( q)
+ # print( "length of q is {}".format(len(q)))
m = 1.0
- for j in range(0, n):
+ for j in range(n):
if j != k:
m = m * (X[k] - X[j])
- # print "m = {}".format(m)
+ # print( "m = {}".format(m))
m = Y[k] / m
- # print "m = {}".format(m)
- for j in range(0, n):
+ # print( "m = {}".format(m))
+ for j in range(n):
A[j] = A[j] + q[j] * m
return A
diff --git a/interval_graph_coloring.py b/interval_graph_coloring.py
index 2125273..0766480 100644
--- a/interval_graph_coloring.py
+++ b/interval_graph_coloring.py
@@ -1,10 +1,12 @@
def interval_graph_coloring(graph):
- '''The input graph is represented as an adjacency matrix since all we need is edge information about the graph'''
+ """
+ The input graph is represented as an adjacency matrix since all we need is edge information about the graph
+ """
m = graph.shape[0]
color = [1] * m
number = 1
- for i in range(0, m):
- for j in range(0, m):
+ for i in range(m):
+ for j in range(m):
if graph[i, j] == 1 and color[i] == color[j]:
color[j] = color[i] + 1
if color[j] > number:
diff --git a/interval_tree.py b/interval_tree.py
index a4fcf41..6795419 100755
--- a/interval_tree.py
+++ b/interval_tree.py
@@ -1,21 +1,24 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-from rb_tree import rb_node, rb_tree
+from rb_tree import RbNode, RbTree
-class interval(object):
+
+class interval:
def __init__(self, low, high):
self.low = low
self.high = high
-class interval_node(rb_node):
+
+
+class interval_node(RbNode):
def __init__(self, key, p, left, right, color, interval, maximum):
- rb_node.__init__(self, key, p, left, right, color)
+ RbNode.__init__(self, key, p, left, right, color)
self.interval = interval
self.maximum = maximum
def list_all_overlapping_intervals(self, T, i):
x = self
if x.interval.high >= i.low and i.high >= x.interval.low:
- print x.interval.low, x.interval.high
+ print(x.interval.low, x.interval.high)
if x.left != T.nil and x.left.maximum >= i.low:
self.left.list_all_overlapping_intervals(T, i)
self.right.list_all_overlapping_intervals(T, i)
@@ -23,7 +26,7 @@ def list_all_overlapping_intervals(self, T, i):
self.right.list_all_overlapping_intervals(T, i)
def interval_search_exactly(self, T, i):
- if self.interval.low == i.low and self.interval.high == i.high:
+ if self.interval.low == i.low and self.interval.high == i.high:
return self
if self.interval.low > i.low:
if self.left != T.nil:
@@ -36,17 +39,19 @@ def interval_search_exactly(self, T, i):
else:
return T.nil
-
-class interval_tree(rb_tree):
+class interval_tree(RbTree):
nil = interval_node(None, None, None, None, 1, None, float("-Inf"))
root = nil
+
def __init__(self, intervals):
if isinstance(intervals, list):
for i in intervals:
- self.insert(interval_node(i.low, None, None, None, 0, i, i.high))
+ self.insert(interval_node(
+ i.low, None, None, None, 0, i, i.high))
else:
- print "Not invalid argument"
+ print("Not invalid argument")
+
def insert(self, z):
y = self.nil
x = self.root
@@ -67,8 +72,9 @@ def insert(self, z):
z.p = y
z.left = self.nil
z.right = self.nil
- z.color = 0 #red
+ z.color = 0 # red
self.insert_fixed(z)
+
def left_rotate(self, x):
y = x.right
x.right = y.left
@@ -85,6 +91,7 @@ def left_rotate(self, x):
x.p = y
y.maximum = x.maximum
x.maximum = max(x.left.maximum, x.interval.high, x.right.maximum)
+
def right_rotate(self, y):
x = y.left
y.left = x.right
@@ -101,6 +108,7 @@ def right_rotate(self, y):
y.p = x
x.maximum = y.maximum
y.maximum = max(y.left.maximum, y.interval.high, y.right.maximum)
+
def delete(self, z):
y = z
y_original_color = y.color
@@ -126,7 +134,8 @@ def delete(self, z):
y.color = z.color
traverse = x.p
while traverse != self.nil:
- traverse.maximum = max(traverse.left.maximum, traverse.interval.high, traverse.right.maximum)
+ traverse.maximum = max(
+ traverse.left.maximum, traverse.interval.high, traverse.right.maximum)
traverse = traverse.p
if y_original_color == 1:
self.delete_fixup(x)
@@ -141,8 +150,10 @@ def closed_interval_search(self, interval):
return x
def closed_interval_search_minimum_low_end(self, interval):
- '''given an interval, returns an interval over-
- lapping i that has the minimum low endpoint, or T.nil if no such interval exists'''
+ """
+ given an interval, returns an interval over-
+ lapping i that has the minimum low endpoint, or T.nil if no such interval exists
+ """
x = self.root
overlap = False
i = self.nil
@@ -168,11 +179,11 @@ def open_interval_search(self, interval):
return x
def list_all_overlapping_intervals(self, i):
- if self.root == self.nil:
+ if self.root == self.nil:
return
else:
self.root.list_all_overlapping_intervals(self, i)
- print
+ print()
def interval_search_exactly(self, i):
if self.root == self.nil:
diff --git a/inversion.c b/inversion.c
deleted file mode 100644
index 0a96704..0000000
--- a/inversion.c
+++ /dev/null
@@ -1,81 +0,0 @@
-// This program determines the number of inversions in
-// any permution on n elements using a global variable invs
-#include
-#include
-#include
-
- // MERGE(A, p, q, r)
- // n1 = q - p + 1
- // n2 = r - q
- // L[1...n1] = A[p...q]
- // R[1...n2] = A[q+1...r]
- // L[n1+1] = ∞
- // R[n2+1] = ∞
- // i = 1
- // j = 1
- // for k = p to r
- // if L[i] <= R[j]
- // A[k] = L[i]
- // i = i + 1
- // else
- // A[k] = R[j]
- // j = j + 1
-static int invs = 0;
-
-static void combine(int B[], int first, int inter, int end)
-{
- int len1 = inter - first + 1;
- int len2 = end - inter;
- int i;
- int j;
- int k;
- int *L;
- int *R;
-
- L = (int *)calloc(len1 + 1, sizeof(int));
- R = (int *)calloc(len2 + 1, sizeof(int));
- for (i = 0; i < len1; i++)
- L[i] = B[first + i];
- for (j = 0; j < len2; j++)
- R[j] = B[inter + j + 1];
- L[len1] = INT_MAX;
- R[len2] = INT_MAX;
-
- i = 0;
- j = 0;
- for (k = first; k <= end; k++)
- {
- if (L[i] <= R[j])
- B[k] = L[i++]; else { B[k] = R[j++];
- invs = invs + len1 - i;
- }
-
- }
- free(L);
- free(R);
-}
-
-static void divide(int B[], int first, int end)
-{
- if (first < end)
- {
- int middle = (first + end) / 2;
-
- divide(B, first, middle);
- divide(B, middle + 1, end);
- combine(B, first, middle, end);
- }
-}
-
-int inversion(int A[], int first, int end) {
- int i;
- int *B = (int *) calloc(end - first + 1, sizeof(int));
-
- for (i = first; i <= end; i++)
- B[i] = A[i];
- divide(B, first, end);
- free(B);
- i = invs;
- invs = 0;
- return i;
-}
diff --git a/inversion.py b/inversion.py
new file mode 100644
index 0000000..8ebff46
--- /dev/null
+++ b/inversion.py
@@ -0,0 +1,84 @@
+#!/usr/bin/env python
+# encoding: utf-8
+
+
+def inversion_with_insertion_sort(array):
+ """
+ Count number of inversions of an array using insertion sort
+
+ Let A[1...n] be an array of n numbers. If i < j and A[i] > A[j] ,
+ then the pair (i, j) is called an inversion_with_insertion_sort of A
+ :param array:
+ :return:
+ """
+ array = array[:]
+ return _inversion_with_insertion_sort(array)
+
+
+def _inversion_with_insertion_sort(array):
+ """
+ :param array:
+ :return:
+ """
+ inverse = 0
+ for j in range(1, len(array)):
+ key = array[j]
+ i = j - 1
+ while i >= 0 and key < array[i]:
+ inverse += 1
+ array[i + 1] = array[i]
+ i = i - 1
+ array[i + 1] = key
+ return inverse
+
+
+def inversion_with_merge_sort(array):
+ """
+ Count number of inversions of an array using merge sort
+
+ Let A[1...n] be an array of n numbers. If i < j and A[i] > A[j] ,
+ then the pair (i, j) is called an inversion_with_insertion_sort of A
+ :param array:
+ :return:
+ """
+ array = array[:]
+ return _inversion_with_merge_sort(array, 0, len(array) - 1)
+
+
+def _inversion_with_merge_sort(array, left, right):
+ if left < right:
+ mid = (left + right) // 2
+ left_inverse = _inversion_with_merge_sort(array, left, mid)
+ right_inverse = _inversion_with_merge_sort(array, mid + 1, right)
+ inter_inverse = _merge(array, left, mid, right)
+ return left_inverse + right_inverse + inter_inverse
+ else:
+ return 0
+
+
+def _merge(array, left, mid, right):
+ """
+
+ :param array:
+ :param left:
+ :param mid:
+ :param right:
+ :return:
+ """
+ left_part = array[left: mid + 1]
+ left_part.append(float("Inf"))
+ right_part = array[mid + 1: right + 1]
+ right_part.append(float("Inf"))
+ i = 0
+ j = 0
+ inverse = 0
+ for k in range(left, right + 1):
+ if left_part[i] <= right_part[j]:
+ array[k] = left_part[i]
+ i = i + 1
+ else:
+ array[k] = right_part[j]
+ j = j + 1
+ inverse += (mid - left + 1 - i)
+ return inverse
+
diff --git a/inversion2.c b/inversion2.c
deleted file mode 100644
index a645192..0000000
--- a/inversion2.c
+++ /dev/null
@@ -1,87 +0,0 @@
-// This program determines the number of inversions in
-// any permution on n elements
-// This version no longer uses global variable. It is more 'divide and conquer' than inversion.c
-#include
-#include
-#include
-
- // MERGE(A, p, q, r)
- // n1 = q - p + 1
- // n2 = r - q
- // L[1...n1] = A[p...q]
- // R[1...n2] = A[q+1...r]
- // L[n1+1] = ∞
- // R[n2+1] = ∞
- // i = 1
- // j = 1
- // for k = p to r
- // if L[i] <= R[j]
- // A[k] = L[i]
- // i = i + 1
- // else
- // A[k] = R[j]
- // j = j + 1
-
-static int combine(int B[], int first, int inter, int end)
-{
- int len_left = inter - first + 1;
- int len_right = end - inter;
- int i;
- int j;
- int k;
- int *L;
- int *R;
- int invs_cross = 0;
-
- L = (int *)calloc(len_left + 1, sizeof(int));
- R = (int *)calloc(len_right + 1, sizeof(int));
- for (i = 0; i < len_left; i++)
- L[i] = B[first + i];
- for (j = 0; j < len_right; j++)
- R[j] = B[inter + j + 1];
- L[len_left] = INT_MAX;
- R[len_right] = INT_MAX;
-
- i = 0;
- j = 0;
- for (k = first; k <= end; k++)
- {
- if (L[i] <= R[j])
- B[k] = L[i++];
- else {
- B[k] = R[j++];
- invs_cross = invs_cross + len_left - i;
- }
-
- }
- free(L);
- free(R);
- return invs_cross;
-}
-
-int divide(int B[], int first, int end)
-{
- int invs_left, invs_right, invs_cross;
-
- if (first < end)
- {
- int middle = (first + end) / 2;
-
- invs_left = divide(B, first, middle);
- invs_right = divide(B, middle + 1, end);
- invs_cross = combine(B, first, middle, end);
- return invs_left + invs_right + invs_cross;
- }
- return 0;
-}
-
-int inversion(int A[], int first, int end) {
- int i;
- int *B = (int *) calloc(end - first + 1, sizeof(int));
-
- for (i = first; i <= end; i++)
- B[i] = A[i];
- i = divide(B, first, end);
- free(B);
- return i;
-}
diff --git a/inversion_tree.py b/inversion_tree.py
index e02fa8d..97f818f 100644
--- a/inversion_tree.py
+++ b/inversion_tree.py
@@ -10,8 +10,8 @@ def inversion(A):
i = i + 1
x = rank_node(key, None, None, None, 0, 1)
T.insert(x)
- # print 'x.key = {}, x.rank = {}'.format(x.key, x.rank)
+ # print( 'x.key = {}, x.rank = {}'.format(x.key, x.rank))
inversion = inversion + i - x.rank
return inversion
else:
- print "Not invalid argument"
+ print("Not invalid argument")
diff --git a/k_way_merge.py b/k_way_merge.py
index af45cf1..f014ba6 100644
--- a/k_way_merge.py
+++ b/k_way_merge.py
@@ -28,13 +28,17 @@ def merge(list1, list2):
def k_way_merge(lists):
- '''Merge k sorted lists and return it as one sorted list'''
+ """
+ Merge k sorted lists and return it as one sorted list
+ :param lists:
+ :return:
+ """
length = len(lists)
if length == 1:
return lists[0]
elif length == 2:
return merge(lists[0], lists[1])
else:
- list1 = k_way_merge(lists[0:length / 2])
- list2 = k_way_merge(lists[length / 2 : length])
+ list1 = k_way_merge(lists[:length // 2])
+ list2 = k_way_merge(lists[length // 2:])
return merge(list1, list2)
diff --git a/k_way_merge_test.py b/k_way_merge_test.py
deleted file mode 100644
index 3245415..0000000
--- a/k_way_merge_test.py
+++ /dev/null
@@ -1,16 +0,0 @@
-#!/usr/bin/env ipython
-import unittest
-import random
-from k_way_merge import k_way_merge
-
-class TestKWayMerge(unittest.TestCase):
- def test_k_way_merge(self):
- for j in range(0, 10000):
- A = [random.randint(1, 10000) for i in range(0, 100)]
- lists = [None] * 10
- for i in range(0, 10):
- lists[i] = A[10 * i : (i + 1) * 10]
- lists[i].sort()
- A.sort()
- self.assertEquals(k_way_merge(lists), A)
-
diff --git a/kleene_star.py b/kleene_star.py
index 8a21a21..c7238fd 100644
--- a/kleene_star.py
+++ b/kleene_star.py
@@ -1,7 +1,8 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
from numpy import zeros
+
def kleene_star(x, L, A):
length = len(x)
m = zeros((length, length))
@@ -13,7 +14,4 @@ def kleene_star(x, L, A):
m[i - 1, j - 1] = 1
if m[i - 1, j - 1] != 1:
m[i - 1, j - 1] = A(x[i - 1:j], L)
- if m[0, length - 1] != 0:
- return True
- else:
- return False
+ return m[0, length - 1] != 0
diff --git a/knapsack_0_1.py b/knapsack_0_1.py
index 52407b4..ed2fc0b 100644
--- a/knapsack_0_1.py
+++ b/knapsack_0_1.py
@@ -1,17 +1,19 @@
from numpy import zeros
+
def knapsack_0_1(W, w, v):
n = len(w)
return knapsack_0_1_aux(W, w, v, 1, n)
+
def knapsack_0_1_aux(W, w, v, m, n):
- '''
+ """
m: the first item
n: the last item
W: total weight
w: the list of weights of items
v: the list of values of items
- '''
+ """
# if m > n, then we have scanned all the items
if m > n:
@@ -25,16 +27,18 @@ def knapsack_0_1_aux(W, w, v, m, n):
else:
return max(knapsack_0_1_aux(W - w[m - 1], w, v, m + 1, n) + v[m - 1], knapsack_0_1_aux(W, w, v, m + 1, n))
+
def knapsack_0_1_memoized(W, w, v):
m = 1
n = len(w)
- value = zeros((W + 1, n + 1))
- solution = zeros((W + 1, n + 1))
- for i in range(0, W + 1):
- for j in range(0, n + 1):
+ value = zeros((W + 1, n + 1))
+ solution = zeros((W + 1, n + 1))
+ for i in range(W + 1):
+ for j in range(n + 1):
value[i, j] = float("-Inf")
knapsack_0_1_memoized_aux(W, w, v, m, n, value, solution)
- return value,solution
+ return value, solution
+
def knapsack_0_1_memoized_aux(W, w, v, m, n, value, solution):
if m > n:
@@ -42,7 +46,7 @@ def knapsack_0_1_memoized_aux(W, w, v, m, n, value, solution):
if value[W, m] >= 0:
return value[W, m]
if W < w[m - 1]:
- value[W, m] = knapsack_0_1_memoized_aux(W, w, v, m + 1, n, value, solution)
+ value[W, m] = knapsack_0_1_memoized_aux(W, w, v, m + 1, n, value, solution)
solution[W, m] = 0
else:
s = knapsack_0_1_memoized_aux(W - w[m - 1], w, v, m + 1, n, value, solution) + v[m - 1]
@@ -52,12 +56,13 @@ def knapsack_0_1_memoized_aux(W, w, v, m, n, value, solution):
value[W, m] = max(s, t)
return value[W, m]
+
def print_knapsack_solution(solution, w):
W = solution.shape[0] - 1
n = solution.shape[1] - 1
i = 1
while W != 0 and i <= n:
if solution[W, i] == 1:
- print i
+ print(i)
W = W - w[i - 1]
i = i + 1
diff --git a/kth-Quantiles.py b/kth-Quantiles.py
index 13d9ef6..258a9a6 100755
--- a/kth-Quantiles.py
+++ b/kth-Quantiles.py
@@ -1,44 +1,50 @@
-#! /usr/bin/env ipython
+#! /usr/bin/env python
import math
import random
from randomized_select import randomized_select
from quicksort import randomized_quicksort
+
def kth_quantiles(A, B, k, p, r):
if k > 0:
n = r - p + 1
location = math.floor(k / 2) * math.ceil(n / k)
- B[math.floor(k / 2)]= randomized_select(A, p, r, location)
+ B[math.floor(k / 2)] = randomized_select(A, p, r, location)
kth_quantiles(A, B, p, math.floor(k / 2) - 1, location - 1)
kth_quantiles(A, B, math.floor(k / 2), location + 1, r)
+
def median_of_two_arrays(X, x_start, x_end, Y, y_start, y_end, size):
- print X[x_start:x_end + 1], '\t', Y[y_start:y_end + 1], '\t', size
+ print(X[x_start:x_end + 1], '\t', Y[y_start:y_end + 1], '\t', size)
if size == 1:
return min(X[x_start], Y[y_start])
xc = X[x_start + int(math.floor(size / 2)) - 1]
yc = Y[y_start + int(math.ceil(size / 2)) - 1]
- print xc, yc
+ print(xc, yc)
if xc == yc:
return xc
elif xc < yc:
- return median_of_two_arrays(X, x_start + int(math.floor(size / 2)), x_end, Y, y_start, y_end, math.ceil(size / 2))
+ return median_of_two_arrays(X, x_start + int(math.floor(size / 2)), x_end, Y, y_start, y_end,
+ math.ceil(size / 2))
else:
- return median_of_two_arrays(X, x_start, x_end, Y, y_start + int(math.ceil(size / 2)), y_end, math.floor(size / 2))
-A = [random.randint(1, 100) for i in range(0, 15)]
-print A
-randomized_quicksort(A, 0, 14)
-print A
-B = [random.randint(1, 100) for i in range(0, 15)]
-print B
-randomized_quicksort(B, 0, 14)
-print B
-print median_of_two_arrays(A, 0, 14, B, 0, 14, 3.0)
-#randomized_select(A, 0, 14, 7)
-#print A
-#for i in range(1, 16):
-# randomized_select(A, 0, 14, i)
-# print i, '\t', A
-# print randomized_select(A, 0, 14, i)
+ return median_of_two_arrays(X, x_start, x_end, Y, y_start + int(math.ceil(size / 2)), y_end,
+ math.floor(size / 2))
+
+if __name__ == '__main__':
+ A = [random.randint(1, 100) for i in range(15)]
+ print(A)
+ randomized_quicksort(A, 0, 14)
+ print(A)
+ B = [random.randint(1, 100) for i in range(15)]
+ print(B)
+ randomized_quicksort(B, 0, 14)
+ print(B)
+ print(median_of_two_arrays(A, 0, 14, B, 0, 14, 3.0))
+# randomized_select(A, 0, 14, 7)
+# print( A)
+# for i in range(1, 16):
+# randomized_select(A, 0, 14, i)
+# print( i, '\t', A)
+# print( randomized_select(A, 0, 14, i))
diff --git a/linked_list.py b/linked_list.py
deleted file mode 100644
index ead4c9a..0000000
--- a/linked_list.py
+++ /dev/null
@@ -1,35 +0,0 @@
-class linked_list(object):
- def __init__(self, key = None):
- self.head = None
- self.size = 0
- self.key = key
- def empty(self):
- return self.size == 0
- def search(self, k):
- x = self.head
- while x != None and x.key != k:
- x = x.next
- return x
- def insert(self, x):
- self.size = self.size + 1
- x.next = self.head
- if self.head != None:
- self.head.prev = x
- self.head = x
- x.prev = None
- def delete(self, x):
- self.size = self.size - 1
- if x.prev != None:
- x.prev.next = x.next
- else:
- self.head = x.next
- if x.next != None:
- x.next.prev = x.prev
- def extract(self, x):
- self.delete(x)
- return x
-class linked_list_node(object):
- def __init__(self, element):
- self.key = element
- self.prev = None
- self.next = None
diff --git a/linked_list_test.py b/linked_list_test.py
deleted file mode 100644
index c1f44f6..0000000
--- a/linked_list_test.py
+++ /dev/null
@@ -1,54 +0,0 @@
-import unittest
-from linked_list import linked_list, linked_list_node
-
-class TestLinkedList(unittest.TestCase):
- def test_insert(self):
- L = linked_list()
- a = linked_list_node(1)
- b = linked_list_node(4)
- c = linked_list_node(16)
- d = linked_list_node(9)
- e = linked_list_node(25)
- L.insert(a)
- L.insert(b)
- L.insert(c)
- L.insert(d)
- L.insert(e)
- l = []
- x = L.head
- while x != None:
- l.append(x)
- x = x.next
- self.assertEquals(l, [e, d, c, b, a])
- def test_search(self):
- L = linked_list()
- a = linked_list_node(1)
- b = linked_list_node(4)
- c = linked_list_node(16)
- d = linked_list_node(9)
- e = linked_list_node(25)
- L.insert(a)
- L.insert(b)
- L.insert(c)
- L.insert(d)
- L.insert(e)
- self.assertEquals(L.search(4), b)
- def test_delete(self):
- L = linked_list()
- a = linked_list_node(1)
- b = linked_list_node(4)
- c = linked_list_node(16)
- d = linked_list_node(9)
- e = linked_list_node(25)
- L.insert(a)
- L.insert(b)
- L.insert(c)
- L.insert(d)
- L.insert(e)
- L.delete(b)
- l = []
- x = L.head
- while x != None:
- l.append(x)
- x = x.next
- self.assertEquals(l, [e, d, c, a])
diff --git a/linkedlist.py b/linkedlist.py
new file mode 100644
index 0000000..a4d9b41
--- /dev/null
+++ b/linkedlist.py
@@ -0,0 +1,45 @@
+from typing import Any, Optional
+
+
+class LinkedListNode:
+ def __init__(self, key: Any):
+ self.key: Any = key
+ self.prev: Optional[LinkedListNode] = None
+ self.next: Optional[LinkedListNode] = None
+
+
+class LinkedList:
+ def __init__(self, key=None):
+ self.head: Optional[LinkedListNode] = None
+ self.size: int = 0
+ self.key = key
+
+ def empty(self) -> bool:
+ return self.size == 0
+
+ def search(self, key: Any) -> Optional[LinkedListNode]:
+ node = self.head
+ while node and node.key != key:
+ node = node.next
+ return node
+
+ def insert(self, node: LinkedListNode) -> None:
+ self.size = self.size + 1
+ node.next = self.head
+ if self.head:
+ self.head.prev = node
+ self.head = node
+ node.prev = None
+
+ def delete(self, node: LinkedListNode) -> None:
+ self.size = self.size - 1
+ if node.prev:
+ node.prev.next = node.next
+ else:
+ self.head = node.next
+ if node.next:
+ node.next.prev = node.prev
+
+ def extract(self, node: LinkedListNode) -> LinkedListNode:
+ self.delete(node)
+ return node
diff --git a/longest_common_subsequence.py b/longest_common_subsequence.py
index 2d4db66..dcf61a7 100644
--- a/longest_common_subsequence.py
+++ b/longest_common_subsequence.py
@@ -1,5 +1,6 @@
from numpy import zeros
+
def lcs_length(X, Y):
m = len(X)
n = len(Y)
@@ -17,7 +18,9 @@ def lcs_length(X, Y):
else:
c[i, j] = c[i, j - 1]
b[i, j] = 2
- return c,b
+ return c, b
+
+
def lcs_length_one_row(X, Y):
m = len(X)
n = len(Y)
@@ -35,14 +38,15 @@ def lcs_length_one_row(X, Y):
a = c[j]
c[j] = value
return c[n]
+
+
def print_lcs(b, X, i, j):
if i == 0 or j == 0:
return
if b[i, j] == 0:
print_lcs(b, X, i - 1, j - 1)
- print X[i - 1],
+ print(X[i - 1], )
elif b[i, j] == 1:
print_lcs(b, X, i - 1, j)
else:
print_lcs(b, X, i, j - 1)
-
diff --git a/longest_palindrome_subsequence.py b/longest_palindrome_subsequence.py
index 66b87b5..ff1ff0e 100644
--- a/longest_palindrome_subsequence.py
+++ b/longest_palindrome_subsequence.py
@@ -3,11 +3,12 @@
from longest_common_subsequence import lcs_length, print_lcs
+
def longest_palindrome_subsequence(s):
- #c, b = lcs_length(s, s[::-1])
- #print_lcs(b, s, len(s), len(s))
+ # c, b = lcs_length(s, s[::-1])
+ # print(_lcs(b, s, len(s), len(s)))
n = len(s)
- c = [[0] * n for i in range(n)]
+ c = [[0] * n for _ in range(n)]
for i in range(n):
c[i][i] = 1
for i in range(n - 1):
@@ -16,15 +17,16 @@ def longest_palindrome_subsequence(s):
else:
c[i][i + 1] = 1
for length in range(3, n + 1):
- for i in range(0, n - length + 1):
+ for i in range(n - length + 1):
j = i + length - 1
if s[i] == s[j]:
- print i, j, c[i + 1][j - 1]
+ print(i, j, c[i + 1][j - 1])
c[i][j] = 2 + c[i + 1][j - 1]
else:
c[i][j] = max(c[i][j - 1], c[i + 1][j])
return c
+
def print_lps(c, s):
start = 0
end = len(s) - 1
@@ -48,8 +50,3 @@ def print_lps(c, s):
l.insert(index, s[start])
idx.insert(index, start)
return ''.join(l), idx
-
-
-
-
-
diff --git a/lowest_common_multiple.py b/lowest_common_multiple.py
new file mode 100644
index 0000000..7706aba
--- /dev/null
+++ b/lowest_common_multiple.py
@@ -0,0 +1,5 @@
+from gcd import gcd
+
+
+def lcm(num1: int, num2: int):
+ return num1 * num2 // gcd(num1, num2)
diff --git a/main.c b/main.c
deleted file mode 100644
index 0c2685f..0000000
--- a/main.c
+++ /dev/null
@@ -1,28 +0,0 @@
-#include
-#include
-
-int main(int argc, char *argv[]) {
- //int pow1(int, unsigned);
- //int pow1(int, unsigned);
- //int num = atoi(argv[1]);
- //int exp = atoi(argv[2]);
-//
- //printf("%d\n", pow2(num, exp));
- //printf("%d\n", pow1(num, exp));
- void matrix_exp(int *, int *, int, int);
- int A[16] = {-1, 1, 1, -1, 1, -1, -1, 1, 1, -1, -1, 1, -1, 1, 1, -1};
- int B[16];
- int C[4] = {1, 1, 0, 1}; //3, 2, -4, -2};//1, 0, 0, 1};
- int E[9] = {2, 1, 1, 3, 1, 0, 0, 1, 2};//1, 0, 0, 1, 0, 1, 0, 1, 0};
- int D[4];
- int i, j;
- int n = 2;
- matrix_exp(C, D, n, atoi(argv[1]));
- for (i = 0; i < n; i++) {
- for (j = 0; j < n; j++)
- printf("%d\t", *(D + n * i + j));
- printf("\n");
- }
-
- return 0;
-}
diff --git a/matrix_chain_order.py b/matrix_chain_order.py
index e494ae4..e32d7ab 100644
--- a/matrix_chain_order.py
+++ b/matrix_chain_order.py
@@ -1,6 +1,7 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
+
+from numpy import zeros
-from numpy import zeros
def bottom_up_matrix_chain_order(p):
n = len(p) - 1
@@ -15,7 +16,9 @@ def bottom_up_matrix_chain_order(p):
if q < m[i, j]:
m[i, j] = q
s[i, j] = k
- return m,s
+ return m, s
+
+
def memoized_matrix_chain_order(p):
n = len(p) - 1
m = zeros((n + 1, n + 1))
@@ -23,6 +26,8 @@ def memoized_matrix_chain_order(p):
for j in range(1, n + 1):
m[i, j] = float("Inf")
return lookup_chain(m, p, 1, n)
+
+
def lookup_chain(m, p, i, j):
if m[i, j] < float("Inf"):
return m[i, j]
@@ -30,26 +35,32 @@ def lookup_chain(m, p, i, j):
m[i, j] = 0
else:
for k in range(i, j):
- q = lookup_chain(m, p, i, k) + lookup_chain(m, p, k + 1, j) + p[i - 1] * p[k] * p[j]
+ q = lookup_chain(m, p, i, k) + lookup_chain(m, p,
+ k + 1, j) + p[i - 1] * p[k] * p[j]
if q < m[i, j]:
m[i, j] = q
return m[i, j]
+
+
def print_optimal_parens(s, i, j):
if i == j:
- print "A{}".format(int(i)),
+ print("A{}".format(int(i)), )
else:
- print "(",
+ print("(", )
print_optimal_parens(s, i, s[i, j])
print_optimal_parens(s, s[i, j] + 1, j)
- print ")",
+ print(")", )
+
# An incorrect greedy approach for matrix chain order problem
def greedy_matrix_chain_order(p):
n = len(p) - 1
return greedy_matrix_chain_order_aux(p, 1, n)
+
+
def greedy_matrix_chain_order_aux(p, i, j):
if i == j:
- return 0
+ return 0
q = float("Inf")
for k in range(i, j):
value = p[i - 1] * p[k] * p[j]
diff --git a/memoized_cut_rod.py b/memoized_cut_rod.py
index 86a608c..3f5da3e 100644
--- a/memoized_cut_rod.py
+++ b/memoized_cut_rod.py
@@ -2,6 +2,7 @@ def memoized_cut_rod(p, n):
r = [float("-Inf")] * (n + 1)
return memoized_cut_rod_aux(p, n, r)
+
def memoized_cut_rod_aux(p, n, r):
if r[n] >= 0:
return r[n]
@@ -13,5 +14,3 @@ def memoized_cut_rod_aux(p, n, r):
q = max(q, p[i - 1] + memoized_cut_rod_aux(p, n - i, r))
r[n] = q
return q
-
-
diff --git a/merge-sort.c b/merge-sort.c
deleted file mode 100644
index b46723d..0000000
--- a/merge-sort.c
+++ /dev/null
@@ -1,47 +0,0 @@
-// implemention of algorithm merge sort
-
-#include
-#include
-// A version of merge procedure that uses sentinels
-void merge(int a[], int begin, int middle, int end) {
- int n1 = middle - begin + 1;
- int n2 = end - middle;
-// What's this?
- int l[n1 + 1], r[n2 + 1];
- int i, j, k;
-
- for (i=0; i < n1; i++)
- l[i] = a[begin + i];
- for (j=0; j < n2; j++)
- r[j] = a[middle + j + 1];
- l[n1] = INT_MAX;
- r[n2] = INT_MAX;
- i = 0, j = 0;
- for (k = begin; k <= end; k++) {
- if (l[i] <= r[j]) {
- a[k] = l[i];
- i++;
- }
- else {
- a[k] = r[j];
- j++;
- }
- }
-}
-
-void merge_sort(int a[], int start, int end) {
- if (start < end) {
- int middle = (start + end) / 2;
- merge_sort(a, start, middle);
- merge_sort(a, middle+1, end);
- merge(a, start, middle, end);
- }
-}
-
-int main() {
- int a[8] = {1,3,4,5,2,6,0,10};
-
- merge_sort(a, 0, 7);
- printf("%d, %d, %d, %d, %d, %d, %d, %d\n", a[0], a[1], a[2], a[3], a[4], a[5], a[6], a[7]);
- return 0;
-}
diff --git a/merge.py b/merge.py
new file mode 100644
index 0000000..62957e5
--- /dev/null
+++ b/merge.py
@@ -0,0 +1,56 @@
+def merge_with_sentinel(array, left, mid, right):
+ """
+ merge procedure with sentinels
+
+ merge array[left...mid] and array[mid + 1...right]
+ :param array:
+ :param left:
+ :param mid:
+ :param right:
+ :return:
+ """
+ left_part = array[left: mid + 1]
+ left_part.append(float("Inf"))
+ right_part = array[mid + 1: right + 1]
+ right_part.append(float("Inf"))
+ i = 0
+ j = 0
+ for k in range(left, right + 1):
+ if left_part[i] <= right_part[j]:
+ array[k] = left_part[i]
+ i += 1
+ else:
+ array[k] = right_part[j]
+ j += 1
+
+
+def merge_without_sentinel(array, left, mid, right):
+ """
+ merge procedure without sentinels
+
+ A merge procedure without sentinels that stops once either array `left_part` or `right_part` has had all its elements
+ copied back to `array` and then copying the remainder of another array back into `array`
+ :param array:
+ :param left:
+ :param mid:
+ :param right:
+ :return:
+ """
+ left_part = array[left: mid + 1]
+ right_part = array[mid + 1: right + 1]
+ i = 0
+ j = 0
+ k = left
+ while i < len(left_part) and j < len(right_part):
+ if left_part[i] <= right_part[j]:
+ array[k] = left_part[i]
+ k += 1
+ i += 1
+ else:
+ array[k] = right_part[j]
+ k += 1
+ j += 1
+ if i < len(left_part):
+ array[k: right + 1] = left_part[i:]
+ else:
+ array[k: right + 1] = right_part[j:]
\ No newline at end of file
diff --git a/merge_sort.py b/merge_sort.py
index 5435558..12bad53 100644
--- a/merge_sort.py
+++ b/merge_sort.py
@@ -1,26 +1,86 @@
-def merge(A, p, q, r):
- n1 = q - p + 1
- n2 = r - q
- L = [0] * (n1 + 1)
- R = [0] * (n2 + 1)
- for i in range(0, n1):
- L[i] = A[p + i]
- for j in range(0, n2):
- R[j] = A[q + j + 1]
- L[n1] = float("Inf")
- R[n2] = float("Inf")
- i = 0
- j = 0
- for k in range(p, r + 1):
- if L[i] <= R[j]:
- A[k] = L[i]
- i = i + 1
- else:
- A[k] = R[j]
- j = j + 1
-def merge_sort(A, p, r):
- if p < r:
- q = (p + r) / 2
- merge_sort(A, p, q)
- merge_sort(A, q + 1, r)
- merge(A, p, q, r)
+from insertion_sort import insertion_sort
+from merge import merge_with_sentinel
+
+
+def merge_sort(array, merge_method=merge_with_sentinel):
+ """
+ inplace O(nlgn) sort
+ :param array:
+ :param merge_method:
+ :return:
+ """
+ _merge_sort(array, 0, len(array) - 1, merge_method)
+
+
+def _merge_sort(array, left, right, merge_method):
+ if left < right:
+ mid = (left + right) // 2
+ _merge_sort(array, left, mid, merge_method)
+ _merge_sort(array, mid + 1, right, merge_method)
+ merge_method(array, left, mid, right)
+
+
+def merge_ins_sort_bottom_to_top(array, partition: int = 2):
+ """
+ Although merge sort runs faster than insertion sort asymptotically,
+ the constant factors in insertion sort can make it faster in practice for small problem sizes on many machines.
+ Thus, it makes sense to coarsen the leaves of the recursion by using insertion sort within merge sort when
+ subproblems become sufficiently small. Consider a modification to merge sort in which n/k sublists of length k are
+ sorted using insertion sort and then merged using the standard merging mechanism, where k is a value to be determined.
+
+ bottom to top version with number of sublists specified
+ :param array:
+ :param partition: number of sublists
+ :return:
+ """
+ assert partition > 0
+ n = len(array)
+ sublist_length = n // partition
+ sublist_number = partition
+ for i in range(sublist_number):
+ left = sublist_length * i
+ right = min(sublist_length * (i + 1) - 1, n - 1)
+ insertion_sort(array, left, right)
+ while sublist_number > 1:
+ for i in range(0, sublist_number - 1, 2):
+ merge_with_sentinel(array, sublist_length * i, sublist_length * (i + 1) - 1,
+ min(sublist_length * (i + 2) - 1, n - 1))
+ sublist_length *= 2
+ sublist_number = sublist_number // 2
+
+
+def merge_ins_sort_top_to_bottom(array, sublist_length):
+ """
+ Although merge sort runs faster than insertion sort asymptotically, the constant factors in insertion sort can make
+ it faster in practice for small problem sizes on many machines.
+ Thus, it makes sense to coarsen the leaves of the recursion by using insertion sort within merge sort when
+ subproblems become sufficiently small. Consider a modification to merge sort in which n/k sublists of length k are
+ sorted using insertion sort and then merged using the standard merging mechanism, where k is a value to be determined.
+
+ top to bottom version with sublist length specified
+ :param array:
+ :param sublist_length:
+ :return:
+ """
+ n = len(array)
+ assert 0 < sublist_length < n
+ _merge_ins_sort_top_to_bottom(array, 0, n - 1, sublist_length)
+
+
+def _merge_ins_sort_top_to_bottom(array, start, end, sublist_length):
+ """
+
+ :param array:
+ :param start:
+ :param end:
+ :param sublist_length:
+ :return:
+ """
+ length = end - start + 1
+ if length > sublist_length:
+ mid = (start + end) // 2
+ _merge_ins_sort_top_to_bottom(array, start, mid, sublist_length)
+ _merge_ins_sort_top_to_bottom(array, mid + 1, end, sublist_length)
+ merge_with_sentinel(array, start, mid, end)
+ else:
+ insertion_sort(array, start, end)
diff --git a/min_gap_tree.py b/min_gap_tree.py
index 44df937..c47891f 100644
--- a/min_gap_tree.py
+++ b/min_gap_tree.py
@@ -1,22 +1,29 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-from rb_tree import rb_node, rb_tree
+from rb_tree import RbNode, RbTree
-class min_gap_node(rb_node):
+
+class MinGapNode(RbNode):
def __init__(self, key, p, left, right, color, successor, min_gap):
- rb_node.__init__(self, key, p, left, right, color)
+ RbNode.__init__(self, key, p, left, right, color)
self.successor = successor
self.min_gap = min_gap
-class min_gap_tree(rb_tree):
- positive_infinity = min_gap_node(float("Inf"), None, None, None, 1, None, float("Inf"))
- nil = min_gap_node(None, None, None, None, 1, positive_infinity, float("Inf"))
+
+
+class MinGapTree(RbTree):
+ positive_infinity = MinGapNode(
+ float("Inf"), None, None, None, 1, None, float("Inf"))
+ nil = MinGapNode(None, None, None, None, 1,
+ positive_infinity, float("Inf"))
root = nil
+
def __init__(self, values):
if isinstance(values, list):
for i in values:
- self.insert(min_gap_node(i, None, None, None, 0, None, None))
+ self.insert(MinGapNode(i, None, None, None, 0, None, None))
else:
- print "Not invalid argument"
+ print("Not invalid argument")
+
def insert(self, z):
y = self.nil
x = self.root
@@ -43,12 +50,14 @@ def insert(self, z):
z.p = y
z.left = self.nil
z.right = self.nil
- z.color = 0 #red
+ z.color = 0 # red
traverse = z
while traverse != self.nil:
- traverse.min_gap = min(traverse.left.min_gap, traverse.successor.key - traverse.key, traverse.right.min_gap)
+ traverse.min_gap = min(
+ traverse.left.min_gap, traverse.successor.key - traverse.key, traverse.right.min_gap)
traverse = traverse.p
self.insert_fixed(z)
+
def delete(self, z):
traverse = self.predecessor(z)
y = z
@@ -73,17 +82,20 @@ def delete(self, z):
y.left = z.left
y.left.p = y
y.color = z.color
- # After we delete z, the only nodes whose successor attributes need to be updated are z's successor and z's predecessor
+ # After we delete z, the only nodes whose successor attributes need to be updated are z's successor and z's predecessor
traverse.successor = z.successor
while traverse != self.nil:
- traverse.min_gap = min(traverse.left.min_gap, traverse.successor.key - traverse.key, traverse.right.min_gap)
+ traverse.min_gap = min(
+ traverse.left.min_gap, traverse.successor.key - traverse.key, traverse.right.min_gap)
traverse = traverse.p
traverse = x.p
while traverse != self.nil:
- traverse.min_gap = min(traverse.left.min_gap, traverse.successor.key - traverse.key, traverse.right.min_gap)
+ traverse.min_gap = min(
+ traverse.left.min_gap, traverse.successor.key - traverse.key, traverse.right.min_gap)
traverse = traverse.p
if y_original_color == 1:
self.delete_fixup(x)
+
def left_rotate(self, x):
y = x.right
x.right = y.left
@@ -99,7 +111,9 @@ def left_rotate(self, x):
y.left = x
x.p = y
y.min_gap = x.min_gap
- x.min_gap = min(x.left.min_gap, x.successor.key - x.key, x.right.min_gap)
+ x.min_gap = min(x.left.min_gap, x.successor.key -
+ x.key, x.right.min_gap)
+
def right_rotate(self, y):
x = y.left
y.left = x.right
@@ -115,7 +129,9 @@ def right_rotate(self, y):
x.right = y
y.p = x
x.min_gap = y.min_gap
- y.min_gap = min(y.left.min_gap, y.successor.key - y.key, y.right.min_gap)
+ y.min_gap = min(y.left.min_gap, y.successor.key -
+ y.key, y.right.min_gap)
+
def predecessor(self, x):
if x.left != self.nil:
return x.left.maximum()
diff --git a/min_heap_with_linked_list.py b/min_heap_with_linked_list.py
index fc2a7bd..9eebd03 100644
--- a/min_heap_with_linked_list.py
+++ b/min_heap_with_linked_list.py
@@ -1,19 +1,25 @@
-from linked_list import linked_list_node, linked_list
+import sys
-class min_heap(list):
+
+class MinHeap(list):
def __init__(self, data):
list.__init__(self, data)
self.length = len(data)
self.heap_size = self.length
self.build_min_heap()
+
def __contains__(self, y):
return y in self[0:self.heap_size]
+
def left(self, i):
return 2 * i + 1
+
def right(self, i):
return 2 * i + 2
+
def parent(self, i):
return (i - 1) / 2
+
def min_heapify(self, i):
l = self.left(i)
r = self.right(i)
@@ -23,16 +29,20 @@ def min_heapify(self, i):
smallest = i
if (r <= (self.heap_size - 1)) and (self[r].key < self[smallest].key):
smallest = r
- if smallest != i:
- self[i],self[smallest] = self[smallest],self[i]
+ if smallest != i:
+ self[i], self[smallest] = self[smallest], self[i]
self.min_heapify(smallest)
+
def build_min_heap(self):
self.heap_size = self.length
- for i in range(self.length / 2 - 1, -1, -1):
+ for i in range(self.length // 2 - 1, -1, -1):
self.min_heapify(i)
-class min_priority_queue(min_heap):
+
+
+class MinPriorityQueue(MinHeap):
def heap_minimum(self):
return self[0].head
+
def heap_extract_min(self):
if self.heap_size < 1:
sys.exit("heap underflow")
@@ -42,6 +52,7 @@ def heap_extract_min(self):
self.heap_size = self.heap_size - 1
self.min_heapify(0)
return minimum
+
def heap_decrease_key(self, i, element, key):
if key > self[i]:
sys.exit("new key is larger than current key")
@@ -49,8 +60,9 @@ def heap_decrease_key(self, i, element, key):
while i > 0 and self[self.parent(i)] > self[i]:
tmp = self[self.parent(i)]
self[self.parent(i)] = self[i]
- self[i] = tmp
+ self[i] = tmp
i = self.parent(i)
+
def min_heap_insert(self, key):
if self.heap_size >= self.length:
sys.exit("heap overflow")
diff --git a/min_heap_with_linked_list_test.py b/min_heap_with_linked_list_test.py
index 67bbdaf..05e0cc3 100644
--- a/min_heap_with_linked_list_test.py
+++ b/min_heap_with_linked_list_test.py
@@ -1,89 +1,93 @@
import unittest
from min_heap_with_linked_list import min_heap, min_priority_queue
-from linked_list import linked_list, linked_list_node
+from linkedlist import LinkedList, LinkedListNode
+
class TestHeap(unittest.TestCase):
def test_min_heapify(self):
- L1 = linked_list(1)
- L2 = linked_list(2)
- L2.insert(linked_list_node(2))
- L2.insert(linked_list_node(2))
- L3 = linked_list(3)
- L3.insert(linked_list_node(3))
- L3.insert(linked_list_node(3))
- L4 = linked_list(4)
- L4.insert(linked_list_node(4))
- L5 = linked_list(5)
- L3.insert(linked_list_node(5))
- L3.insert(linked_list_node(5))
- L3.insert(linked_list_node(5))
+ L1 = LinkedList(1)
+ L2 = LinkedList(2)
+ L2.insert(LinkedListNode(2))
+ L2.insert(LinkedListNode(2))
+ L3 = LinkedList(3)
+ L3.insert(LinkedListNode(3))
+ L3.insert(LinkedListNode(3))
+ L4 = LinkedList(4)
+ L4.insert(LinkedListNode(4))
+ L5 = LinkedList(5)
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
h = min_heap([L5, L1, L2, L3, L4])
h.min_heapify(0)
- self.assertEquals(h, [L1, L3, L2, L5, L4])
+ self.assertEqual(h, [L1, L3, L2, L5, L4])
+
def test_build_min_heap(self):
- L1 = linked_list(1)
- L2 = linked_list(2)
- L2.insert(linked_list_node(2))
- L2.insert(linked_list_node(2))
- L3 = linked_list(3)
- L3.insert(linked_list_node(3))
- L3.insert(linked_list_node(3))
- L4 = linked_list(4)
- L4.insert(linked_list_node(4))
- L5 = linked_list(5)
- L3.insert(linked_list_node(5))
- L3.insert(linked_list_node(5))
- L3.insert(linked_list_node(5))
+ L1 = LinkedList(1)
+ L2 = LinkedList(2)
+ L2.insert(LinkedListNode(2))
+ L2.insert(LinkedListNode(2))
+ L3 = LinkedList(3)
+ L3.insert(LinkedListNode(3))
+ L3.insert(LinkedListNode(3))
+ L4 = LinkedList(4)
+ L4.insert(LinkedListNode(4))
+ L5 = LinkedList(5)
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
h = min_heap([L3, L4, L5, L2, L1])
h.build_min_heap()
- self.assertEquals(h, [L1, L2, L5, L3, L4])
+ self.assertEqual(h, [L1, L2, L5, L3, L4])
+
def test_heap_minimum(self):
- L1 = linked_list(1)
- L1.insert(linked_list_node(1))
- L1.insert(linked_list_node(1))
- L2 = linked_list(2)
- L2.insert(linked_list_node(2))
- L2.insert(linked_list_node(2))
- L3 = linked_list(3)
- L3.insert(linked_list_node(3))
- L3.insert(linked_list_node(3))
- L4 = linked_list(4)
- L4.insert(linked_list_node(4))
- L5 = linked_list(5)
- L3.insert(linked_list_node(5))
- L3.insert(linked_list_node(5))
- L3.insert(linked_list_node(5))
+ L1 = LinkedList(1)
+ L1.insert(LinkedListNode(1))
+ L1.insert(LinkedListNode(1))
+ L2 = LinkedList(2)
+ L2.insert(LinkedListNode(2))
+ L2.insert(LinkedListNode(2))
+ L3 = LinkedList(3)
+ L3.insert(LinkedListNode(3))
+ L3.insert(LinkedListNode(3))
+ L4 = LinkedList(4)
+ L4.insert(LinkedListNode(4))
+ L5 = LinkedList(5)
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
q = min_priority_queue([L1, L2, L3, L4, L5])
- self.assertEquals(q.heap_minimum().key, 1)
+ self.assertEqual(q.heap_minimum().key, 1)
+
def test_heap_extract_min(self):
- L1 = linked_list(1)
- L1.insert(linked_list_node(1))
- L1.insert(linked_list_node(1))
- L2 = linked_list(2)
- L2.insert(linked_list_node(2))
- L2.insert(linked_list_node(2))
- L3 = linked_list(3)
- L3.insert(linked_list_node(3))
- L3.insert(linked_list_node(3))
- L4 = linked_list(4)
- L4.insert(linked_list_node(4))
- L5 = linked_list(5)
- L3.insert(linked_list_node(5))
- L3.insert(linked_list_node(5))
- L3.insert(linked_list_node(5))
+ L1 = LinkedList(1)
+ L1.insert(LinkedListNode(1))
+ L1.insert(LinkedListNode(1))
+ L2 = LinkedList(2)
+ L2.insert(LinkedListNode(2))
+ L2.insert(LinkedListNode(2))
+ L3 = LinkedList(3)
+ L3.insert(LinkedListNode(3))
+ L3.insert(LinkedListNode(3))
+ L4 = LinkedList(4)
+ L4.insert(LinkedListNode(4))
+ L5 = LinkedList(5)
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
q = min_priority_queue([L1, L2, L3, L4, L5])
- self.assertEquals(q.heap_extract_min().key, 1)
- self.assertEquals(q, [L1, L2, L3, L4, L5])
- self.assertEquals(q.heap_extract_min().key, 1)
- self.assertEquals(q, [L2, L4, L3, L5, L5])
+ self.assertEqual(q.heap_extract_min().key, 1)
+ self.assertEqual(q, [L1, L2, L3, L4, L5])
+ self.assertEqual(q.heap_extract_min().key, 1)
+ self.assertEqual(q, [L2, L4, L3, L5, L5])
# def test_heap_decrease_key(self):
# a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
-# q = min_priority_queue(a)
+# q = MinPriorityQueue(a)
# q.heap_decrease_key(8, 1)
-# self.assertEquals(q, [1, 1, 3, 2, 7, 8, 9, 10, 4, 16])
+# self.assertEqual(q, [1, 1, 3, 2, 7, 8, 9, 10, 4, 16])
# def test_heap_insert(self):
# a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
-# q = min_priority_queue(a)
+# q = MinPriorityQueue(a)
# q.heap_extract_min()
# q.min_heap_insert(0)
-# self.assertEquals(q, [0, 2, 3, 10, 4, 8, 9, 16, 14, 7])
+# self.assertEqual(q, [0, 2, 3, 10, 4, 8, 9, 16, 14, 7])
diff --git a/min_priority_queue_using_rb_tree.py b/min_priority_queue_using_rb_tree.py
index e591e7e..dea6c42 100644
--- a/min_priority_queue_using_rb_tree.py
+++ b/min_priority_queue_using_rb_tree.py
@@ -1,18 +1,22 @@
-from rb_tree import rb_tree
+from rb_tree import RbTree
import sys
-class min_priority_queue(rb_tree):
+
+class min_priority_queue(RbTree):
def heap_minimum(self):
return self.minimum()
+
def heap_extract_min(self):
x = self.minimum()
self.delete(x)
return x
+
def heap_decrease_key(self, node, key):
if key > node.key:
sys.exit("new key is larger than current key")
self.delete(node)
node.key = key
self.insert(node)
+
def min_heap_insert(self, node):
self.insert(node)
diff --git a/min_priority_queue_using_rb_tree_test.py b/min_priority_queue_using_rb_tree_test.py
deleted file mode 100644
index d6faca0..0000000
--- a/min_priority_queue_using_rb_tree_test.py
+++ /dev/null
@@ -1,40 +0,0 @@
-#!/usr/bin/env ipython
-import unittest
-from min_priority_queue_using_rb_tree import min_priority_queue
-from rb_tree import rb_node
-
-class TestMinPriorityQueue(unittest.TestCase):
- def test_extract_min(self):
- q = min_priority_queue([41, 38, 31, 12, 19, 9])
- self.assertEquals(q.heap_extract_min().key, 9)
- self.assertEquals(q.heap_extract_min().key, 12)
- self.assertEquals(q.heap_extract_min().key, 19)
- self.assertEquals(q.heap_extract_min().key, 31)
- self.assertEquals(q.heap_extract_min().key, 38)
- self.assertEquals(q.heap_extract_min().key, 41)
- def test_heap_decrease_key(self):
- q = min_priority_queue([41, 38, 31, 12, 19, 9])
- q.heap_decrease_key(q.iterative_tree_search(9), 5)
- q.heap_decrease_key(q.iterative_tree_search(38), 5)
- self.assertEquals(q.heap_extract_min().key, 5)
- self.assertEquals(q.heap_extract_min().key, 5)
- self.assertEquals(q.heap_extract_min().key, 12)
- self.assertEquals(q.heap_extract_min().key, 19)
- self.assertEquals(q.heap_extract_min().key, 31)
- self.assertEquals(q.heap_extract_min().key, 41)
- def test_heap_insert(self):
- q = min_priority_queue([41, 38, 31, 12, 19, 9])
- q.min_heap_insert(rb_node(5, None, None, None, 0))
- q.min_heap_insert(rb_node(38, None, None, None, 0))
- q.min_heap_insert(rb_node(50, None, None, None, 0))
- self.assertEquals(q.heap_extract_min().key, 5)
- self.assertEquals(q.heap_extract_min().key, 9)
- self.assertEquals(q.heap_extract_min().key, 12)
- self.assertEquals(q.heap_extract_min().key, 19)
- self.assertEquals(q.heap_extract_min().key, 31)
- self.assertEquals(q.heap_extract_min().key, 38)
- self.assertEquals(q.heap_extract_min().key, 38)
- self.assertEquals(q.heap_extract_min().key, 41)
- self.assertEquals(q.heap_extract_min().key, 50)
-if __name__ == '__main__':
- unittest.main()
diff --git a/most_reliable_path.py b/most_reliable_path.py
index 2a102bb..988e2b5 100644
--- a/most_reliable_path.py
+++ b/most_reliable_path.py
@@ -1,7 +1,8 @@
from graph import max_priority_queue
+
def most_reliable_path(G, r, s):
- '''
+ """
We are given a directed graph G = (V, E) on which
each edge (u, v) that belongs to E has an associated
value r(u, v), which is a real number in the range
@@ -16,7 +17,7 @@ def most_reliable_path(G, r, s):
s: the source
r: the function that returns the probability that the
channel from u to v will not fail.
- '''
+ """
initialize_single_source(G, s)
S = set()
Q = max_priority_queue(G.vertices, 'r')
@@ -29,6 +30,7 @@ def most_reliable_path(G, r, s):
v.p = u
Q.heap_increase_key(v.index, u.r * r(u, v))
+
def initialize_single_source(G, s):
for v in G.vertices:
v.r = 0
diff --git a/optimal_binary_search_tree.py b/optimal_binary_search_tree.py
index b5b1419..6687b6d 100644
--- a/optimal_binary_search_tree.py
+++ b/optimal_binary_search_tree.py
@@ -1,11 +1,12 @@
from numpy import zeros
+
def optimal_bst(p, q, n):
e = zeros((n + 2, n + 1))
w = zeros((n + 2, n + 1))
root = zeros((1 + n, 1 + n))
for i in range(1, n + 2):
- print "i = {}".format(i)
+ print("i = {}".format(i))
e[i, i - 1] = q[i - 1]
w[i, i - 1] = q[i - 1]
for l in range(1, n + 1):
@@ -18,27 +19,31 @@ def optimal_bst(p, q, n):
if t < e[i, j]:
e[i, j] = t
root[i, j] = r
- return e,root
+ return e, root
+
+
def construct_optimal_bst(root):
n = root.shape[1] - 1
r = root[1, n]
- print "k{} is the root".format(int(r))
+ print("k{} is the root".format(int(r)))
construct_optimal_bst_aux(root, r, 1, r - 1)
construct_optimal_bst_aux(root, r, r + 1, n)
+
+
def construct_optimal_bst_aux(root, p, i, j):
if j < p:
if i <= j:
r = root[i, j]
- print "k{} is the left child of k{}".format(int(r), int(p))
+ print("k{} is the left child of k{}".format(int(r), int(p)))
construct_optimal_bst_aux(root, r, i, r - 1)
construct_optimal_bst_aux(root, r, r + 1, j)
else:
- print "d{} is the left child of k{}".format(int(j), int(p))
+ print("d{} is the left child of k{}".format(int(j), int(p)))
if i > p:
if i <= j:
r = root[i, j]
- print "k{} is the right child of k{}".format(int(r), int(p))
+ print("k{} is the right child of k{}".format(int(r), int(p)))
construct_optimal_bst_aux(root, r, i, r - 1)
construct_optimal_bst_aux(root, r, r + 1, j)
else:
- print "d{} is the right child of k{}".format(int(j), int(p))
+ print("d{} is the right child of k{}".format(int(j), int(p)))
diff --git a/os_tree.py b/os_tree.py
index a30d31e..46cd716 100755
--- a/os_tree.py
+++ b/os_tree.py
@@ -1,11 +1,13 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-from rb_tree import rb_node, rb_tree
+from rb_tree import RbNode, RbTree
-class os_node(rb_node):
+
+class OSNode(RbNode):
def __init__(self, key, p, left, right, color, size):
- rb_node.__init__(self, key, p, left, right, color)
+ RbNode.__init__(self, key, p, left, right, color)
self.size = size
+
def select_recursive(self, i):
r = self.left.size + 1
if i == r:
@@ -14,6 +16,7 @@ def select_recursive(self, i):
return self.left.select_recursive(i)
else:
return self.right.select_recursive(i - r)
+
def select_iterative(self, i):
x = self
while True:
@@ -25,6 +28,7 @@ def select_iterative(self, i):
else:
x = x.right
i = i - r
+
def key_rank(self, k):
r = self.left.size + 1
if k == self.key:
@@ -33,6 +37,7 @@ def key_rank(self, k):
return self.left.key_rank(k)
else:
return r + self.right.key_rank(k)
+
def ith_successor(self, i):
if i == 0:
return self
@@ -47,15 +52,19 @@ def ith_successor(self, i):
y = y.p
if y.size != 0:
return y.ith_successor(i - r - 1)
-class os_tree(rb_tree):
- nil = os_node(None, None, None, None, 1, 0)
+
+
+class os_tree(RbTree):
+ nil = OSNode(None, None, None, None, 1, 0)
root = nil
+
def __init__(self, values):
if isinstance(values, list):
for i in values:
- self.insert(os_node(i, None, None, None, 0, 1))
+ self.insert(OSNode(i, None, None, None, 0, 1))
else:
- print "Not invalid argument"
+ print("Not invalid argument")
+
def insert(self, z):
y = self.nil
x = self.root
@@ -75,8 +84,9 @@ def insert(self, z):
z.p = y
z.left = self.nil
z.right = self.nil
- z.color = 0 #red
+ z.color = 0 # red
self.insert_fixed(z)
+
def delete(self, z):
y = z
y_original_color = y.color
@@ -106,6 +116,7 @@ def delete(self, z):
traverse = traverse.p
if y_original_color == 1:
self.delete_fixup(x)
+
def left_rotate(self, x):
y = x.right
x.right = y.left
@@ -122,6 +133,7 @@ def left_rotate(self, x):
x.p = y
y.size = x.size
x.size = x.left.size + x.right.size + 1
+
def right_rotate(self, y):
x = y.left
y.left = x.right
@@ -138,6 +150,7 @@ def right_rotate(self, y):
y.p = x
x.size = y.size
y.size = y.left.size + y.right.size + 1
+
def rank(self, x):
r = x.left.size + 1
y = x
diff --git a/partition.py b/partition.py
index 2f449b5..ae41bf5 100644
--- a/partition.py
+++ b/partition.py
@@ -1,58 +1,54 @@
import random
-def partition(A, p, r):
- x = A[r]
- i = p - 1
- for j in range(p, r):
- if A[j] <= x:
- i = i + 1
- A[i], A[j] = A[j], A[i]
- A[i + 1], A[r] = A[r], A[i + 1]
- return i + 1
-
-def partition2(A, p, r):
- '''
- Partition A into three parts: < x, = x, > x. The return value is the median of the second part. So the return value is floor((p + r) / 2) when all elements in the array A[p .. r] have the same value. Partition in place.
- '''
- x = A[r]
- i = p - 1
+
+def partition(array, left, right):
+ pivot_index = left
+ pivot = array[right]
+ for i in range(left, right):
+ if array[i] <= pivot:
+ array[i], array[pivot_index] = array[pivot_index], array[i]
+ pivot_index += 1
+ array[pivot_index], array[right] = array[right], array[pivot_index]
+ return pivot_index
+
+
+def partition2(array, left, right):
+ """
+ Partition A into three parts: < x, = x, > x. The return value is the median of the second part.
+ So the return value is (left + right) // 2 when all elements in the array A[left .. right] have the same value. Partition in place.
+ """
+ x = array[right]
+ i = left - 1
k = i
- for j in range(p, r):
- if A[j] < x:
+ for j in range(left, right):
+ if array[j] < x:
i = i + 1
- A[i], A[j] = A[j], A[i]
+ array[i], array[j] = array[j], array[i]
k = k + 1
if i != k:
- A[j], A[k] = A[k], A[j]
- elif A[j] == x:
+ array[j], array[k] = array[k], array[j]
+ elif array[j] == x:
k = k + 1
- A[k], A[j] = A[j], A[k]
- A[k + 1], A[r] = A[r], A[k + 1]
- return (k + 2 + i) / 2
-
-def partition3(A, p, r):
- '''
- Variant of partition2. Requires O(n) extra space, but it is easier to implement.
- '''
- x = A[r]
- n = r - p + 1
- i = -1
- k = n
- B = [0] * n
- for j in range(p, r):
- if A[j] < x:
- i = i + 1
- B[i] = A[j]
- elif A[j] > x:
- k = k - 1
- B[k] = A[j]
- for j in range(i + 1, k):
- B[j] = x
- for j in range(p, r + 1):
- A[j] = B[j - p]
- return (2 * p + i + k) / 2
-
-def randomized_partition(A, p, r):
- i = random.randint(p, r)
- A[i], A[r] = A[r], A[i]
- return partition(A, p, r)
+ array[k], array[j] = array[j], array[k]
+ array[k + 1], array[right] = array[right], array[k + 1]
+ return (k + 2 + i) // 2
+
+
+def partition3(array, left, right):
+ """
+ Variant of partition. Requires O(n) extra space, but it is easier to implement.
+ """
+ pivot = array[right]
+ left_part = [array[i] for i in range(left, right) if array[i] <= pivot]
+ right_part = [array[i] for i in range(left, right) if array[i] > pivot]
+ pivot_index = left + len(left_part)
+ array[left:pivot_index] = left_part[:]
+ array[pivot_index + 1:right + 1] = right_part[:]
+ array[pivot_index] = pivot
+ return pivot_index
+
+
+def randomized_partition(array, left, right):
+ i = random.randint(left, right)
+ array[i], array[right] = array[right], array[i]
+ return partition(array, left, right)
diff --git a/partition_test.py b/partition_test.py
deleted file mode 100644
index c5407ef..0000000
--- a/partition_test.py
+++ /dev/null
@@ -1,17 +0,0 @@
-import unittest
-from partition import partition, partition2, partition3
-
-class TestPartition(unittest.TestCase):
- def test_partition(self):
- a = [2, 8, 7, 1, 3, 5, 6, 4]
- partition(a, 0, 7)
- self.assertEquals(a, [2, 1, 3, 4, 7, 5, 6, 8])
- def test_partition2(self):
- a = [2, 8, 7, 1, 4, 5, 6, 4]
- partition2(a, 0, 7)
- self.assertEquals(a, [2, 1, 4, 4, 7, 5, 6, 8])
- def test_partition3(self):
- a = [2, 8, 7, 1, 3, 5, 6, 4]
- partition3(a, 0, 7)
- self.assertEquals(a, [2, 1, 3, 4, 6, 5, 7, 8])
-
diff --git a/pointer_tree.py b/pointer_tree.py
index 57e431f..aeae9c1 100644
--- a/pointer_tree.py
+++ b/pointer_tree.py
@@ -1,25 +1,34 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-from rb_tree import rb_node, rb_tree
+from rb_tree import RbNode, RbTree
-class pointer_node(rb_node):
+
+class pointer_node(RbNode):
def __init__(self, key, p, left, right, color, minimum, maximum, predecessor, successor):
- rb_node.__init__(self, key, p, left, right, color)
+ RbNode.__init__(self, key, p, left, right, color)
self.minimum = minimum
self.maximum = maximum
self.predecessor = predecessor
self.successor = successor
-class pointer_tree(rb_tree):
- negative_infinity = pointer_node(float("-Inf"), None, None, None, 1, None, None, None, None)
- positive_infinity = pointer_node(float("Inf"), None, None, None, 1, None, None, None, None)
- nil = pointer_node(None, None, None, None, 1, negative_infinity, positive_infinity, None, None)
+
+
+class pointer_tree(RbTree):
+ negative_infinity = pointer_node(
+ float("-Inf"), None, None, None, 1, None, None, None, None)
+ positive_infinity = pointer_node(
+ float("Inf"), None, None, None, 1, None, None, None, None)
+ nil = pointer_node(None, None, None, None, 1,
+ negative_infinity, positive_infinity, None, None)
root = nil
+
def __init__(self, values):
if isinstance(values, list):
for i in values:
- self.insert(pointer_node(i, None, None, None, 0, None, None, None, None))
+ self.insert(pointer_node(i, None, None,
+ None, 0, None, None, None, None))
else:
- print "Not invalid argument"
+ print("Not invalid argument")
+
def insert(self, z):
y = self.nil
x = self.root
@@ -61,8 +70,9 @@ def insert(self, z):
z.p = y
z.left = self.nil
z.right = self.nil
- z.color = 0 #red
+ z.color = 0 # red
self.insert_fixed(z)
+
def left_rotate(self, x):
y = x.right
x.right = y.left
@@ -82,6 +92,7 @@ def left_rotate(self, x):
x.maximum = x
else:
x.maximum = x.right.maximum
+
def right_rotate(self, y):
x = y.left
y.left = x.right
@@ -101,6 +112,7 @@ def right_rotate(self, y):
y.minimum = y
else:
y.minimum = y.left.minimum
+
def delete(self, z):
y = z
y_original_color = y.color
@@ -124,7 +136,7 @@ def delete(self, z):
y.left = z.left
y.left.p = y
y.color = z.color
- # After we delete z, the only nodes whose predecessor and successor attributes need to be updated are z's successor and z's predecessor
+ # After we delete z, the only nodes whose predecessor and successor attributes need to be updated are z's successor and z's predecessor
z.predecessor.successor = z.successor
z.successor.predecessor = z.predecessor
traverse = x.p
diff --git a/polar_angle.py b/polar_angle.py
index 67f2b4a..d4ab834 100644
--- a/polar_angle.py
+++ b/polar_angle.py
@@ -1,33 +1,42 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-from heap import max_heap
+from heap import MaxHeap
-class vector(object):
- def __init__(self, p2, p1 = (0, 0)):
+
+class Vector:
+ def __init__(self, p2, p1=(0, 0)):
self.x = p2[0] - p1[0]
self.y = p2[1] - p1[0]
+
def cross_product(self, v):
return self.x * v.y - v.x * self.y
+
def __lt__(self, v):
return self.cross_product(v) > 0
+
def __gt__(self, v):
return self.cross_product(v) < 0
+
def __eq__(self, v):
return self.cross_product(v) == 0
+
def __le__(self, v):
return self.cross_product(v) >= 0
+
def __ge__(self, v):
return self.cross_product(v) <= 0
+
+
def polar_angle(p0, point_list):
- '''sort a sequence of n points according to
+ """sort a sequence of n points according to
their polar angles with respect to a given origin point p0.
- '''
- v0 = vector((p0[0] + 1, p0[1]), p0) # The polar angle of v0 is 0
- vector_list = [vector(p, p0) for p in point_list]
- angle_0 = [] #list of vectors whose polar angles are 0
- angle_pi = [] #list of vectors whose polar angles are pi
- angle_0_pi = [] #list of vectors whose polar angles are larger than 0 and smaller than pi
- angle_pi_2pi = [] #list of vectors whose polar angles are larger than pi and smaller than 2pi
+ """
+ v0 = Vector((p0[0] + 1, p0[1]), p0) # The polar angle of v0 is 0
+ vector_list = [Vector(p, p0) for p in point_list]
+ angle_0 = [] # list of vectors whose polar angles are 0
+ angle_pi = [] # list of vectors whose polar angles are pi
+ angle_0_pi = [] # list of vectors whose polar angles are larger than 0 and smaller than pi
+ angle_pi_2pi = [] # list of vectors whose polar angles are larger than pi and smaller than 2pi
for v in vector_list:
if v == v0:
if v.x > 0:
@@ -38,8 +47,8 @@ def polar_angle(p0, point_list):
angle_pi_2pi.append(v)
elif v > v0:
angle_0_pi.append(v)
- heap_0_pi = max_heap(angle_0_pi)
- heap_pi_2pi = max_heap(angle_pi_2pi)
+ heap_0_pi = MaxHeap(angle_0_pi)
+ heap_pi_2pi = MaxHeap(angle_pi_2pi)
heap_0_pi.heapsort()
heap_pi_2pi.heapsort()
return [(v.x, v.y) for v in (angle_0 + heap_0_pi + angle_pi + heap_pi_2pi)]
diff --git a/polygon_area.py b/polygon_area.py
index 262f89c..6d41e6e 100644
--- a/polygon_area.py
+++ b/polygon_area.py
@@ -1,9 +1,11 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
+from typing import Sequence, Tuple, Union
-def polygon_area(P):
- n = len(P)
- S = 0
- for i in range(0, n - 1):
- S = S + (P[i][0] + P[i + 1][0]) * (P[i + 1][1] - P[i][1])
- S = S + (P[0][0] + P[n - 1][0]) * (P[0][1] - P[n - 1][1])
- return 0.5 * abs(S)
+Number = Union[int, float]
+
+
+def polygon_area(polygon: Sequence[Tuple[Number, Number]]) -> float:
+ n = len(polygon)
+ area = sum((polygon[i][0] + polygon[i + 1][0]) * (polygon[i + 1][1] - polygon[i][1]) for i in range(n - 1))
+ area += (polygon[0][0] + polygon[n - 1][0]) * (polygon[0][1] - polygon[n - 1][1])
+ return 0.5 * abs(area)
diff --git a/polynomial_multiply.py b/polynomial_multiply.py
index 11fd194..15c8d7d 100644
--- a/polynomial_multiply.py
+++ b/polynomial_multiply.py
@@ -1,23 +1,24 @@
import math
-import ft
+import fft
-def polynominal_multiply(a, b, precision = 0):
+
+def polynominal_multiply(a, b, precision=0):
a_len = len(a)
b_len = len(b)
length = int(2 ** (1 + math.ceil(math.log(max(a_len, b_len)))))
- print length
+ print(length)
extend_a = [0] * length
extend_b = [0] * length
- for i in range(0, a_len):
+ for i in range(a_len):
extend_a[i] = a[i]
for i in range(a_len, length):
extend_a[i] = 0
- for i in range(0, b_len):
+ for i in range(b_len):
extend_b[i] = b[i]
for i in range(b_len, length):
extend_b[i] = 0
- a_fft = ft.recursive_fft(extend_a)
- b_fft = ft.recursive_fft(extend_b)
- m_fft = [a_fft[i] * b_fft[i] for i in range(0, len(a_fft))]
- ab = ft.recursive_inverse_fft(m_fft)
- return [round(ab[i].real, precision) for i in range(0, a_len + b_len - 1)]
+ a_fft = fft.recursive_fft(extend_a)
+ b_fft = fft.recursive_fft(extend_b)
+ m_fft = [a_fft[i] * b_fft[i] for i in range(len(a_fft))]
+ ab = fft.recursive_inverse_fft(m_fft)
+ return [round(ab[i].real, precision) for i in range(a_len + b_len - 1)]
diff --git a/pow.c b/pow.c
deleted file mode 100644
index 491909c..0000000
--- a/pow.c
+++ /dev/null
@@ -1,38 +0,0 @@
-// AUTHOR: WangQiang
-// CREATE DATE:
-// LAST UPDATE DATE: 20140524
-// EMAIL: cntqrxj@gmail.com
-
-/* pow: comput x^n; return value: x ^ n */
-int pow1(int x, unsigned n) {
- int square;
-
- if (n == 0)
- return 1;
- if (n == 1)
- return x;
-
- square = x * x;
- if (n == 2)
- return square;
- if (n % 2)
- return pow1(square, n / 2) * x;
- else
- return pow1(square, n / 2);
-}
-
-int pow2(int x, unsigned n) {
- int tmp;
-
- if (n == 0)
- return 1;
- if (n == 1)
- return x;
- if (n == 2)
- return x * x;
- tmp = pow2(x, n / 2);
- if (n % 2)
- return tmp * tmp * x;
- else
- return tmp * tmp;
-}
diff --git a/pow.py b/pow.py
new file mode 100644
index 0000000..00b5f0a
--- /dev/null
+++ b/pow.py
@@ -0,0 +1,22 @@
+def pow1(x, n: int):
+ """
+ compute x ^ n
+ """
+ if n == 0:
+ return 1
+ square = x * x
+ if n % 2:
+ return pow1(square, n // 2) * x
+ return pow1(square, n // 2)
+
+
+def pow2(x, n: int):
+ """
+ compute x ^ n
+ """
+ if n == 0:
+ return 1
+ tmp = pow2(x, n // 2)
+ if n % 2:
+ return tmp * tmp * x
+ return tmp * tmp
diff --git a/priority_queue.py b/priority_queue.py
index 7d9252b..2d39594 100644
--- a/priority_queue.py
+++ b/priority_queue.py
@@ -1,9 +1,11 @@
import sys
-from heap import max_heap, min_heap
+from heap import MaxHeap, MinHeap
-class max_priority_queue(max_heap):
+
+class MaxPriorityQueue(MaxHeap):
def heap_maximum(self):
return self[0]
+
def heap_extract_max(self):
if self.heap_size < 1:
sys.exit("heap underflow")
@@ -12,29 +14,33 @@ def heap_extract_max(self):
self.heap_size = self.heap_size - 1
self.max_heapify(0)
return maximum
+
def heap_increase_key(self, i, key):
if key < self[i]:
sys.exit("new key is smaller than current key")
self[i] = key
while i > 0 and self[self.parent(i)] < self[i]:
- tmp = self[self.parent(i)]
- self[self.parent(i)] = self[i]
- self[i] = tmp
+ self[i], self[self.parent(i)] = self[self.parent(i)], self[i]
i = self.parent(i)
+
def max_heap_insert(self, key):
if self.heap_size >= self.length:
sys.exit("heap overflow")
self.heap_size = self.heap_size + 1
self[self.heap_size - 1] = float("-Inf")
self.heap_increase_key(self.heap_size - 1, key)
+
def heap_delete(self, i):
self.heap_increase_key(i, float("Inf"))
self[0], self[self.heap_size - 1] = self[self.heap_size - 1], self[0]
self.heap_size = self.heap_size - 1
self.max_heapify(0)
-class min_priority_queue(min_heap):
+
+
+class MinPriorityQueue(MinHeap):
def heap_minimum(self):
return self[0]
+
def heap_extract_min(self):
if self.heap_size < 1:
sys.exit("heap underflow")
@@ -43,15 +49,15 @@ def heap_extract_min(self):
self.heap_size = self.heap_size - 1
self.min_heapify(0)
return minimum
+
def heap_decrease_key(self, i, key):
if key > self[i]:
sys.exit("new key is larger than current key")
self[i] = key
while i > 0 and self[self.parent(i)] > self[i]:
- tmp = self[self.parent(i)]
- self[self.parent(i)] = self[i]
- self[i] = tmp
+ self[i], self[self.parent(i)] = self[self.parent(i)], self[i]
i = self.parent(i)
+
def min_heap_insert(self, key):
if self.heap_size >= self.length:
sys.exit("heap overflow")
diff --git a/priority_queue_test.py b/priority_queue_test.py
deleted file mode 100644
index b9a9999..0000000
--- a/priority_queue_test.py
+++ /dev/null
@@ -1,74 +0,0 @@
-import unittest
-from priority_queue import max_priority_queue, min_priority_queue
-
-class TestMaxPriorityQueue(unittest.TestCase):
- def test_init(self):
- a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
- q = max_priority_queue(a)
- self.assertEquals(q, [16, 14, 10, 8, 7, 9, 3, 2, 4, 1])
- def test_heap_maximum(self):
- a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
- self.assertEquals(max_priority_queue(a).heap_maximum(), 16)
- def test_heap_extract_max(self):
- a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
- h = max_priority_queue(a)
- self.assertEquals(h.heap_extract_max(), 16)
- self.assertEquals(h, [14, 8, 10, 4, 7, 9, 3, 2, 1, 1])
- def test_heap_increase_key(self):
- a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
- h = max_priority_queue(a)
- h.heap_increase_key(8, 15)
- self.assertEquals(h, [16, 15, 10, 14, 7, 9, 3, 2, 8, 1])
- def test_heap_insert(self):
- a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
- queue = max_priority_queue(a)
- queue.heap_extract_max()
- queue.max_heap_insert(100)
- self.assertEquals(queue, [100, 14, 10, 4, 8, 9, 3, 2, 1, 7])
- def test_heap_delete(self):
- a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
- h = max_priority_queue(a)
- h.heap_delete(4)
- self.assertEquals(h[0:h.heap_size], [16, 14, 10, 8, 1, 9, 3, 2, 4])
- h.heap_delete(2)
- self.assertEquals(h[0:h.heap_size], [16, 14, 9, 8, 1, 4, 3, 2])
- h.heap_delete(0)
- self.assertEquals(h[0:h.heap_size], [14, 8, 9, 2, 1, 4, 3])
- h.heap_delete(5)
- self.assertEquals(h[0:h.heap_size], [14, 8, 9, 2, 1, 3])
- h.heap_delete(3)
- self.assertEquals(h[0:h.heap_size], [14, 8, 9, 3, 1])
- h.heap_delete(1)
- self.assertEquals(h[0:h.heap_size], [14, 3, 9, 1])
- h.heap_delete(3)
- self.assertEquals(h[0:h.heap_size], [14, 3, 9])
- h.heap_delete(2)
- self.assertEquals(h[0:h.heap_size], [14, 3])
- h.heap_delete(1)
- self.assertEquals(h[0:h.heap_size], [14])
- h.heap_delete(0)
- self.assertEquals(h[0:h.heap_size], [])
-class TestMinPriorityQueue(unittest.TestCase):
- def test_init(self):
- a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
- q = min_priority_queue(a)
- self.assertEquals(q, [1, 2, 3, 4, 7, 8, 9, 10, 14, 16])
- def test_heap_minimum(self):
- a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
- self.assertEquals(min_priority_queue(a).heap_minimum(), 1)
- def test_heap_extract_min(self):
- a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
- q = min_priority_queue(a)
- self.assertEquals(q.heap_extract_min(), 1)
- self.assertEquals(q, [2, 4, 3, 10, 7, 8, 9, 16, 14, 16])
- def test_heap_decrease_key(self):
- a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
- q = min_priority_queue(a)
- q.heap_decrease_key(8, 1)
- self.assertEquals(q, [1, 1, 3, 2, 7, 8, 9, 10, 4, 16])
- def test_heap_insert(self):
- a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
- q = min_priority_queue(a)
- q.heap_extract_min()
- q.min_heap_insert(0)
- self.assertEquals(q, [0, 2, 3, 10, 4, 8, 9, 16, 14, 7])
diff --git a/qsort.c b/qsort.c
deleted file mode 100644
index 9729ace..0000000
--- a/qsort.c
+++ /dev/null
@@ -1,25 +0,0 @@
-/* qsort: sort v[left]...v[right] into increasing order */
-void qsort(int v[], int left, int right) {
- int i, last;
-
- void swap(int v[], int, int);
-
- if (left >= right) /* do nothing if array contains */
- return; /* fewer than two elements */
- swap(v, left, (left + right)/2);
- last = left;
- for (i = left + 1; i <= right; i++)
- if (v[i] < v[left])
- swap(v, ++last, i);
- swap(v, left, last);
- qsort(v, left, last - 1 );
- qsort(v, last+1, right);
-}
-
-void swap(int v[], int i, int j) {
- int temp;
-
- temp = v[i];
- v[i] = v[j];
- v[j] = temp;
-}
diff --git a/quicksort.py b/quicksort.py
index e269c00..02b79e7 100644
--- a/quicksort.py
+++ b/quicksort.py
@@ -1,11 +1,15 @@
-from partition import partition, partition2, partition3, randomized_partition
-def quicksort(A, p, r, partition_method = partition):
- if p < r:
- q = partition_method(A, p, r)
- quicksort(A, p, q - 1)
- quicksort(A, q+1, r)
-def randomized_quicksort(A, p, r):
- if p < r:
- q = randomized_partition(A, p, r)
- randomized_quicksort(A, p, q - 1)
- randomized_quicksort(A, q+1, r)
+from partition import partition, randomized_partition
+
+
+def quicksort(array, left, right, partition_method=partition):
+ if left < right:
+ index = partition_method(array, left, right)
+ quicksort(array, left, index - 1)
+ quicksort(array, index + 1, right)
+
+
+def randomized_quicksort(array, left, right):
+ if left < right:
+ index = randomized_partition(array, left, right)
+ randomized_quicksort(array, left, index - 1)
+ randomized_quicksort(array, index + 1, right)
diff --git a/quicksort_test.py b/quicksort_test.py
deleted file mode 100644
index e09c230..0000000
--- a/quicksort_test.py
+++ /dev/null
@@ -1,32 +0,0 @@
-import unittest
-from partition import partition, partition2, partition3
-import random
-from quicksort import quicksort, randomized_quicksort
-
-class TestQuickSort(unittest.TestCase):
- def test_quicksort(self):
- for i in range(0, 100):
- A = [random.randint(1, 10000) for i in range(0, 100)]
- B = A[:]
- quicksort(A, 0, len(A) - 1, partition)
- B.sort()
- self.assertEquals(A, B)
- for i in range(0, 100):
- A = [random.randint(1, 10000) for i in range(0, 100)]
- B = A[:]
- quicksort(A, 0, len(A) - 1, partition2)
- B.sort()
- self.assertEquals(A, B)
- for i in range(0, 100):
- A = [random.randint(1, 10000) for i in range(0, 100)]
- B = A[:]
- quicksort(A, 0, len(A) - 1, partition3)
- B.sort()
- self.assertEquals(A, B)
- def test_randomized_quicksort(self):
- for i in range(0, 100):
- A = [random.randint(1, 10000) for i in range(0, 100)]
- B = A[:]
- randomized_quicksort(A, 0, len(A) - 1)
- B.sort()
- self.assertEquals(A, B)
diff --git a/random_array.py b/random_array.py
new file mode 100644
index 0000000..e1a7cca
--- /dev/null
+++ b/random_array.py
@@ -0,0 +1,6 @@
+import random
+
+
+def random_arrays(array_num=100, array_size=100, array_lowerbound=0, array_upperbound=10000):
+ for _ in range(array_num):
+ yield [random.randint(array_lowerbound, array_upperbound) for _ in range(array_size)]
diff --git a/randomized_permute.py b/randomized_permute.py
index b1d05c6..a5bc53a 100644
--- a/randomized_permute.py
+++ b/randomized_permute.py
@@ -1,16 +1,17 @@
import random
+
def randomize_in_place(A):
- '''
+ """
An algorithm to permute the given array in place.
It computes a uniform random permutation.
- '''
+ """
n = len(A)
- for i in range(0, n):
+ for i in range(n):
j = random.randint(i, n - 1)
A[i], A[j] = A[j], A[i]
-#def permute_by_sorting(A):
+# def permute_by_sorting(A):
# n = len(A)
# P = [0] * n
-# for i in
+# for i in
diff --git a/randomized_select.py b/randomized_select.py
index fac9905..101525f 100644
--- a/randomized_select.py
+++ b/randomized_select.py
@@ -1,5 +1,6 @@
from partition import randomized_partition
+
def randomized_select(A, p, r, i):
if p == r:
return A[p]
@@ -11,4 +12,3 @@ def randomized_select(A, p, r, i):
return randomized_select(A, p, q - 1, i)
else:
return randomized_select(A, q + 1, r, i - k)
-
diff --git a/rank_tree.py b/rank_tree.py
index e9d66d4..5c1e8e5 100644
--- a/rank_tree.py
+++ b/rank_tree.py
@@ -1,17 +1,20 @@
# The variant of os_tree that use rank instead of size
-#!/usr/bin/env ipython
+# !/usr/bin/env python
-from rb_tree import rb_node, rb_tree
+from rb_tree import RbNode, RbTree
-class rank_node(rb_node):
+
+class rank_node(RbNode):
def __init__(self, key, p, left, right, color, rank):
- rb_node.__init__(self, key, p, left, right, color)
+ RbNode.__init__(self, key, p, left, right, color)
self.rank = rank
+
def update_rank_whole_tree(self, amount):
if self.rank != 0:
self.rank = self.rank + amount
self.left.update_rank_whole_tree(amount)
self.right.update_rank_whole_tree(amount)
+
def decrease_all_successors(self, amount):
self.rank = self.rank - amount
self.right.update_rank_whole_tree(-1 * amount)
@@ -23,15 +26,18 @@ def decrease_all_successors(self, amount):
if y.rank != 0:
y.decrease_all_successors(amount)
-class rank_tree(rb_tree):
+
+class rank_tree(RbTree):
nil = rank_node(None, None, None, None, 1, 0)
root = nil
+
def __init__(self, values):
if isinstance(values, list):
for i in values:
self.insert(rank_node(i, None, None, None, 0, 1))
else:
- print "Not invalid argument"
+ print("Not invalid argument")
+
def insert(self, z):
y = self.nil
x = self.root
@@ -55,10 +61,11 @@ def insert(self, z):
z.p = y
z.left = self.nil
z.right = self.nil
- z.color = 0 #red
+ z.color = 0 # red
self.insert_fixed(z)
+
def delete(self, z):
- z.decrease_all_successors(1) # z is counted as a successor
+ z.decrease_all_successors(1) # z is counted as a successor
y = z
y_original_color = y.color
if z.left == self.nil:
diff --git a/rb_tree.py b/rb_tree.py
index 3d5d0a3..77a33c9 100644
--- a/rb_tree.py
+++ b/rb_tree.py
@@ -1,13 +1,15 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
# we use 0 to mean red, 1 to mean black
from tree import Node, Tree
-class rb_node(Node):
+
+class RbNode(Node):
def __init__(self, key, p, left, right, color):
Node.__init__(self, key, p, left, right)
self.color = color
+
def minimum(self, nil):
x = self
y = x
@@ -16,17 +18,21 @@ def minimum(self, nil):
x = x.left
return y
-class rb_tree(Tree):
- nil = rb_node(None, None, None, None, 1)
+
+class RbTree(Tree):
+ nil = RbNode(None, None, None, None, 1)
root = nil
+
def __init__(self, values):
if isinstance(values, list):
for i in values:
- self.insert(rb_node(i, None, None, None, 0))
+ self.insert(RbNode(i, None, None, None, 0))
else:
- print "Not invalid argument"
+ print("Not invalid argument")
+
def minimum(self):
return self.root.minimum(self.nil)
+
def __getitem__(self, key):
return self.iterative_tree_search(key)
@@ -82,8 +88,9 @@ def insert(self, z):
z.p = y
z.left = self.nil
z.right = self.nil
- z.color = 0 #red
+ z.color = 0 # red
self.insert_fixed(z)
+
def insert_fixed(self, z):
while z.p.color == 0:
if z.p.p.left == z.p:
@@ -117,6 +124,7 @@ def insert_fixed(self, z):
z.color = 0
z.p.color = 1
self.root.color = 1
+
def iterative_tree_search(self, k):
x = self.root
while x != self.nil and x.key != k:
@@ -134,6 +142,7 @@ def transplant(self, u, v):
else:
u.p.right = v
v.p = u.p
+
def delete(self, z):
y = z
y_original_color = y.color
@@ -159,6 +168,7 @@ def delete(self, z):
y.color = z.color
if y_original_color == 1:
self.delete_fixup(x)
+
def delete_fixup(self, x):
while x != self.root and x.color == 1:
if x == x.p.left:
diff --git a/right_horizontal_ray_intersect.py b/right_horizontal_ray_intersect.py
index 9ba42d5..0f2c43f 100644
--- a/right_horizontal_ray_intersect.py
+++ b/right_horizontal_ray_intersect.py
@@ -1,9 +1,10 @@
-#!/usr/bin/ipython
+#!/usr/bin/python
from segment_intersect import segments_intersect
+
def right_horizontal_ray_intersect(p0, p1, p2):
- '''An algorithm to determine whether a given right horizontal ray from p0 intersects a line segment p1p2'''
+ """An algorithm to determine whether a given right horizontal ray from p0 intersects a line segment p1p2"""
max_x = max(p1[0], p2[0])
if max_x < p0[0]:
return False
@@ -15,6 +16,7 @@ def right_horizontal_ray_intersect(p0, p1, p2):
return equal(p0, p1) or equal(p0, p2)
else:
return segments_intersect(p1, p2, p0, (max_x, p0[1]))
-
+
+
def equal(p1, p2):
return p1[0] == p2[0] and p1[1] == p2[1]
diff --git a/segment_intersect.py b/segment_intersect.py
index b17b420..9a594ab 100644
--- a/segment_intersect.py
+++ b/segment_intersect.py
@@ -1,11 +1,12 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
+
def segments_intersect(p1, p2, p3, p4):
d1 = direction(p3, p4, p1)
d2 = direction(p3, p4, p2)
d3 = direction(p1, p2, p3)
d4 = direction(p1, p2, p4)
- if ((d1 > 0 and d2 < 0) or (d1 < 0 and d2 > 0)) and ((d3 > 0 and d4 < 0) or (d3 < 0 and d4 > 0)):
+ if ((d1 > 0 > d2) or (d1 < 0 < d2)) and ((d3 > 0 > d4) or (d3 < 0 < d4)):
return True
elif d1 == 0 and on_segment(p3, p4, p1):
return True
@@ -17,12 +18,14 @@ def segments_intersect(p1, p2, p3, p4):
return True
else:
return False
+
+
def direction(pi, pj, pk):
v1 = (pk[0] - pi[0], pk[1] - pi[1])
v2 = (pj[0] - pi[0], pj[1] - pi[1])
return v1[0] * v2[1] - v2[0] * v1[1]
+
+
def on_segment(pi, pj, pk):
- if min(pi[0], pj[0]) <= pk[0] and pk[0] <= max(pi[0], pj[0]) and min(pi[1], pj[1]) <= pk[1] and pk[1] <= max(pi[1], pj[1]):
- return True
- else:
- return False
+ return min(pi[0], pj[0]) <= pk[0] <= max(pi[0], pj[0]) and min(pi[1], pj[1]) <= pk[1] <= max(
+ pi[1], pj[1])
diff --git a/selection-sort.c b/selection-sort.c
deleted file mode 100644
index 1ed70eb..0000000
--- a/selection-sort.c
+++ /dev/null
@@ -1,29 +0,0 @@
-#include
-
-void SelectionSort(int *A, int n) {
- int i, j;
- int min, index;
- int tmp;
-
- for (i = 0; i < n - 1; i++) {
- min = A[i];
- index = i;
-
- for (j = i + 1; j < n; j++)
- if (A[j] < min) {
- min = A[j];
- index = j;
- }
- tmp = A[i];
- A[i] = A[index];
- A[index] = tmp;
- }
-}
-
-int main() {
- int A[6] = {6, 5, 5, 3, 100, 1};
-
- SelectionSort(A, 6);
- printf("%d, %d, %d, %d, %d, %d\n", A[0], A[1], A[2], A[3], A[4], A[5]);
- return 0;
-}
diff --git a/selection_sort.py b/selection_sort.py
new file mode 100644
index 0000000..a7b18a8
--- /dev/null
+++ b/selection_sort.py
@@ -0,0 +1,22 @@
+#!/usr/bin/env python
+# encoding: utf-8
+
+
+def selection_sort(array: list):
+ """
+ Inplace sort
+ Consider sorting n numbers stored in array A by first finding the smallest element of A
+ and exchanging it with the element in A[0] . Then find the second smallest element of A, and exchange it with A[1].
+ Continue in this manner for the first n - 1 elements of A.
+ :param array:
+ :return:
+ """
+ n = len(array)
+ for i in range(n - 1):
+ minimum = array[i]
+ index = i
+ for j in range(i + 1, n):
+ if minimum > array[j]:
+ minimum = array[j]
+ index = j
+ array[i], array[index] = array[index], array[i]
diff --git a/simplex.py b/simplex.py
index d472d2d..249ed80 100644
--- a/simplex.py
+++ b/simplex.py
@@ -1,34 +1,36 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import sys
+
def pivot(N, B, A, b, c, v, l, e):
new_A = dict()
new_b = dict()
new_c = dict()
-#Compute the coefficients of the equation for new basic variable
+ # Compute the coefficients of the equation for new basic variable
new_b[e] = b[l] / A[l][e]
new_A[e] = dict()
for j in N - {e}:
new_A[e][j] = A[l][j] / A[l][e]
new_A[e][l] = 1 / A[l][e]
-#Compute the coefficients of the remaining constraints
+ # Compute the coefficients of the remaining constraints
for i in B - {l}:
new_A[i] = dict()
new_b[i] = b[i] - A[i][e] * new_b[e]
for j in N - {e}:
new_A[i][j] = A[i][j] - A[i][e] * new_A[e][j]
new_A[i][l] = -1 * A[i][e] * new_A[e][l]
-#Compute the objective function
+ # Compute the objective function
new_v = v + c[e] * new_b[e]
for j in N - {e}:
new_c[j] = c[j] - c[e] * new_A[e][j]
new_c[l] = -1 * c[e] * new_A[e][l]
-#Compute new sets of basic and nonbasic variables
+ # Compute new sets of basic and nonbasic variables
new_N = (N - {e}).union({l})
new_B = (B - {l}).union({e})
return new_N, new_B, new_A, new_b, new_c, new_v
+
def simplex(A, b, c):
N, B, A, b, c, v = initialize_simplex(A, b, c)
while True:
@@ -37,7 +39,7 @@ def simplex(A, b, c):
if c[j] > 0:
e = j
break
- if e == None:
+ if not e:
break
minimum = float("Inf")
for i in sorted(B):
@@ -50,7 +52,7 @@ def simplex(A, b, c):
return "unbounded"
else:
(N, B, A, b, c, v) = pivot(N, B, A, b, c, v, l, e)
- print N, B, A, b, c, v
+ print(N, B, A, b, c, v)
n = len(N)
x = [0] * n
for i in range(1, n + 1):
@@ -58,11 +60,12 @@ def simplex(A, b, c):
x[i - 1] = b[i]
return x
+
def initialize_simplex(A, b, c):
m = len(b)
n = len(c)
minimum = float("Inf")
- for i in range(0, m):
+ for i in range(m):
if minimum > b[i]:
k = i + 1
minimum = b[i]
@@ -88,29 +91,29 @@ def initialize_simplex(A, b, c):
new_A[n + i] = dict()
new_A[n + i][0] = -1
for j in range(1, n + 1):
- new_A[n + i][j] = A[i -1][j - 1]
+ new_A[n + i][j] = A[i - 1][j - 1]
for j in range(1, n + 1):
new_c[j] = 0
new_c[0] = -1
A = new_A
b = new_b
c = new_c
- N = set(range(0, n + 1))
+ N = set(range(n + 1))
B = set(range(n + 1, n + m + 1))
v = 0
l = n + k
(N, B, A, b, c, v) = pivot(N, B, A, b, c, v, l, 0)
- print N, B, A, b, c, v
+ print(N, B, A, b, c, v)
while True:
e = None
- print N
+ print(N)
for j in sorted(N):
- print "c[{}] = {}".format(j, c[j])
+ print("c[{}] = {}".format(j, c[j]))
if c[j] > 0:
e = j
break
- print "e = {}".format(e)
- if e == None:
+ print("e = {}".format(e))
+ if not e:
break
minimum = float("Inf")
for i in sorted(B):
@@ -119,15 +122,15 @@ def initialize_simplex(A, b, c):
if minimum > delta:
l = i
minimum = delta
- print "l = {}".format(l)
+ print("l = {}".format(l))
if minimum == float("Inf"):
-# return "unbounded"
+ # return "unbounded"
break
else:
(N, B, A, b, c, v) = pivot(N, B, A, b, c, v, l, e)
- print N, B, A, b, c, v
+ print(N, B, A, b, c, v)
if abs(v) <= 2.0e-10:
- # if v == 0:
+ # if v == 0:
if 0 in B:
for e in N:
if A[0][e] != 0:
@@ -144,21 +147,20 @@ def initialize_simplex(A, b, c):
N = N - {0}
for j in N:
new_c[j] = 0
- j
- print N, B, A, b, c, v
+ print(N, B, A, b, c, v)
for i in range(1, n + 1):
if i in B:
v = v + c[i] * b[i]
for j in N:
new_c[j] = new_c[j] - c[i] * A[i][j]
else:
- print "i = {}".format(i)
- print N
- print B
- print new_c
- print c
+ print("i = {}".format(i))
+ print(N)
+ print(B)
+ print(new_c)
+ print(c)
new_c[i] = new_c[i] + c[i - 1]
- print N, B, new_A, b, new_c, v
+ print(N, B, new_A, b, new_c, v)
return N, B, new_A, b, new_c, v
else:
sys.exit("infeasible")
diff --git a/single_edge.py b/single_edge.py
index 50e57b1..f3736c9 100644
--- a/single_edge.py
+++ b/single_edge.py
@@ -1,135 +1,144 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-class node(object):
+class node:
def __init__(self, key, right):
self.right = right
self.key = key
-class graph(object):
- def __init__(self, data, option = 0):
+
+
+class graph:
+ def __init__(self, data, option=0):
if option == 0:
self.vertices_number = len(data)
self.vertices = [None] * self.vertices_number
self.edges_number = 0
- for i in range(0, self.vertices_number):
+ for i in range(self.vertices_number):
for j in data[i]:
self.insert_edge(i + 1, j)
elif option == 1:
self.vertices_number = data
self.vertices = [None] * self.vertices_number
self.edges_number = 0
+
def transpose(self):
t = graph(self.vertices_number, 1)
- for i in range(0, self.vertices_number):
+ for i in range(self.vertices_number):
j = self.vertices[i]
- while j != None:
+ while j is not None:
t.insert_edge(j.key, i + 1)
j = j.right
return t
+
def union(self, g):
u = graph(self.vertices_number, 1)
- for i in range(0, self.vertices_number):
+ for i in range(self.vertices_number):
j = self.vertices[i]
- while j != None:
+ while j is not None:
u.insert_edge(i + 1, j.key)
j = j.right
- for i in range(0, g.vertices_number):
+ for i in range(g.vertices_number):
j = g.vertices[i]
- while j != None:
+ while j is not None:
u.insert_edge(i + 1, j.key)
j = j.right
- return u
+ return u
+
def single_edge(self):
g = self.union(self.transpose())
single = graph(g.vertices_number, 1)
s = [0] * g.vertices_number
- for u in range(0, g.vertices_number):
+ for u in range(g.vertices_number):
v = g.vertices[u]
- while v != None:
+ while v:
if (u + 1) != v.key and s[v.key - 1] == 0:
single.insert_edge(u + 1, v.key)
s[v.key - 1] = 1
v = v.right
v = g.vertices[u]
- while v != None:
+ while v:
if s[v.key - 1] == 1:
s[v.key - 1] = 0
v = v.right
s[u] = 2
return single
+
def insert_edge(self, u, v):
a = node(v, self.vertices[u - 1])
self.vertices[u - 1] = a
self.edges_number = self.edges_number + 1
+
def print_graph(self):
- for i in range(0, self.vertices_number):
+ for i in range(self.vertices_number):
j = self.vertices[i]
- print '{}: '.format(i + 1),
- while j != None:
- print j.key,
+ print('{}: '.format(i + 1), )
+ while j is not None:
+ print(j.key, )
j = j.right
- print
+ print()
+
def square(self):
grandchild = graph(self.vertices_number, 1)
descendent = graph(self.vertices_number, 1)
s = [0] * self.vertices_number
# generate grandchild graph
- for i in range(0, self.vertices_number):
+ for i in range(self.vertices_number):
j = self.vertices[i]
- while j != None:
+ while j is not None:
k = self.vertices[j.key - 1]
- while k != None:
+ while k is not None:
if s[k.key - 1] == 0:
- grandchild.insert_edge(i + 1, k.key)
+ grandchild.insert_edge(i + 1, k.key)
s[k.key - 1] = 1
k = k.right
j = j.right
j = grandchild.vertices[i]
- while j != None:
+ while j is not None:
s[j.key - 1] = 0
j = j.right
# generate great grandchild graph
- for i in range(0, grandchild.vertices_number):
+ for i in range(grandchild.vertices_number):
j = grandchild.vertices[i]
- while j != None:
+ while j is not None:
k = self.vertices[j.key - 1]
- while k != None:
+ while k is not None:
if s[k.key - 1] == 0:
- descendent.insert_edge(i + 1, k.key)
+ descendent.insert_edge(i + 1, k.key)
k = k.right
j = j.right
j = descendent.vertices[i]
- while j != None:
+ while j is not None:
s[j.key - 1] = 0
j = j.right
square = graph(self.vertices_number, 1)
- for i in range(0, self.vertices_number):
+ for i in range(self.vertices_number):
j = self.vertices[i]
- print j
- while j != None:
+ print(j)
+ while j is not None:
square.insert_edge(i + 1, j.key)
s[j.key - 1] = 1
j = j.right
j = grandchild.vertices[i]
- while j != None:
+ while j is not None:
if s[j.key - 1] == 0 and (i + 1) != j.key:
square.insert_edge(i + 1, j.key)
s[j.key - 1] = 1
j = j.right
j = descendent.vertices[i]
- while j != None:
+ while j is not None:
if s[j.key - 1] == 0 and (i + 1) != j.key:
square.insert_edge(i + 1, j.key)
s[j.key - 1] = 1
j = j.right
j = square.vertices[i]
- while j != None:
+ while j is not None:
s[j.key - 1] = 0
j = j.right
-# self.print_graph()
-# grandchild.print_graph()
-# print
-# descendent.print_graph()
+ # self.print(_graph())
+ # grandchild.print(_graph())
+ # print()
+ # descendent.print(_graph())
return square
+
def grandchild(self):
pass
diff --git a/square-matrix-multiply-Strassen.py b/square_matrix_multiply_Strassen.py
similarity index 50%
rename from square-matrix-multiply-Strassen.py
rename to square_matrix_multiply_Strassen.py
index f39dd74..a006392 100755
--- a/square-matrix-multiply-Strassen.py
+++ b/square_matrix_multiply_Strassen.py
@@ -1,40 +1,36 @@
#! /usr/bin/python2.7
-# AUTHOR: WangQiang
-# CREATE DATE: 20140603
-# LAST UPDATE DATE: 20140604
-# EMAIL: cntqrxj@gmail.com
-
from numpy import *
+
def square_matrix_multiply(A, B):
shape = A.shape
length = shape[0]
half = length / 2
-
- C = zeros(shape, dtype = int64)
+
+ C = zeros(shape, dtype=int64)
if length == 1:
C[0, 0] = A[0, 0] * B[0, 0]
return C
-
- S1 = zeros((half, half), dtype = int64)
- S2 = zeros((half, half), dtype = int64)
- S3 = zeros((half, half), dtype = int64)
- S4 = zeros((half, half), dtype = int64)
- S5 = zeros((half, half), dtype = int64)
- S6 = zeros((half, half), dtype = int64)
- S7 = zeros((half, half), dtype = int64)
- S8 = zeros((half, half), dtype = int64)
- S9 = zeros((half, half), dtype = int64)
- S10 = zeros((half, half), dtype = int64)
- P1 = zeros((half, half), dtype = int64)
- P2 = zeros((half, half), dtype = int64)
- P3 = zeros((half, half), dtype = int64)
- P4 = zeros((half, half), dtype = int64)
- P5 = zeros((half, half), dtype = int64)
- P6 = zeros((half, half), dtype = int64)
- P7 = zeros((half, half), dtype = int64)
+ S1 = zeros((half, half), dtype=int64)
+ S2 = zeros((half, half), dtype=int64)
+ S3 = zeros((half, half), dtype=int64)
+ S4 = zeros((half, half), dtype=int64)
+ S5 = zeros((half, half), dtype=int64)
+ S6 = zeros((half, half), dtype=int64)
+ S7 = zeros((half, half), dtype=int64)
+ S8 = zeros((half, half), dtype=int64)
+ S9 = zeros((half, half), dtype=int64)
+ S10 = zeros((half, half), dtype=int64)
+
+ P1 = zeros((half, half), dtype=int64)
+ P2 = zeros((half, half), dtype=int64)
+ P3 = zeros((half, half), dtype=int64)
+ P4 = zeros((half, half), dtype=int64)
+ P5 = zeros((half, half), dtype=int64)
+ P6 = zeros((half, half), dtype=int64)
+ P7 = zeros((half, half), dtype=int64)
S1 = B[0:half, half:length] - B[half:length, half:length]
S2 = A[0:half, 0:half] + A[0:half, half:length]
@@ -54,21 +50,22 @@ def square_matrix_multiply(A, B):
P5 = square_matrix_multiply(S5, S6)
P6 = square_matrix_multiply(S7, S8)
P7 = square_matrix_multiply(S9, S10)
-
+
C[0:half, 0:half] = P5 + P4 - P2 + P6
C[0:half, half:length] = P1 + P2
C[half:length, 0:half] = P3 + P4
C[half:length, half:length] = P5 + P1 - P3 - P7
-
- return C
-#A = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
-#B = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
-#A = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
-#B = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
-A = array([[1, 3], [7, 5]])
-B = array([[6, 8], [4, 2]])
-#A = array([[1, 2, 3], [4, 5, 6]])
-#B = array([[1, 2], [4, 5]])
-print square_matrix_multiply(A, B)
-#print dot(A, B)
+ return C
+
+
+# # A = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
+# # B = array([[1, 2, 3, 4], [5, 6, 7, 8], [9, 10, 11, 12], [13, 14, 15, 16]])
+# # A = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
+# # B = array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
+# A = array([[1, 3], [7, 5]])
+# B = array([[6, 8], [4, 2]])
+# # A = array([[1, 2, 3], [4, 5, 6]])
+# # B = array([[1, 2], [4, 5]])
+# print(square_matrix_multiply(A, B))
+# # print( dot(A, B))
diff --git a/stack.py b/stack.py
index 854f5bf..19b17d3 100644
--- a/stack.py
+++ b/stack.py
@@ -1,30 +1,36 @@
-class FullException(BaseException):
+class FullException(Exception):
pass
-class EmptyException(BaseException):
+
+
+class EmptyException(Exception):
pass
-class stack(list):
+class Stack(list):
def __init__(self, size):
- list.__init__(self, [None] * size)
+ super(Stack, self).__init__([None] * size)
self.top = -1
self.size = len(size)
+
def push(self, x):
if self.full():
raise FullException("This stack is full")
else:
self.top = self.top + 1
self[self.top] = x
- def pop(self):
+
+ def pop(self, *args, **kwargs):
if self.empty():
raise EmptyException('This stack is empty')
else:
self.top = self.top - 1
return self[self.top + 1]
+
def empty(self):
- return self.top == -1:
+ return self.top == -1
+
def full(self):
- return self.top == self.size - 1:
+ return self.top == self.size - 1
# def multipop(self, k):
# l = []
diff --git a/synthetic_division.py b/synthetic_division.py
index 260e3e5..d3b84a9 100644
--- a/synthetic_division.py
+++ b/synthetic_division.py
@@ -1,4 +1,5 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
+
def synthetic_division(A, n, x):
q = [0] * (n - 1)
diff --git a/test.sh b/test.sh
deleted file mode 100644
index 8de1f72..0000000
--- a/test.sh
+++ /dev/null
@@ -1 +0,0 @@
-for f in $(ls *test.py | cut -d '.' -f1); do ipython -m unittest $f;done
diff --git a/tests/Bellman_Ford_matrix_test.py b/tests/Bellman_Ford_matrix_test.py
new file mode 100644
index 0000000..012f71c
--- /dev/null
+++ b/tests/Bellman_Ford_matrix_test.py
@@ -0,0 +1,22 @@
+from Bellman_Ford_matrix import Bellman_Ford_matrix, slow_all_pairs_shortest_paths
+import unittest
+import numpy
+
+
+class TestBellmanFordMatrix(unittest.TestCase):
+ def test_Bellman_Ford_matrix(self):
+ W = numpy.array([[float("Inf"), 6., 7., float("Inf"), float("Inf")], [float("Inf"), float("Inf"), 8., 5., -4.],
+ [float("Inf"), float("Inf"), float("Inf"), -3., 9.],
+ [float("Inf"), -2., float("Inf"), float("Inf"), float("Inf")],
+ [2., float("Inf"), float("Inf"), 7., float("Inf")]])
+ d, p = Bellman_Ford_matrix(W, 1)
+ self.assertEqual(d, [0, 2.0, 7.0, 4.0, -2.0])
+ self.assertEqual(p, [None, 4, 1, 3, 2])
+
+ def test_slow_all_pairs_shortest_paths(self):
+ W = numpy.array([[0, 6., 7., float("Inf"), float("Inf")], [float("Inf"), 0, 8., 5., -4.],
+ [float("Inf"), float("Inf"), 0, -3., 9.], [float("Inf"), -2., float("Inf"), 0, float("Inf")],
+ [2., float("Inf"), float("Inf"), 7., 0]])
+ L = slow_all_pairs_shortest_paths(W, 1)
+ # print(L)
+ self.assertEqual(L, [0, 2.0, 7.0, 4.0, -2.0])
diff --git a/tests/Horner_rule_test.py b/tests/Horner_rule_test.py
new file mode 100644
index 0000000..2e33809
--- /dev/null
+++ b/tests/Horner_rule_test.py
@@ -0,0 +1,17 @@
+#!/usr/bin/env python
+# encoding: utf-8
+
+import unittest
+import random
+from Horner_rule import Horner_rule
+
+
+class TestHornerRule(unittest.TestCase):
+ def test_horner_rule(self):
+ for _ in range(100):
+ x = random.randint(1, 5)
+ coefficients = [random.randint(0, 100) for _ in range(11)]
+ expected_result = 0
+ for index, coefficient in enumerate(coefficients):
+ expected_result += coefficient * x ** index
+ self.assertEqual(Horner_rule(x, coefficients), expected_result)
diff --git a/Johnson_test.py b/tests/Johnson_test.py
similarity index 85%
rename from Johnson_test.py
rename to tests/Johnson_test.py
index 5352e58..f062a6a 100644
--- a/Johnson_test.py
+++ b/tests/Johnson_test.py
@@ -2,6 +2,7 @@
from graph import Vertex, Graph
import unittest
+
class TestJohnson(unittest.TestCase):
def testJohnson(self):
a1 = Vertex(1)
@@ -14,10 +15,10 @@ def testJohnson(self):
g = Graph(vertices, edges)
weight = [3, 8, -4, 1, 7, 4, 2, -5, 6]
w = dict()
- for i,j in zip(edges, weight):
- w[i] = j
+ for i, j in zip(edges, weight):
+ w[i] = j
D = Johnson(g, w)
- print D
+ # print(D)
a1 = Vertex(1)
a2 = Vertex(2)
a3 = Vertex(3)
@@ -29,7 +30,7 @@ def testJohnson(self):
g = Graph(vertices, edges)
weight = [-1, 1, 2, 2, -8, -4, 3, 7, 5, 10]
w = dict()
- for i,j in zip(edges, weight):
- w[i] = j
+ for i, j in zip(edges, weight):
+ w[i] = j
D = Johnson(g, w)
- print D
+ # print(D)
diff --git a/tests/__init__.py b/tests/__init__.py
new file mode 100644
index 0000000..e69de29
diff --git a/tests/all_pairs_shortest_paths_test.py b/tests/all_pairs_shortest_paths_test.py
new file mode 100644
index 0000000..a5bf18b
--- /dev/null
+++ b/tests/all_pairs_shortest_paths_test.py
@@ -0,0 +1,43 @@
+from all_pairs_shortest_paths import slow_all_pairs_shortest_paths, faster_all_pairs_shortest_paths
+import unittest
+import numpy as np
+
+
+class TestAllPairsShortestPaths(unittest.TestCase):
+ def test_slow_all_pairs_shortest_paths(self):
+ W = np.array([[0, 3, 8, float("Inf"), -4], [float("Inf"), 0, float("Inf"), 1, 7],
+ [float("Inf"), 4, 0, float("Inf"), float("Inf")], [2, float("Inf"), -5, 0, float("Inf")],
+ [float("Inf"), float("Inf"), float("Inf"), 6, 0]])
+ R = slow_all_pairs_shortest_paths(W)
+ L = np.array([[0, 1, -3, 2, -4], [3, 0, -4, 1, -1], [7, 4, 0, 5, 3], [2, -1, -5, 0, -2], [8, 5, 1, 6, 0]])
+ self.assertEqual((R == L).all(), True)
+ W = np.array([[0, float("Inf"), float("Inf"), float("Inf"), -1, float("Inf")],
+ [1, 0, float("Inf"), 2, float("Inf"), float("Inf")],
+ [float("Inf"), 2, 0, float("Inf"), float("Inf"), -8],
+ [-4, float("Inf"), float("Inf"), 0, 3, float("Inf")],
+ [float("Inf"), 7, float("Inf"), float("Inf"), 0, float("Inf")],
+ [float("Inf"), 5, 10, float("Inf"), float("Inf"), 0]])
+ R = slow_all_pairs_shortest_paths(W)
+ L = np.array([[0, 6, float("Inf"), 8, -1, float("Inf")], [-2, 0, float("Inf"), 2, -3, float("Inf")],
+ [-5, -3, 0, -1, -6, -8], [-4, 2, float("Inf"), 0, -5, float("Inf")],
+ [5, 7, float("Inf"), 9, 0, float("Inf")], [3, 5, 10, 7, 2, 0]])
+ self.assertEqual((R == L).all(), True)
+
+ def test_faster_all_pairs_shortest_paths(self):
+ W = np.array([[0, 3, 8, float("Inf"), -4], [float("Inf"), 0, float("Inf"), 1, 7],
+ [float("Inf"), 4, 0, float("Inf"), float("Inf")], [2, float("Inf"), -5, 0, float("Inf")],
+ [float("Inf"), float("Inf"), float("Inf"), 6, 0]])
+ R = faster_all_pairs_shortest_paths(W)
+ L = np.array([[0, 1, -3, 2, -4], [3, 0, -4, 1, -1], [7, 4, 0, 5, 3], [2, -1, -5, 0, -2], [8, 5, 1, 6, 0]])
+ self.assertEqual((R == L).all(), True)
+ W = np.array([[0, float("Inf"), float("Inf"), float("Inf"), -1, float("Inf")],
+ [1, 0, float("Inf"), 2, float("Inf"), float("Inf")],
+ [float("Inf"), 2, 0, float("Inf"), float("Inf"), -8],
+ [-4, float("Inf"), float("Inf"), 0, 3, float("Inf")],
+ [float("Inf"), 7, float("Inf"), float("Inf"), 0, float("Inf")],
+ [float("Inf"), 5, 10, float("Inf"), float("Inf"), 0]])
+ R = faster_all_pairs_shortest_paths(W)
+ L = np.array([[0, 6, float("Inf"), 8, -1, float("Inf")], [-2, 0, float("Inf"), 2, -3, float("Inf")],
+ [-5, -3, 0, -1, -6, -8], [-4, 2, float("Inf"), 0, -5, float("Inf")],
+ [5, 7, float("Inf"), 9, 0, float("Inf")], [3, 5, 10, 7, 2, 0]])
+ self.assertEqual((R == L).all(), True)
diff --git a/bh_tree_test.py b/tests/bh_tree_test.py
similarity index 94%
rename from bh_tree_test.py
rename to tests/bh_tree_test.py
index 4979b1f..24bf74d 100755
--- a/bh_tree_test.py
+++ b/tests/bh_tree_test.py
@@ -1,27 +1,31 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
from bh_tree import bh_tree, bh_node
-class TestRbtree(unittest.TestCase):
+class TestRbTree(unittest.TestCase):
def test_insert_one(self):
T = bh_tree([41])
self.wrap(T, 41, 1)
+
def test_insert_two(self):
T = bh_tree([41, 38])
self.wrap(T, 41, 1)
self.wrap(T, 38, 1)
+
def test_insert_three(self):
T = bh_tree([41, 38, 31])
self.wrap(T, 38, 1)
self.wrap(T, 31, 1)
self.wrap(T, 41, 1)
+
def test_insert_four(self):
T = bh_tree([41, 38, 31, 12])
self.wrap(T, 38, 2)
self.wrap(T, 31, 1)
self.wrap(T, 41, 1)
self.wrap(T, 12, 1)
+
def test_insert_five(self):
T = bh_tree([41, 38, 31, 12, 19])
self.wrap(T, 38, 2)
@@ -29,6 +33,7 @@ def test_insert_five(self):
self.wrap(T, 41, 1)
self.wrap(T, 12, 1)
self.wrap(T, 31, 1)
+
def test_insert_six(self):
T = bh_tree([41, 38, 31, 12, 19, 9])
self.wrap(T, 38, 2)
@@ -37,6 +42,7 @@ def test_insert_six(self):
self.wrap(T, 12, 1)
self.wrap(T, 31, 1)
self.wrap(T, 9, 1)
+
def test_delete_one(self):
T = bh_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -45,6 +51,7 @@ def test_delete_one(self):
self.wrap(T, 41, 1)
self.wrap(T, 12, 1)
self.wrap(T, 31, 1)
+
def test_delete_two(self):
T = bh_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -53,6 +60,7 @@ def test_delete_two(self):
self.wrap(T, 19, 1)
self.wrap(T, 41, 1)
self.wrap(T, 31, 1)
+
def test_delete_three(self):
T = bh_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -61,6 +69,7 @@ def test_delete_three(self):
self.wrap(T, 38, 2)
self.wrap(T, 31, 1)
self.wrap(T, 41, 1)
+
def test_delete_four(self):
T = bh_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -69,6 +78,7 @@ def test_delete_four(self):
T.delete(T.iterative_tree_search(31))
self.wrap(T, 38, 1)
self.wrap(T, 41, 1)
+
def test_delete_five(self):
T = bh_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -77,6 +87,7 @@ def test_delete_five(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
self.wrap(T, 41, 1)
+
def test_delete_six(self):
T = bh_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -85,8 +96,11 @@ def test_delete_six(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
T.delete(T.iterative_tree_search(41))
- self.assertEquals(T.root, T.nil)
+ self.assertEqual(T.root, T.nil)
+
def wrap(self, tree, node, bh):
- self.assertEquals(tree.iterative_tree_search(node).bh, bh)
+ self.assertEqual(tree.iterative_tree_search(node).bh, bh)
+
+
if __name__ == '__main__':
unittest.main()
diff --git a/tests/binary_search_test.py b/tests/binary_search_test.py
new file mode 100644
index 0000000..999d173
--- /dev/null
+++ b/tests/binary_search_test.py
@@ -0,0 +1,32 @@
+#!/usr/bin/env python
+import unittest
+import random
+from binary_search import binary_search, bisect_left, bisect_right
+
+
+class TestBinarySearch(unittest.TestCase):
+ def test_binary_search(self):
+ for _ in range(100):
+ array = sorted([random.randint(1, 10000) for _ in range(100)])
+ target = random.randint(1, 10000)
+ index = binary_search(target, array)
+ if index == -1:
+ self.assertNotIn(target, array)
+ else:
+ self.assertEqual(target, array[index])
+
+ def test_bisect_left(self):
+ for length in range(10):
+ array = sorted([random.randint(1, 10) for _ in range(length)])
+ target = random.randint(0, 15)
+ index = bisect_left(array, target)
+ self.assertTrue(all(val < target for val in array[:index]))
+ self.assertTrue(all(val >= target for val in array[index:]))
+
+ def test_bisect_right(self):
+ for length in range(10):
+ array = sorted([random.randint(1, 10) for _ in range(length)])
+ target = random.randint(0, 15)
+ index = bisect_right(array, target)
+ self.assertTrue(all(val <= target for val in array[:index]))
+ self.assertTrue(all(val > target for val in array[index:]))
diff --git a/tests/bubble_sort_test.py b/tests/bubble_sort_test.py
new file mode 100644
index 0000000..3fd80be
--- /dev/null
+++ b/tests/bubble_sort_test.py
@@ -0,0 +1,13 @@
+#!/usr/bin/env python
+import unittest
+import random
+from bubble_sort import bubble_sort
+
+
+class TestBubbleSort(unittest.TestCase):
+ def test_bubble_sort(self):
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ bubble_sort(array)
+ self.assertEqual(array, sorted(array_copy))
diff --git a/tests/constraints_test.py b/tests/constraints_test.py
new file mode 100644
index 0000000..8fca7d0
--- /dev/null
+++ b/tests/constraints_test.py
@@ -0,0 +1,74 @@
+from constraints import difference_constraints, equality_constraints, difference_constraints_without_aux_vertex, \
+ single_variable_constraints, difference_constraints_with_arbitrary_weight
+import unittest
+from math import floor
+
+
+class TestConstraints(unittest.TestCase):
+ def test_difference_constraints(self):
+ A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, 0, -1], [-1, 0, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0],
+ [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
+ b = [0, -1, 1, 5, 4, -1, -3, -3]
+ self.assertEqual(difference_constraints(A, b), [-5, -3, 0, -1, -4])
+ A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1],
+ [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
+ b = [1, -4, 2, 7, 5, 10, 2, -1, 3, -8]
+ self.assertEqual(difference_constraints(A, b), [-5, -3, 0, -1, -6, -8])
+ A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, -1, 0], [0, -1, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0],
+ [0, 0, 0, 1, -1], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
+ b = [4, 5, -6, 1, 3, 5, 10, -4, 8]
+ self.assertEqual(difference_constraints(A, b), None)
+ A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1],
+ [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
+ b = [1, -4, 2, 7.3, 5, 10.1, 2.9, -1.11, 3, -8.6]
+ c = [int(floor(i)) for i in b]
+ print(difference_constraints(A, c))
+
+ def test_equality_constraints(self):
+ A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, 0, -1], [-1, 0, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0],
+ [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
+ b = [0, -1, 1, 5, 4, -1, -3, -3]
+ self.assertEqual(equality_constraints(A, b), None)
+ A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1],
+ [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
+ b = [1, -4, 2, 7, 5, 10, 2, -1, 3, -8]
+ self.assertEqual(equality_constraints(A, b), None)
+ A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, -1, 0], [0, -1, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0],
+ [0, 0, 0, 1, -1], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
+ b = [4, 5, -6, 1, 3, 5, 10, -4, 8]
+ self.assertEqual(equality_constraints(A, b), None)
+ A = [[-1, 1, 0], [0, -1, 1], [-1, 0, 1]]
+ b = [1, 1, 2]
+ self.assertEqual(equality_constraints(A, b), [-2, -1, 0])
+
+ def test_difference_constraints_without_aux_vertex(self):
+ A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, 0, -1], [-1, 0, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0],
+ [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
+ b = [0, -1, 1, 5, 4, -1, -3, -3]
+ self.assertEqual(difference_constraints_without_aux_vertex(A, b), [-5, -3, 0, -1, -4])
+ A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1],
+ [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
+ b = [1, -4, 2, 7, 5, 10, 2, -1, 3, -8]
+ self.assertEqual(difference_constraints_without_aux_vertex(A, b), [-5, -3, 0, -1, -6, -8])
+ A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, -1, 0], [0, -1, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0],
+ [0, 0, 0, 1, -1], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
+ b = [4, 5, -6, 1, 3, 5, 10, -4, 8]
+ self.assertEqual(difference_constraints_without_aux_vertex(A, b), None)
+
+ def test_single_variable_constraints(self):
+ A = [[1, 0], [0, 1], [-1, 0], [0, -1], [1, 0]]
+ b = [3, 1, 5, -1, 2]
+ self.assertEqual(single_variable_constraints(A, b), [2, 1])
+ A = [[1, 0], [0, 1], [-1, 0], [0, -1], [1, 0]]
+ b = [3, -1, 5, -1, 2]
+ self.assertEqual(single_variable_constraints(A, b), None)
+# def test_difference_constraints_with_arbitrary_weight(self):
+# A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, 0, -1], [-1, 0, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
+# b = [0, -1, 1, 5, 4, -1, -3, -3]
+# self.assertEqual(difference_constraints_with_arbitrary_weight(A, b), [-5, -3, 0, -1, -4])
+# A = [[1, -1, 0, 0, 0, 0], [1, 0, 0, -1, 0, 0], [0, 1, -1, 0, 0, 0], [0, 1, 0, 0, -1, 0], [0, 1, 0, 0, 0, -1], [0, 0, 1, 0, 0, -1], [0, -1, 0, 1, 0, 0], [-1, 0, 0, 0, 1, 0], [0, 0, 0, -1, 1, 0], [0, 0, -1, 0, 0, 1]]
+# b = [1, -4, 2, 7, 5, 10, 2, -1, 3, -8]
+# self.assertEqual(difference_constraints_with_arbitrary_weight(A, b), [-5, -3, 0, -1, -6, -8])
+# A = [[1, -1, 0, 0, 0], [1, 0, 0, 0, -1], [0, 1, 0, -1, 0], [0, -1, 1, 0, 0], [-1, 0, 0, 1, 0], [0, 0, -1, 1, 0], [0, 0, 0, 1, -1], [0, 0, -1, 0, 1], [0, 0, 0, -1, 1]]
+# b = [4, 5, -6, 1, 3, 5, 10, -4, 8]
+# self.assertEqual(difference_constraints_with_arbitrary_weight(A, b), None)
diff --git a/tests/contains_test.py b/tests/contains_test.py
new file mode 100644
index 0000000..dee5f30
--- /dev/null
+++ b/tests/contains_test.py
@@ -0,0 +1,14 @@
+#!/usr/bin/env python
+
+import unittest
+from contains import contains
+
+
+class TestContains(unittest.TestCase):
+ def test_contains(self):
+ x = [1, 1.5, 3.5, 2.3, 10.01]
+ self.assertEqual(contains(x, 5), {
+ (1, 2), (2.3, 3.3), (3.5, 4.5), (10.01, 11.01)})
+ x = [3.5, 5.2, -1.1, -4, -12, -11.33]
+ self.assertEqual(contains(x, 6), {
+ (-12, -11), (-4, -3), (-1.1, -0.10000000000000009), (3.5, 4.5), (5.2, 6.2)})
diff --git a/counting_sort_test.py b/tests/counting_sort_test.py
similarity index 52%
rename from counting_sort_test.py
rename to tests/counting_sort_test.py
index ace37b9..adfd457 100644
--- a/counting_sort_test.py
+++ b/tests/counting_sort_test.py
@@ -1,12 +1,13 @@
import unittest
from counting_sort import counting_sort
+
class TestHeap(unittest.TestCase):
def test_counting_sort(self):
- A = [2,5,3,0,2,3,0,3]
+ A = [2, 5, 3, 0, 2, 3, 0, 3]
B = []
- for i in range(0, len(A)):
+ for i in range(len(A)):
B.append(0)
counting_sort(A, B, 5)
- self.assertEquals(B, [0,0,2,2,3,3,3,5])
- self.assertEquals(A, [2,5,3,0,2,3,0,3])
+ self.assertEqual(B, [0, 0, 2, 2, 3, 3, 3, 5])
+ self.assertEqual(A, [2, 5, 3, 0, 2, 3, 0, 3])
diff --git a/tests/cut_rod_test.py b/tests/cut_rod_test.py
new file mode 100755
index 0000000..596b93e
--- /dev/null
+++ b/tests/cut_rod_test.py
@@ -0,0 +1,48 @@
+#!/usr/bin/env python
+import unittest
+
+from cut_rod import bottom_up_cut_rod, bottom_up_cut_rod_two_subproblem, memoized_cut_rod, print_cut_rod_solution, \
+ bottom_up_cut_rod_with_fixed_cut_cost, extended_memoized_cut_rod
+
+
+class TestCutRod(unittest.TestCase):
+ def test_bottom_up_cut_rod(self):
+ p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
+ values = [1, 1, 2, 5, 3, 8, 4, 10, 5, 13,
+ 6, 17, 7, 18, 8, 22, 9, 25, 10, 30]
+ for i in range(len(values), 2):
+ self.assertEqual(bottom_up_cut_rod(p, values[i]), values[i + 1])
+
+ def test_bottom_up_cut_rod_two_subproblem(self):
+ p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
+ values = [1, 1, 2, 5, 3, 8, 4, 10, 5, 13,
+ 6, 17, 7, 18, 8, 22, 9, 25, 10, 30]
+ for i in range(len(values), 2):
+ self.assertEqual(bottom_up_cut_rod_two_subproblem(
+ p, values[i]), values[i + 1])
+
+ def test_memoized_cut_rod(self):
+ p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
+ values = [1, 1, 2, 5, 3, 8, 4, 10, 5, 13,
+ 6, 17, 7, 18, 8, 22, 9, 25, 10, 30]
+ for i in range(len(values), 2):
+ self.assertEqual(memoized_cut_rod(p, values[i]), values[i + 1])
+
+ def test_bottom_up_cut_rod_with_fixed_cut_cost(self):
+ p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
+ values = [1, 1, 2, 5, 3, 8, 4, 9, 5, 11,
+ 6, 17, 7, 17, 8, 20, 9, 24, 10, 30]
+ for i in range(len(values), 2):
+ self.assertEqual(bottom_up_cut_rod_with_fixed_cut_cost(
+ p, values[i], 2), values[i + 1])
+ values = [1, 1, 2, 5, 3, 8, 4, 9, 5, 11.5,
+ 6, 17, 7, 17, 8, 20.5, 9, 24, 10, 30]
+ for i in range(len(values), 2):
+ self.assertEqual(bottom_up_cut_rod_with_fixed_cut_cost(
+ p, values[i], 1.5), values[i + 1])
+
+ def test_print_rod_solution(self):
+ p = [1, 5, 8, 9, 10, 17, 17, 20, 24, 30]
+ values = [1, 1, 2, 5, 3, 8, 4, 10, 5, 13,
+ 6, 17, 7, 18, 8, 22, 9, 25, 10, 30]
+ print_cut_rod_solution(p, 9, extended_memoized_cut_rod)
diff --git a/depth_tree_test.py b/tests/depth_tree_test.py
similarity index 95%
rename from depth_tree_test.py
rename to tests/depth_tree_test.py
index c9d6ac2..1e5f13b 100755
--- a/depth_tree_test.py
+++ b/tests/depth_tree_test.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
from depth_tree import depth_tree, depth_node
@@ -7,21 +7,25 @@ class TestRbtree(unittest.TestCase):
def test_insert_one(self):
T = depth_tree([41])
self.wrap(T, 41, 0)
+
def test_insert_two(self):
T = depth_tree([41, 38])
self.wrap(T, 41, 0)
self.wrap(T, 38, 1)
+
def test_insert_three(self):
T = depth_tree([41, 38, 31])
self.wrap(T, 38, 0)
self.wrap(T, 31, 1)
self.wrap(T, 41, 1)
+
def test_insert_four(self):
T = depth_tree([41, 38, 31, 12])
self.wrap(T, 38, 0)
self.wrap(T, 31, 1)
self.wrap(T, 41, 1)
self.wrap(T, 12, 2)
+
def test_insert_five(self):
T = depth_tree([41, 38, 31, 12, 19])
self.wrap(T, 38, 0)
@@ -29,6 +33,7 @@ def test_insert_five(self):
self.wrap(T, 41, 1)
self.wrap(T, 12, 2)
self.wrap(T, 31, 2)
+
def test_insert_six(self):
T = depth_tree([41, 38, 31, 12, 19, 9])
self.wrap(T, 38, 0)
@@ -37,6 +42,7 @@ def test_insert_six(self):
self.wrap(T, 12, 2)
self.wrap(T, 31, 2)
self.wrap(T, 9, 3)
+
def test_delete_one(self):
T = depth_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -45,6 +51,7 @@ def test_delete_one(self):
self.wrap(T, 41, 1)
self.wrap(T, 12, 2)
self.wrap(T, 31, 2)
+
def test_delete_two(self):
T = depth_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -53,6 +60,7 @@ def test_delete_two(self):
self.wrap(T, 19, 1)
self.wrap(T, 41, 1)
self.wrap(T, 31, 2)
+
def test_delete_three(self):
T = depth_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -61,6 +69,7 @@ def test_delete_three(self):
self.wrap(T, 38, 0)
self.wrap(T, 31, 1)
self.wrap(T, 41, 1)
+
def test_delete_four(self):
T = depth_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -69,6 +78,7 @@ def test_delete_four(self):
T.delete(T.iterative_tree_search(31))
self.wrap(T, 38, 0)
self.wrap(T, 41, 1)
+
def test_delete_five(self):
T = depth_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -77,6 +87,7 @@ def test_delete_five(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
self.wrap(T, 41, 0)
+
def test_delete_six(self):
T = depth_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -85,8 +96,11 @@ def test_delete_six(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
T.delete(T.iterative_tree_search(41))
- self.assertEquals(T.nil.depth, -1)
+ self.assertEqual(T.nil.depth, -1)
+
def wrap(self, tree, node, depth):
- self.assertEquals(tree.iterative_tree_search(node).depth, depth)
+ self.assertEqual(tree.iterative_tree_search(node).depth, depth)
+
+
if __name__ == '__main__':
unittest.main()
diff --git a/disjoint_sets_forest_test.py b/tests/disjoint_sets_forest_test.py
similarity index 61%
rename from disjoint_sets_forest_test.py
rename to tests/disjoint_sets_forest_test.py
index 7e1ce6b..5d431ce 100644
--- a/disjoint_sets_forest_test.py
+++ b/tests/disjoint_sets_forest_test.py
@@ -1,41 +1,45 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
import disjoint_sets_forest as ds
+
+
class TestDisjointSets(unittest.TestCase):
def test_forest(self):
pool = [0] * 17
for i in range(1, 17):
pool[i] = ds.node(i)
for i in range(1, 17):
- self.assertEquals(pool[i].p, pool[i])
+ self.assertEqual(pool[i].p, pool[i])
for i in range(1, 16, 2):
pool[i].union(pool[i + 1])
parent_list = [2, 2, 4, 4, 6, 6, 8, 8, 10, 10, 12, 12, 14, 14, 16, 16]
for i in range(1, 17):
- self.assertEquals(pool[i].p, pool[parent_list[i - 1]])
+ self.assertEqual(pool[i].p, pool[parent_list[i - 1]])
for i in range(1, 14, 4):
pool[i].union(pool[i + 2])
parent_list = [2, 4, 4, 4, 6, 8, 8, 8, 10, 12, 12, 12, 14, 16, 16, 16]
for i in range(1, 17):
- self.assertEquals(pool[i].p, pool[parent_list[i - 1]])
+ self.assertEqual(pool[i].p, pool[parent_list[i - 1]])
pool[1].union(pool[5])
parent_list = [4, 4, 4, 8, 8, 8, 8, 8, 10, 12, 12, 12, 14, 16, 16, 16]
for i in range(1, 17):
- self.assertEquals(pool[i].p, pool[parent_list[i - 1]])
+ self.assertEqual(pool[i].p, pool[parent_list[i - 1]])
pool[11].union(pool[13])
parent_list = [4, 4, 4, 8, 8, 8, 8, 8, 10, 12, 12, 16, 16, 16, 16, 16]
for i in range(1, 17):
- self.assertEquals(pool[i].p, pool[parent_list[i - 1]])
+ self.assertEqual(pool[i].p, pool[parent_list[i - 1]])
pool[1].union(pool[10])
parent_list = [8, 4, 4, 8, 8, 8, 8, 16, 10, 16, 12, 16, 16, 16, 16, 16]
for i in range(1, 17):
- self.assertEquals(pool[i].p, pool[parent_list[i - 1]])
+ self.assertEqual(pool[i].p, pool[parent_list[i - 1]])
self.assertTrue(pool[2].find_set() == pool[16])
- parent_list = [8, 16, 4, 16, 8, 8, 8, 16, 10, 16, 12, 16, 16, 16, 16, 16]
+ parent_list = [8, 16, 4, 16, 8, 8, 8,
+ 16, 10, 16, 12, 16, 16, 16, 16, 16]
for i in range(1, 17):
- self.assertEquals(pool[i].p, pool[parent_list[i - 1]])
+ self.assertEqual(pool[i].p, pool[parent_list[i - 1]])
self.assertTrue(pool[9].find_set() == pool[16])
- parent_list = [8, 16, 4, 16, 8, 8, 8, 16, 16, 16, 12, 16, 16, 16, 16, 16]
+ parent_list = [8, 16, 4, 16, 8, 8, 8,
+ 16, 16, 16, 12, 16, 16, 16, 16, 16]
for i in range(1, 17):
- self.assertEquals(pool[i].p, pool[parent_list[i - 1]])
+ self.assertEqual(pool[i].p, pool[parent_list[i - 1]])
diff --git a/disjoint_sets_test.py b/tests/disjoint_sets_test.py
similarity index 90%
rename from disjoint_sets_test.py
rename to tests/disjoint_sets_test.py
index e78f8f4..9fa89ca 100644
--- a/disjoint_sets_test.py
+++ b/tests/disjoint_sets_test.py
@@ -1,15 +1,17 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
import disjoint_sets_linked_list as ds
+
+
class TestDisjointSets(unittest.TestCase):
def test_linked_lists_with_head_and_tail(self):
pool = [0] * 17
for i in range(1, 17):
pool[i] = ds.node(i)
a = ds.header(pool[i])
- self.assertEquals(a.head, pool[i])
- self.assertEquals(a.tail, pool[i])
+ self.assertEqual(a.head, pool[i])
+ self.assertEqual(a.tail, pool[i])
for i in range(1, 16, 2):
pool[i].union(pool[i + 1])
for i in range(1, 14, 4):
@@ -19,6 +21,7 @@ def test_linked_lists_with_head_and_tail(self):
pool[1].union(pool[10])
self.assertTrue(pool[2].find_set() == pool[1])
self.assertTrue(pool[9].find_set() == pool[1])
+
def test_linked_lists_no_tail(self):
pool = [0] * 17
for i in range(1, 17):
diff --git a/tests/graph_test.py b/tests/graph_test.py
new file mode 100644
index 0000000..caedff1
--- /dev/null
+++ b/tests/graph_test.py
@@ -0,0 +1,741 @@
+#!/usr/bin/env python
+import unittest
+from typing import List
+from graph import Vertex, Graph
+
+
+class TestGraph(unittest.TestCase):
+ def setUp(self):
+ self.graphs: List[Graph] = []
+ v1 = Vertex(1)
+ v2 = Vertex(2)
+ v3 = Vertex(3)
+ v4 = Vertex(4)
+ v5 = Vertex(5)
+ v6 = Vertex(6)
+ self.v1 = v1
+ self.v2 = v2
+ self.v3 = v3
+ self.v4 = v4
+ self.v5 = v5
+ self.v6 = v6
+ vertices = [v1, v2, v3, v4, v5, v6]
+ edges = [(v1, v2), (v1, v3), (v2, v3), (v2, v4), (v2, v5), (v3, v4),
+ (v3, v6), (v4, v5), (v5, v6)]
+ self.graphs.append(Graph(vertices, edges))
+ edges = [(v1, v2), (v2, v3), (v3, v4), (v4, v2), (v3, v5), (v2, v4),
+ (v4, v3), (v1, v6)]
+ self.graphs.append(Graph([v1, v2, v3, v4, v5, v6], edges))
+
+ def tearDown(self):
+ pass
+
+ @staticmethod
+ def _build_graph(cls, keys, pairs, directed):
+ d = dict()
+ vertices = [None] * len(keys)
+ edges = [None] * len(pairs)
+ for i in range(len(vertices)):
+ vertices[i] = Vertex(keys[i])
+ d[keys[i]] = vertices[i]
+
+ for i in range(len(edges)):
+ w1, w2 = pairs[i]
+ edges[i] = (d[w1], d[w2])
+ return Graph(vertices, edges, directed)
+
+ def testBfs(self):
+ s = Vertex('s')
+ r = Vertex('r')
+ v = Vertex('v')
+ w = Vertex('w')
+ t = Vertex('t')
+ x = Vertex('x')
+ u = Vertex('u')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [v, r, s, w, t, x, u, y, z]
+ edges = [(s, r), (s, w), (r, v), (r, s), (v, r), (w, s), (w, t),
+ (w, x), (t, w), (t, x), (t, u), (u, t), (u, x),
+ (u, y), (x, w), (x, t), (x, u), (x, y), (y, x), (y, u)]
+ g = Graph(vertices, edges)
+ # g.print(AllEdges())
+ # for i in g.vertices:
+ # i.print(Edge())
+ # print()
+ g.bfs(s)
+ # g.print(Vertices())
+ self.assertEqual(s.distance, 0)
+ self.assertEqual(r.distance, 1)
+ self.assertEqual(v.distance, 2)
+ self.assertEqual(w.distance, 1)
+ self.assertEqual(t.distance, 2)
+ self.assertEqual(x.distance, 2)
+ self.assertEqual(u.distance, 3)
+ self.assertEqual(y.distance, 3)
+
+ # def testDfs(self):
+ # s = Vertex('s')
+ # v = Vertex('v')
+ # z = Vertex('z')
+ # w = Vertex('w')
+ # y = Vertex('y')
+ # x = Vertex('x')
+ # t = Vertex('t')
+ # u = Vertex('u')
+ # # edges_list = [(z, w), (s, w), (y, w),
+ # # (x, ), (x, ), (z, ), (v, u), (v, t)]
+ # # vertices = (s, v, z, w, y, x, t, u)
+ # # map(
+ # # lambda vertex, edges:
+ # # map(lambda vertex, edge:
+ # # vertex.addEdge(edge),
+ # # zip([vertex] * len(edges) , edges)),
+ # # zip(vertices, edges_list))
+ # vertices = [s, v, z, w, y, x, t, u]
+ # edges = [(y, x), (x, z), (z, y), (z, w), (w, x), (s, z),
+ # (s, w), (v, w), (v, s), (t, v), (t, u), (u, v), (u, t)]
+ # g = Graph(vertices, edges)
+ # g.dfs()
+ # # vertices = (s, v, z, w, y, x, t, u)
+
+ def testIsCyclic(self):
+ s = Vertex('s')
+ v = Vertex('v')
+ z = Vertex('z')
+ vertices = [s, v, z]
+ self.assertFalse(Graph(vertices, [(s, v), (v, z)]).is_cyclic())
+ self.assertTrue(Graph(vertices, [(s, v), (v, z), (z, s)]).is_cyclic())
+
+ def testPathNum(self):
+ m = Vertex('m')
+ n = Vertex('n')
+ o = Vertex('o')
+ p = Vertex('p')
+ q = Vertex('q')
+ r = Vertex('r')
+ s = Vertex('s')
+ t = Vertex('t')
+ u = Vertex('u')
+ v = Vertex('v')
+ w = Vertex('w')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [m, n, o, p, q, r, s, t, u, v, w, x, y, z]
+ edges = [(m, q), (m, r), (m, x), (n, q), (n, o), (n, u),
+ (o, r), (o, s), (o, v), (p, o), (p, s), (p, z), (q, t),
+ (r, u), (r, y), (s, r), (u, t), (v, w),
+ (v, x), (w, z), (y, v)]
+ g = Graph(vertices, edges)
+ self.assertEqual(g.path_num(m, v), 1)
+ self.assertEqual(g.path_num(n, v), 3)
+ self.assertEqual(g.path_num(o, v), 3)
+ self.assertEqual(g.path_num(p, v), 4)
+ self.assertEqual(g.path_num(q, v), 0)
+ self.assertEqual(g.path_num(r, v), 1)
+ self.assertEqual(g.path_num(s, v), 1)
+ self.assertEqual(g.path_num(t, v), 0)
+ self.assertEqual(g.path_num(u, v), 0)
+ self.assertEqual(g.path_num(v, v), 1)
+ self.assertEqual(g.path_num(w, v), 0)
+ self.assertEqual(g.path_num(x, v), 0)
+ self.assertEqual(g.path_num(y, v), 1)
+ self.assertEqual(g.path_num(z, v), 0)
+
+ g = self.graphs[0]
+ self.assertEqual(g.path_num(self.v1, self.v2), 1)
+ self.assertEqual(g.path_num(self.v1, self.v3), 2)
+ self.assertEqual(g.path_num(self.v1, self.v4), 3)
+ self.assertEqual(g.path_num(self.v1, self.v5), 4)
+ self.assertEqual(g.path_num(self.v1, self.v6), 6)
+ self.assertEqual(g.path_num(self.v2, self.v1), 0)
+ self.assertEqual(g.path_num(self.v2, self.v3), 1)
+ self.assertEqual(g.path_num(self.v2, self.v4), 2)
+ self.assertEqual(g.path_num(self.v2, self.v5), 3)
+ self.assertEqual(g.path_num(self.v2, self.v6), 4)
+ g = self.graphs[1]
+ self.assertEqual(g.path_num(self.v1, self.v5), 1)
+
+ def testSCC(self):
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ g = Vertex('g')
+ h = Vertex('h')
+ vertices = [a, b, c, d, e, f, g, h]
+ edges = [(e, a), (a, b), (b, c), (d, c), (c, d), (b, e),
+ (e, f), (b, f), (g, f), (f, g), (c, g), (g, h), (h, h)]
+ G = Graph(vertices, edges)
+ G.strongly_connected_components()
+ self.assertEqual(a.cc, 1)
+ self.assertEqual(b.cc, 1)
+ self.assertEqual(c.cc, 2)
+ self.assertEqual(d.cc, 2)
+ self.assertEqual(e.cc, 1)
+ self.assertEqual(f.cc, 3)
+ self.assertEqual(g.cc, 3)
+ self.assertEqual(h.cc, 4)
+
+ def testSimplified(self):
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ g = Vertex('g')
+ h = Vertex('h')
+ vertices = [a, b, c, d, e, f, g, h]
+ # edges = [(a, c), (b, a), (d, h), (d, f), (e, a), (a, b), (b, c),
+ # (d, c), (c, d), (b, e), (e, f), (b, f), (g, f), (f, g), (c, g),
+ # (g, h), (h, h)]
+ edges = [(e, a), (a, b), (b, c), (d, c), (c, d), (b, e),
+ (e, f), (b, f), (g, f), (f, g), (c, g), (g, h), (h, h)]
+ G = Graph(vertices, edges)
+ s = G.simplified()
+ # for u in s.vertices:
+ # print( "u.key: {}, u.cc: {}".format(u.key, u.cc) )
+ # s.print(Edge(u))
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ vertices = [a, b, c, d, e, f]
+ edges = [(a, b), (b, a), (b, c), (b, d), (c, b), (d, b),
+ (c, e), (b, e), (d, f), (e, f), (f, e)]
+ G = Graph(vertices, edges)
+ s = G.simplified()
+ # for u in s.vertices:
+ # print( "u.key: {}, u.cc: {}".format(u.key, u.cc) )
+ # s.print(Edge(u))
+
+ def testComponentGraph(self):
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ g = Vertex('g')
+ h = Vertex('h')
+ vertices = [a, b, c, d, e, f, g, h]
+ edges = [(e, a), (a, b), (b, c), (d, c), (c, d), (d, h), (b, e),
+ (e, f), (b, f), (g, f), (f, g), (c, g), (g, h), (h, h)]
+ G = Graph(vertices, edges)
+ cg = G.component_graph()
+ # print()
+ # for u in cg.vertices:
+ # print( "u.key: {}".format(u.key) )
+ # cg.print(Edge(u))
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ vertices = [a, b, c, d, e, f]
+ edges = [(a, b), (b, a), (b, c), (b, d), (c, b), (d, b),
+ (c, e), (b, e), (d, f), (e, f), (f, e)]
+ G = Graph(vertices, edges)
+ cg = G.component_graph()
+
+ # print( "www")
+ # print()
+ # for u in cg.vertices:
+ # print( "u.key: {}".format(u.key) )
+ # cg.print(Edge(u))
+ def testSemiconnected(self):
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ g = Vertex('g')
+ h = Vertex('h')
+ vertices = [a, b, c, d, e, f, g, h]
+ edges = [(e, a), (a, b), (b, c), (d, c), (c, d), (d, h), (b, e),
+ (e, f), (b, f), (g, f), (f, g), (c, g), (g, h),
+ (h, h)]
+ G = Graph(vertices, edges)
+ self.assertEqual(G.semiconnected(), True)
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ vertices = [a, b, c, d, e, f]
+ edges = [(a, b), (b, a), (b, c), (b, d), (c, b), (d, b),
+ (c, e), (b, e), (d, f), (e, f), (f, e)]
+ G = Graph(vertices, edges)
+ self.assertEqual(G.semiconnected(), True)
+ edges = [(a, b), (b, a), (b, c), (b, d), (c, b), (d, b), (e, f)]
+ G = Graph(vertices, edges)
+ self.assertEqual(G.semiconnected(), False)
+ abe = Vertex('abe')
+ cd = Vertex('cd')
+ fg = Vertex('fg')
+ h = Vertex('h')
+ vertices = [abe, cd, fg, h]
+ edges = [(abe, fg), (abe, cd), (fg, h), (cd, h), (cd, fg)]
+ G = Graph(vertices, edges)
+ self.assertEqual(G.semiconnected(), True)
+ edges = [(abe, fg), (abe, cd), (fg, h), (cd, h)]
+ G = Graph(vertices, edges)
+ self.assertEqual(G.semiconnected(), False)
+ edges = [(abe, fg), (abe, cd), (cd, h), (cd, fg)]
+ G = Graph(vertices, edges)
+ self.assertEqual(G.semiconnected(), False)
+ edges = [(abe, fg), (abe, cd), (fg, h), (cd, fg)]
+ G = Graph(vertices, edges)
+ self.assertEqual(G.semiconnected(), True)
+ edges = [(abe, cd), (fg, h), (cd, fg)]
+ G = Graph(vertices, edges)
+ self.assertEqual(G.semiconnected(), True)
+
+ def testCut(self):
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ g = Vertex('g')
+ h = Vertex('h')
+ i = Vertex('i')
+ vertices = [a, b, c, d, e, f, g, h, i]
+ edges = [(a, b), (b, c), (b, h), (c, i), (d, c), (e, d), (f, d),
+ (f, e), (f, c), (g, f), (g, h), (g, i), (h, a), (h, i)]
+ G = Graph(vertices, edges, directed=False)
+ # weight = [4, 8, 11, 2, 7, 9, 14, 10, 4, 2, 2, 1, 8, 7]
+ weight = [4, 8, 11, 2, 7, 9, 14, 10, 4, 2, 1, 6, 8, 7]
+ z = dict()
+ for x, y in zip(edges, weight):
+ z[x] = y
+ z[(x[1], x[0])] = y
+
+ def w(x, y):
+ return z[(x, y)]
+
+ G.cut(a, h, w)
+ r1 = set()
+ r2 = set()
+ for u in G.vertices:
+ if u.root == a:
+ r1.add(u)
+ else:
+ r2.add(u)
+ self.assertEqual(r1, set([a, b]))
+ self.assertEqual(r2, set([h, i, g, c, f, d, e]))
+
+ # for u in G.vertices:
+ # print( "u.key: {}, u.root = {}".format(u.key, u.root))
+ def testKruskal(self):
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ g = Vertex('g')
+ h = Vertex('h')
+ i = Vertex('i')
+ vertices = [a, b, c, d, e, f, g, h, i]
+ edges = [(a, b), (a, h), (b, a), (b, c), (b, h), (c, b), (c, i),
+ (c, f), (c, d), (d, c), (d, e), (d, f), (e, d),
+ (e, f), (f, d), (f, e), (f, c), (f, g), (g, f), (g, h),
+ (g, i), (h, a), (h, b), (h, i), (h, g), (i, c),
+ (i, h), (i, g)]
+ G = Graph(vertices, edges)
+ weight = [4, 8, 4, 8, 11, 8, 2, 4, 7, 7, 9, 14, 9,
+ 10, 14, 10, 4, 2, 2, 1, 6, 8, 11, 7, 1, 2, 7, 6]
+ z = dict()
+ for x, y in zip(edges, weight):
+ z[x] = y
+ print("{}: {}".format(x, y))
+
+ def w(x, y):
+ return z[(x, y)]
+
+ ls = G.Kruskal(w)
+ print(ls)
+
+ def testPrim(self):
+ a = Vertex('a')
+ b = Vertex('b')
+ c = Vertex('c')
+ d = Vertex('d')
+ e = Vertex('e')
+ f = Vertex('f')
+ g = Vertex('g')
+ h = Vertex('h')
+ i = Vertex('i')
+ vertices = [a, b, c, d, e, f, g, h, i]
+ # edges = [(a, b), (a, h), (b, a), (b, c), (b, h), (c, b), (c, i),
+ # (c, f), (c, d), (d, c), (d, e), (d, f), (e, d), (e, f), (f, d),
+ # (f, e), (f, c), (f, g), (g, f), (g, h), (g, i), (h, a), (h, b),
+ # (h, i), (h, g), (i, c), (i, h), (i, g)]
+ # weight = [4, 8, 4, 8, 11, 8, 2, 4, 7, 7, 9, 14, 9, 10, 14, 10, 4, 2,
+ # 2, 1, 6, 8, 11, 7, 1, 2, 7, 6]
+ edges = [(a, b), (b, c), (b, h), (c, i), (d, c), (e, d), (f, d),
+ (f, e), (f, c), (g, f), (g, h), (g, i), (h, a), (h, i)]
+ weight = [4, 8, 11, 2, 7, 9, 14, 10, 4, 2, 1, 6, 8, 7]
+ G = Graph(vertices, edges, False)
+ z = dict()
+ for x, y in zip(edges, weight):
+ z[x] = y
+ z[(x[1], x[0])] = y
+ # print( "Prim edges: {}, weight: {}".format(x, y))
+
+ def w(x, y):
+ return z[(x, y)]
+
+ G.Prim(w, i)
+ s = set()
+ for u in G.vertices:
+ s.add((u.p, u))
+ # self.assertEqual(s, set([(g, h), (f, g), (None, i), (c, d),
+ # (c, f), (i, c), (h, a), (d, e), (a, b)]))
+
+ def testBellmanFord(self):
+ s = Vertex('s')
+ t = Vertex('t')
+ y = Vertex('y')
+ x = Vertex('x')
+ z = Vertex('z')
+ vertices = [s, t, y, x, z]
+ edges = [(s, t), (s, y), (t, y), (t, x), (t, z),
+ (y, x), (y, z), (x, t), (z, s), (z, x)]
+ weight = [6, 7, 8, 5, -4, -3, 9, -2, 2, 7]
+ G = Graph(vertices, edges)
+ we = dict()
+ for x, y in zip(edges, weight):
+ we[x] = y
+
+ def w(x, y):
+ return we[(x, y)]
+
+ G.Bellman_Ford(w, z)
+
+ def testBellmanFordModified(self):
+ s = Vertex('s')
+ t = Vertex('t')
+ u = Vertex('u')
+ v = Vertex('v')
+ x = Vertex('x')
+ y = Vertex('y')
+ vertices = [s, t, u, v, x, y]
+ edges = [(s, t), (s, v), (s, x), (s, y), (t, u), (v, u)]
+ weight = [1, 0, 3, 4, 2, 6]
+ G = Graph(vertices, edges)
+ we = dict()
+ for i, j in zip(edges, weight):
+ we[i] = j
+
+ def w(x, y):
+ return we[(x, y)]
+
+ # G.Bellman_Ford(w, s)
+ G.Bellman_Ford_modified(w, s)
+ self.assertEqual([i.p for i in vertices], [None, s, t, s, s, s])
+ self.assertEqual([i.d for i in vertices], [0, 1, 3, 0, 3, 4])
+ r = Vertex('r')
+ s = Vertex('s')
+ t = Vertex('t')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [r, s, t, x, y, z]
+ edges = [(r, s), (r, t), (s, t), (s, x), (t, x),
+ (t, y), (t, z), (x, y), (x, z), (y, z)]
+ weight = [5, 3, 2, 6, 7, 4, 2, -1, 1, -2]
+ G = Graph(vertices, edges)
+ we = dict()
+ for i, j in zip(edges, weight):
+ we[i] = j
+
+ def w(x, y):
+ return we[(x, y)]
+
+ G.Bellman_Ford_modified(w, s)
+ self.assertEqual([i.p for i in vertices], [None, None, s, s, x, y])
+ self.assertEqual([i.d for i in vertices], [
+ float("Inf"), 0, 2, 6, 5, 3])
+
+ def testTopologicalSort(self):
+ r = Vertex('r')
+ s = Vertex('s')
+ t = Vertex('t')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [r, s, t, x, y, z]
+ edges = [(r, s), (r, t), (s, t), (s, x), (t, x),
+ (t, y), (t, z), (x, y), (x, z), (y, z)]
+ graph = Graph(vertices, edges)
+ # Prove that Graph.topological_sort actually does a topological sort.
+ # A topological sort of a dag(directed acyclic graph) G = (V, E) is a linear ordering of all the vertices
+ # such that if G contains an edge (u, v), then u appears before v in the ordering.
+ mapping = {vertex: index for index, vertex in enumerate(graph.topological_sort())}
+ self.assertTrue(all(mapping[u] < mapping[v] for u, v in graph.edges))
+
+ def testDagShortestPaths(self):
+ r = Vertex('r')
+ s = Vertex('s')
+ t = Vertex('t')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [r, s, t, x, y, z]
+ edges = [(r, s), (r, t), (s, t), (s, x), (t, x),
+ (t, y), (t, z), (x, y), (x, z), (y, z)]
+ weight = [5, 3, 2, 6, 7, 4, 2, -1, 1, -2]
+ G = Graph(vertices, edges)
+ we = dict()
+ for i, j in zip(edges, weight):
+ we[i] = j
+
+ def w(x, y):
+ return we[(x, y)]
+
+ G.dag_shortest_paths(w, s)
+ self.assertEqual([i.p for i in vertices], [None, None, s, s, x, y])
+ self.assertEqual([i.d for i in vertices], [
+ float("Inf"), 0, 2, 6, 5, 3])
+ G.dag_shortest_paths(w, r)
+ self.assertEqual([i.p for i in vertices], [None, r, r, t, t, t])
+ self.assertEqual([i.d for i in vertices], [0, 5, 3, 10, 7, 5])
+
+ def testDagShortestPathsModified(self):
+ u = Vertex('u')
+ v = Vertex('v')
+ w = Vertex('w')
+ z = Vertex('z')
+ u.weight = 1
+ v.weight = 2
+ w.weight = 3
+ z.weight = 4
+ vertices = [u, v, w, z]
+ edges = [(u, v), (v, w), (v, z)]
+ G = Graph(vertices, edges)
+ self.assertEqual(G.dag_shortest_paths_modified(u), [u, v, z])
+
+ def testTotalPathNumber(self):
+ r = Vertex('r')
+ s = Vertex('s')
+ t = Vertex('t')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [r, s, t, x, y, z]
+ edges = [(r, s), (r, t), (s, t), (s, x), (t, x),
+ (t, y), (t, z), (x, y), (x, z), (y, z)]
+ weight = [5, 3, 2, 6, 7, 4, 2, -1, 1, -2]
+ G = Graph(vertices, edges)
+ number = G.total_path_number()
+ self.assertEqual([i.num for i in vertices], [21, 12, 7, 3, 1, 0])
+ self.assertEqual(number, 44)
+
+ def testDijkstra(self):
+ s = Vertex('s')
+ t = Vertex('t')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [s, t, x, y, z]
+ edges = [(s, t), (s, y), (t, x), (t, y), (x, z),
+ (y, t), (y, x), (y, z), (z, s), (z, x)]
+ g = Graph(vertices, edges)
+ weight = [10, 5, 1, 2, 4, 3, 9, 2, 7, 6]
+ we = dict()
+ for i, j in zip(edges, weight):
+ we[i] = j
+
+ def w(x, y):
+ return we[(x, y)]
+
+ g.Dijkstra(w, s)
+ self.assertEqual([i.p for i in vertices], [None, y, t, s, y])
+ self.assertEqual([i.d for i in vertices], [0, 8, 9, 5, 7])
+ s = Vertex('s')
+ t = Vertex('t')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [s, t, x, y, z]
+ edges = [(s, t), (s, y), (t, x), (t, y), (x, z),
+ (y, t), (y, x), (y, z), (z, s), (z, x)]
+ g = Graph(vertices, edges)
+ weight = [3, 5, 6, 2, 2, 1, 4, 6, 3, 7]
+ we = dict()
+ for i, j in zip(edges, weight):
+ we[i] = j
+
+ def w(x, y):
+ return we[(x, y)]
+
+ g.Dijkstra(w, s)
+ self.assertEqual([i.p for i in vertices], [None, s, t, s, y])
+ self.assertEqual([i.d for i in vertices], [0, 3, 9, 5, 11])
+ g.Dijkstra(w, z)
+ self.assertEqual([i.p for i in vertices], [z, s, z, s, None])
+ self.assertEqual([i.d for i in vertices], [3, 6, 7, 8, 0])
+
+ def testDijkstraModified(self):
+ s = Vertex('s')
+ t = Vertex('t')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [s, t, x, y, z]
+ edges = [(s, t), (s, y), (t, x), (t, y), (x, z),
+ (y, t), (y, x), (y, z), (z, s), (z, x)]
+ g = Graph(vertices, edges)
+ weight = [10, 5, 1, 2, 4, 3, 9, 2, 7, 6]
+ we = dict()
+ for i, j in zip(edges, weight):
+ we[i] = j
+
+ def w(x, y):
+ return we[(x, y)]
+
+ g.Dijkstra_modified(w, s, 10)
+ self.assertEqual([i.p for i in vertices], [None, y, t, s, y])
+ self.assertEqual([i.d for i in vertices], [0, 8, 9, 5, 7])
+ s = Vertex('s')
+ t = Vertex('t')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
+ vertices = [s, t, x, y, z]
+ edges = [(s, t), (s, y), (t, x), (t, y), (x, z),
+ (y, t), (y, x), (y, z), (z, s), (z, x)]
+ g = Graph(vertices, edges)
+ weight = [3, 5, 6, 2, 2, 1, 4, 6, 3, 7]
+ we = dict()
+ for i, j in zip(edges, weight):
+ we[i] = j
+
+ def w(x, y):
+ return we[(x, y)]
+
+ g.Dijkstra_modified(w, s, 7)
+ self.assertEqual([i.p for i in vertices], [None, s, t, s, y])
+ self.assertEqual([i.d for i in vertices], [0, 3, 9, 5, 11])
+ g.Dijkstra_modified(w, z, 7)
+ self.assertEqual([i.p for i in vertices], [z, s, z, s, None])
+ self.assertEqual([i.d for i in vertices], [3, 6, 7, 8, 0])
+
+ def testSingleEdge(self):
+ a = Vertex(1)
+ b = Vertex(2)
+ c = Vertex(3)
+ d = Vertex(4)
+ vertices = [a, b, c, d]
+ edges = [(a, b), (b, a), (a, c), (d, d)]
+ graph1 = Graph(vertices, edges)
+ graph2 = graph1.single_edge()
+ edges = {(a, b), (b, a), (a, c), (c, a)}
+ vertices = set(vertices)
+ self.assertEqual(graph2.vertices, vertices)
+ self.assertEqual(graph2.edges, edges)
+ self.assertEqual(graph2.adj[a], {b, c})
+ self.assertEqual(graph2.adj[b], {a})
+ self.assertEqual(graph2.adj[c], {a})
+ self.assertEqual(graph2.adj[d], set())
+
+ def testUnion(self):
+ a = Vertex(1)
+ b = Vertex(2)
+ c = Vertex(3)
+ d = Vertex(4)
+ G1 = Graph([a, b, c], [(a, b), (a, c)])
+ G2 = Graph([c, d], [(c, d)])
+ G3 = G1.union(G2)
+ self.assertEqual(G3.vertices, {a, b, c, d})
+ self.assertEqual(G3.edges, {(a, b), (a, c), (c, d)})
+ self.assertEqual(G3.adj[a], {b, c})
+ self.assertEqual(G3.adj[b], set())
+ self.assertEqual(G3.adj[c], {d})
+ self.assertEqual(G3.adj[d], set())
+ G1 = Graph([a, b, c], [(a, b), (a, c)], directed=False)
+ G2 = Graph([c, d], [(c, d)], directed=False)
+ G3 = G1.union(G2)
+ self.assertEqual(G3.vertices, {a, b, c, d})
+ self.assertEqual(
+ G3.edges, {(a, b), (b, a), (a, c), (c, a), (c, d), (d, c)})
+ self.assertEqual(G3.adj[a], {b, c})
+ self.assertEqual(G3.adj[b], {a})
+ self.assertEqual(G3.adj[c], {d, a})
+ self.assertEqual(G3.adj[d], {c})
+
+ def testCopy(self):
+ a = Vertex(1)
+ b = Vertex(2)
+ c = Vertex(3)
+ G1 = Graph([a, b, c], [(a, b), (a, c)])
+ G2 = G1.copy()
+ self.assertEqual(G1, G2)
+
+ def testSquareGraph(self):
+ a = Vertex(1)
+ b = Vertex(2)
+ c = Vertex(3)
+ d = Vertex(4)
+ G = Graph([a, b, c, d], [(a, b), (a, c), (c, d)])
+ sqrt = G.square()
+ self.assertEqual(sqrt.vertices, {a, b, c, d})
+ self.assertEqual(sqrt.edges, {(a, b), (a, c), (a, d), (c, d)})
+ self.assertEqual(sqrt.adj[a], {b, c, d})
+ self.assertEqual(sqrt.adj[b], set())
+ self.assertEqual(sqrt.adj[c], {d})
+ self.assertEqual(sqrt.adj[d], set())
+ a = Vertex(1)
+ b = Vertex(2)
+ c = Vertex(3)
+ G = Graph([a, b, c], [(a, b), (b, c), (a, c)])
+ sqrt = G.square()
+ self.assertEqual(G, sqrt)
+
+ def testMht(self):
+ print("start mht")
+ g = self.graphs[0]
+ g.mht()
+ print("height")
+ print(self.v1.h)
+ print(self.v2.h)
+ print(self.v3.h)
+ print(self.v4.h)
+ print(self.v5.h)
+ print(self.v6.h)
+ print("height")
+ print(self.v1.mh)
+ print(self.v2.mh)
+ print(self.v3.mh)
+ print(self.v4.mh)
+ print(self.v5.mh)
+ print(self.v6.mh)
+# def testJohnson(self):
+# a1 = Vertex(1)
+# a2 = Vertex(2)
+# a3 = Vertex(3)
+# a4 = Vertex(4)
+# a5 = Vertex(5)
+# vertices = [a1, a2, a3, a4, a5]
+# edges = [(a1, a2), (a1, a3), (a1, a5), (a2, a4), (a2, a5), (a3, a2),
+# (a4, a1), (a4, a3), (a5, a4)]
+# g = Graph(vertices, edges)
+# weight = [3, 8, -4, 1, 7, 4, 2, -5, 6]
+# we = dict()
+# for i,j in zip(edges, weight):
+# we[i] = j
+# def w(x, y):
+# return we[(x, y)]
+# g.Johnson(w)
diff --git a/hamiltonian_path_test.py b/tests/hamiltonian_path_test.py
similarity index 50%
rename from hamiltonian_path_test.py
rename to tests/hamiltonian_path_test.py
index 3dd2c32..ab7eb9d 100644
--- a/hamiltonian_path_test.py
+++ b/tests/hamiltonian_path_test.py
@@ -1,32 +1,33 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
from graph import Vertex, Graph
from hamiltonian_path import hamiltonian_path
+
class TestHamiltonianPath(unittest.TestCase):
def testHamPath(self):
- r = Vertex('r')
- s = Vertex('s')
- t = Vertex('t')
- x = Vertex('x')
- y = Vertex('y')
- z = Vertex('z')
+ r = Vertex('r')
+ s = Vertex('s')
+ t = Vertex('t')
+ x = Vertex('x')
+ y = Vertex('y')
+ z = Vertex('z')
vertices = [r, s, t, x, y, z]
edges = [(r, s), (s, t), (t, x), (x, y), (y, z)]
G = Graph(vertices, edges)
- self.assertEquals([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, False, False, True])
+ self.assertEqual([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, False, False, True])
edges = [(r, s), (r, t), (s, x), (s, y), (t, z)]
G = Graph(vertices, edges)
- self.assertEquals([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, False, False, False])
+ self.assertEqual([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, False, False, False])
edges = [(r, s), (s, t), (s, x), (t, x)]
vertices = [r, s, t, x]
G = Graph(vertices, edges)
- self.assertEquals([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, True])
+ self.assertEqual([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, True])
edges = [(r, s), (s, t), (s, x), (t, x), (r, y), (y, s)]
vertices = [r, s, t, x, y]
G = Graph(vertices, edges)
- self.assertEquals([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, True, False])
+ self.assertEqual([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, True, False])
edges = [(r, s), (s, t), (s, x), (t, x), (r, y)]
vertices = [r, s, t, x, y]
G = Graph(vertices, edges)
- self.assertEquals([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, False, False])
+ self.assertEqual([hamiltonian_path(G, r, v) for v in vertices], [False, False, False, False, False])
diff --git a/tests/heap_test.py b/tests/heap_test.py
new file mode 100644
index 0000000..9bf8d74
--- /dev/null
+++ b/tests/heap_test.py
@@ -0,0 +1,39 @@
+import unittest
+from heap import MaxHeap, MinHeap
+
+
+class TestHeap(unittest.TestCase):
+ # def test_init(self):
+ # a = heap([4, 1, 3, 2, 16, 9, 10, 14, 8, 7])
+ # self.assertEqual(a.__heap, a)
+ # self.assertEqual(a.__length, 10)
+ # self.assertEqual(a.__heap_size, 10)
+ def test_max_heapify(self):
+ a = [16, 4, 10, 14, 7, 9, 3, 2, 8, 1]
+ h = MaxHeap(a)
+ h.max_heapify(1)
+ self.assertEqual(h, [16, 14, 10, 8, 7, 9, 3, 2, 4, 1])
+
+ def test_build_max_heap(self):
+ a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
+ h = MaxHeap(a)
+ h.build_max_heap()
+ self.assertEqual(h, [16, 14, 10, 8, 7, 9, 3, 2, 4, 1])
+
+ def test_heapsort(self):
+ a = [4, 1, 3, 3, 16, 9, 10, 14, 8, 7]
+ h = MaxHeap(a)
+ h.heapsort()
+ self.assertEqual(h, [1, 3, 3, 4, 7, 8, 9, 10, 14, 16])
+
+ def test_min_heapify(self):
+ a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
+ h = MinHeap(a)
+ h.min_heapify(1)
+ self.assertEqual(h, [1, 2, 3, 4, 7, 8, 9, 10, 14, 16])
+
+ def test_build_min_heap(self):
+ a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
+ h = MinHeap(a)
+ h.build_min_heap()
+ self.assertEqual(h, [1, 2, 3, 4, 7, 8, 9, 10, 14, 16])
diff --git a/tests/insertion_sort_test.py b/tests/insertion_sort_test.py
new file mode 100644
index 0000000..1b84092
--- /dev/null
+++ b/tests/insertion_sort_test.py
@@ -0,0 +1,34 @@
+#!/usr/bin/env python
+import unittest
+import random
+from insertion_sort import insertion_sort, insertion_sort_recursive, insert_with_linear_search, \
+ insert_with_binary_search
+
+
+class TestInsertionSort(unittest.TestCase):
+ def test_insertion_sort_with_linear_search(self):
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ insertion_sort(array, insert_method=insert_with_linear_search)
+ self.assertEqual(array, sorted(array_copy))
+
+ def test_insertion_sort_with_binary_search(self):
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ insertion_sort(array, insert_method=insert_with_binary_search)
+ self.assertEqual(array, sorted(array_copy))
+
+ def test_insertion_sort_recursive(self):
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ insertion_sort_recursive(array)
+ self.assertEqual(array, sorted(array_copy))
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ insertion_sort_recursive(
+ array, insert_method=insert_with_binary_search)
+ self.assertEqual(array, sorted(array_copy))
diff --git a/interval_tree_test.py b/tests/interval_tree_test.py
similarity index 88%
rename from interval_tree_test.py
rename to tests/interval_tree_test.py
index e5b8be0..b5dc140 100755
--- a/interval_tree_test.py
+++ b/tests/interval_tree_test.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
from interval_tree import interval, interval_tree, interval_node
@@ -6,11 +6,13 @@
class TestIntervalTree(unittest.TestCase):
def test_insert_one(self):
intervals = []
- values = [16, 21, 8, 9, 25, 30, 5, 8, 15, 23, 17, 19, 26, 26, 0, 3, 6, 10, 19, 20]
+ values = [16, 21, 8, 9, 25, 30, 5, 8, 15,
+ 23, 17, 19, 26, 26, 0, 3, 6, 10, 19, 20]
for i in range(0, len(values), 2):
intervals.append(interval(values[i], values[i + 1]))
T = interval_tree(intervals)
- values = [16, 30, 8, 23, 25, 30, 5, 10, 15, 23, 17, 20, 26, 26, 0, 3, 6, 10, 19, 20]
+ values = [16, 30, 8, 23, 25, 30, 5, 10, 15,
+ 23, 17, 20, 26, 26, 0, 3, 6, 10, 19, 20]
for i in range(0, len(values), 2):
self.wrap(T, values[i], values[i + 1])
values = [41, 41, 38, 42, 31, 35, 12, 45, 19, 23, 9, 21]
@@ -21,6 +23,7 @@ def test_insert_one(self):
values = [38, 45, 19, 45, 41, 41, 12, 45, 31, 35, 9, 21]
for i in range(0, len(values), 2):
self.wrap(T, values[i], values[i + 1])
+
def test_delete_one(self):
intervals = []
values = [41, 41, 38, 42, 31, 35, 12, 45, 19, 23, 9, 21]
@@ -31,6 +34,7 @@ def test_delete_one(self):
values = [38, 45, 19, 45, 41, 41, 12, 45, 31, 35]
for i in range(0, len(values), 2):
self.wrap(T, values[i], values[i + 1])
+
def test_delete_two(self):
intervals = []
values = [41, 41, 38, 42, 31, 35, 12, 45, 19, 23, 9, 21]
@@ -42,6 +46,7 @@ def test_delete_two(self):
values = [38, 42, 19, 35, 41, 41, 31, 35]
for i in range(0, len(values), 2):
self.wrap(T, values[i], values[i + 1])
+
def test_delete_three(self):
intervals = []
values = [41, 41, 38, 42, 31, 35, 12, 45, 19, 23, 9, 21]
@@ -54,6 +59,7 @@ def test_delete_three(self):
values = [38, 42, 31, 35, 41, 41]
for i in range(0, len(values), 2):
self.wrap(T, values[i], values[i + 1])
+
def test_delete_four(self):
intervals = []
values = [41, 41, 38, 42, 31, 35, 12, 45, 19, 23, 9, 21]
@@ -67,6 +73,7 @@ def test_delete_four(self):
values = [38, 42, 41, 41]
for i in range(0, len(values), 2):
self.wrap(T, values[i], values[i + 1])
+
def test_delete_five(self):
intervals = []
values = [41, 41, 38, 42, 31, 35, 12, 45, 19, 23, 9, 21]
@@ -81,6 +88,7 @@ def test_delete_five(self):
values = [41, 41]
for i in range(0, len(values), 2):
self.wrap(T, values[i], values[i + 1])
+
def test_delete_six(self):
intervals = []
values = [41, 41, 38, 42, 31, 35, 12, 45, 19, 23, 9, 21]
@@ -93,8 +101,8 @@ def test_delete_six(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
T.delete(T.iterative_tree_search(41))
- self.assertEquals(T.nil.maximum, float("-Inf"))
-
+ self.assertEqual(T.nil.maximum, float("-Inf"))
+
def test_interval_search(self):
intervals = []
values = [41, 41, 38, 52, 43, 48]
@@ -103,13 +111,13 @@ def test_interval_search(self):
T = interval_tree(intervals)
i = interval(50, 51)
t = T.closed_interval_search(i)
- self.assertEquals(T.root.left, t)
+ self.assertEqual(T.root.left, t)
i = interval(58, 60)
t = T.closed_interval_search(i)
- self.assertEquals(T.nil, t)
+ self.assertEqual(T.nil, t)
i = interval(38, 48)
t = T.closed_interval_search(i)
- self.assertEquals(T.root, t)
+ self.assertEqual(T.root, t)
def test_interval_search_minimum_low_end(self):
intervals = []
@@ -119,13 +127,13 @@ def test_interval_search_minimum_low_end(self):
T = interval_tree(intervals)
i = interval(22, 51)
t = T.closed_interval_search_minimum_low_end(i)
- self.assertEquals(T.root.left, t)
+ self.assertEqual(T.root.left, t)
i = interval(58, 60)
t = T.closed_interval_search_minimum_low_end(i)
- self.assertEquals(T.nil, t)
+ self.assertEqual(T.nil, t)
i = interval(38, 48)
t = T.closed_interval_search_minimum_low_end(i)
- self.assertEquals(T.root.left, t)
+ self.assertEqual(T.root.left, t)
def test_list_all_overlapping_intervals(self):
intervals = []
@@ -152,26 +160,29 @@ def test_interval_search_exactly(self):
T = interval_tree(intervals)
i = interval(22, 51)
t = T.interval_search_exactly(i)
- self.assertEquals(t, T.nil)
+ self.assertEqual(t, T.nil)
i = interval(41, 41)
t = T.interval_search_exactly(i)
- self.assertEquals(t, T.root)
+ self.assertEqual(t, T.root)
i = interval(38, 52)
t = T.interval_search_exactly(i)
- self.assertEquals(t, T.root.left)
+ self.assertEqual(t, T.root.left)
i = interval(43, 48)
t = T.interval_search_exactly(i)
- self.assertEquals(t, T.root.right)
+ self.assertEqual(t, T.root.right)
i = interval(43, 49)
t = T.interval_search_exactly(i)
- self.assertEquals(t, T.nil)
+ self.assertEqual(t, T.nil)
i = interval(20, 50)
t = T.interval_search_exactly(i)
- self.assertEquals(t, T.nil)
+ self.assertEqual(t, T.nil)
i = interval(39, 41)
t = T.interval_search_exactly(i)
- self.assertEquals(t, T.nil)
+ self.assertEqual(t, T.nil)
+
def wrap(self, tree, node, maximum):
- self.assertEquals(tree.iterative_tree_search(node).maximum, maximum)
+ self.assertEqual(tree.iterative_tree_search(node).maximum, maximum)
+
+
if __name__ == '__main__':
unittest.main()
diff --git a/tests/inversion_test.py b/tests/inversion_test.py
new file mode 100644
index 0000000..b85bac9
--- /dev/null
+++ b/tests/inversion_test.py
@@ -0,0 +1,27 @@
+#!/usr/bin/env python
+# encoding: utf-8
+import unittest
+import random
+from inversion import inversion_with_insertion_sort, inversion_with_merge_sort
+
+
+class TestInversion(unittest.TestCase):
+ def test_inversion_with_insertion_sort(self):
+ for _ in range(100):
+ array = [random.randint(0, 100) for _ in range(100)]
+ expected_result = 0
+ for i in range(len(array)):
+ for j in range(i + 1, len(array)):
+ if array[i] > array[j]:
+ expected_result += 1
+ self.assertEqual(inversion_with_insertion_sort(array), expected_result)
+
+ def test_inversion_with_merge_sort(self):
+ for _ in range(100):
+ array = [random.randint(0, 100) for _ in range(100)]
+ expected_result = 0
+ for i in range(len(array)):
+ for j in range(i + 1, len(array)):
+ if array[i] > array[j]:
+ expected_result += 1
+ self.assertEqual(inversion_with_merge_sort(array), expected_result)
diff --git a/tests/k_way_merge_test.py b/tests/k_way_merge_test.py
new file mode 100644
index 0000000..e1944fd
--- /dev/null
+++ b/tests/k_way_merge_test.py
@@ -0,0 +1,14 @@
+#!/usr/bin/env python
+import unittest
+from k_way_merge import k_way_merge
+from random_array import random_arrays
+
+
+class TestKWayMerge(unittest.TestCase):
+ def test_k_way_merge(self):
+ for array in random_arrays():
+ lists = []
+ for i in range(10):
+ lists.append(array[10 * i: (i + 1) * 10])
+ lists[-1].sort()
+ self.assertEqual(k_way_merge(lists), sorted(array))
diff --git a/tests/linked_list_test.py b/tests/linked_list_test.py
new file mode 100644
index 0000000..06779d2
--- /dev/null
+++ b/tests/linked_list_test.py
@@ -0,0 +1,57 @@
+import unittest
+from linkedlist import LinkedList, LinkedListNode
+
+
+class TestLinkedList(unittest.TestCase):
+ def test_insert(self):
+ L = LinkedList()
+ a = LinkedListNode(1)
+ b = LinkedListNode(4)
+ c = LinkedListNode(16)
+ d = LinkedListNode(9)
+ e = LinkedListNode(25)
+ L.insert(a)
+ L.insert(b)
+ L.insert(c)
+ L.insert(d)
+ L.insert(e)
+ l = []
+ x = L.head
+ while x:
+ l.append(x)
+ x = x.next
+ self.assertEqual(l, [e, d, c, b, a])
+
+ def test_search(self):
+ L = LinkedList()
+ a = LinkedListNode(1)
+ b = LinkedListNode(4)
+ c = LinkedListNode(16)
+ d = LinkedListNode(9)
+ e = LinkedListNode(25)
+ L.insert(a)
+ L.insert(b)
+ L.insert(c)
+ L.insert(d)
+ L.insert(e)
+ self.assertEqual(L.search(4), b)
+
+ def test_delete(self):
+ L = LinkedList()
+ a = LinkedListNode(1)
+ b = LinkedListNode(4)
+ c = LinkedListNode(16)
+ d = LinkedListNode(9)
+ e = LinkedListNode(25)
+ L.insert(a)
+ L.insert(b)
+ L.insert(c)
+ L.insert(d)
+ L.insert(e)
+ L.delete(b)
+ l = []
+ x = L.head
+ while x:
+ l.append(x)
+ x = x.next
+ self.assertEqual(l, [e, d, c, a])
diff --git a/longest_common_subsequence_test.py b/tests/longest_common_subsequence_test.py
similarity index 58%
rename from longest_common_subsequence_test.py
rename to tests/longest_common_subsequence_test.py
index 84bd881..3aaa4ec 100644
--- a/longest_common_subsequence_test.py
+++ b/tests/longest_common_subsequence_test.py
@@ -1,28 +1,30 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
from longest_common_subsequence import lcs_length_one_row, lcs_length
+
class TestLCS(unittest.TestCase):
def test_lcs_length(self):
X = "ABCBDAB"
Y = "BDCABA"
- c,b = lcs_length(X, Y)
- self.assertEquals(c[len(X), len(Y)], 4)
+ c, b = lcs_length(X, Y)
+ self.assertEqual(c[len(X), len(Y)], 4)
X = [1, 0, 0, 1, 0, 1, 0, 1]
Y = [0, 1, 0, 1, 1, 0, 1, 1, 0]
- c,b = lcs_length(X, Y)
- self.assertEquals(c[len(X), len(Y)], 6)
+ c, b = lcs_length(X, Y)
+ self.assertEqual(c[len(X), len(Y)], 6)
X = "ACCGGTCGAGTGCGCGGAAGCCGGCCGAA"
Y = "GTCGTTCGGAATGCCGTTGCTCTGTAAA"
- c,b = lcs_length(X, Y)
- self.assertEquals(c[len(X), len(Y)], 20)
+ c, b = lcs_length(X, Y)
+ self.assertEqual(c[len(X), len(Y)], 20)
+
def test_lcs_length_one_row(self):
X = "ABCBDAB"
Y = "BDCABA"
- self.assertEquals(lcs_length_one_row(X, Y), 4)
+ self.assertEqual(lcs_length_one_row(X, Y), 4)
X = [1, 0, 0, 1, 0, 1, 0, 1]
Y = [0, 1, 0, 1, 1, 0, 1, 1, 0]
- self.assertEquals(lcs_length_one_row(X, Y), 6)
+ self.assertEqual(lcs_length_one_row(X, Y), 6)
X = "ACCGGTCGAGTGCGCGGAAGCCGGCCGAA"
Y = "GTCGTTCGGAATGCCGTTGCTCTGTAAA"
- self.assertEquals(lcs_length_one_row(X, Y), 20)
+ self.assertEqual(lcs_length_one_row(X, Y), 20)
diff --git a/longest_monotonically_increasing_subsequence_test.py b/tests/longest_monotonically_increasing_subsequence_test.py
similarity index 59%
rename from longest_monotonically_increasing_subsequence_test.py
rename to tests/longest_monotonically_increasing_subsequence_test.py
index 6f94d7f..3be5ef2 100644
--- a/longest_monotonically_increasing_subsequence_test.py
+++ b/tests/longest_monotonically_increasing_subsequence_test.py
@@ -7,8 +7,8 @@
class TestLMIS(unittest.TestCase):
def test_longest_monotonically_increasing_subsequence(self):
X = [5, 4, 1, 3, 2]
- self.assertEquals(longest_monotonically_increasing_subsequence(X), 2)
+ self.assertEqual(longest_monotonically_increasing_subsequence(X), 2)
X = [1, 3, 4, 2, 5]
- self.assertEquals(longest_monotonically_increasing_subsequence(X), 4)
+ self.assertEqual(longest_monotonically_increasing_subsequence(X), 4)
X = [1, 3, 10, 5, 3, 4]
- self.assertEquals(longest_monotonically_increasing_subsequence(X), 3)
+ self.assertEqual(longest_monotonically_increasing_subsequence(X), 3)
diff --git a/tests/merge_sort_test.py b/tests/merge_sort_test.py
new file mode 100644
index 0000000..7455c8b
--- /dev/null
+++ b/tests/merge_sort_test.py
@@ -0,0 +1,33 @@
+#!/usr/bin/env python
+import unittest
+import random
+from merge_sort import merge_sort, merge_with_sentinel, merge_without_sentinel, merge_ins_sort_bottom_to_top, \
+ merge_ins_sort_top_to_bottom
+
+
+class TestMergeSort(unittest.TestCase):
+ def test_merge_sort_with_sentinel(self):
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ merge_sort(array, merge_with_sentinel)
+ self.assertEqual(array, sorted(array_copy))
+
+ def test_merge_sort_without_sentinel(self):
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ merge_sort(array, merge_without_sentinel)
+ self.assertEqual(array, sorted(array_copy))
+
+ def test_merge_ins_sort(self):
+ for length in range(100, 200):
+ array = [random.randint(1, 10000) for _ in range(length)]
+ array_copy = array[:]
+ merge_ins_sort_bottom_to_top(array, partition=1)
+ self.assertEqual(array, sorted(array_copy))
+ for length in range(100, 200):
+ array = [random.randint(1, 10000) for _ in range(length)]
+ array_copy = array[:]
+ merge_ins_sort_top_to_bottom(array, sublist_length=15)
+ self.assertEqual(array, sorted(array_copy))
diff --git a/min_gap_tree_test.py b/tests/min_gap_tree_test.py
similarity index 76%
rename from min_gap_tree_test.py
rename to tests/min_gap_tree_test.py
index aef1bb7..2bcf352 100755
--- a/min_gap_tree_test.py
+++ b/tests/min_gap_tree_test.py
@@ -1,92 +1,106 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
-from min_gap_tree import min_gap_tree, min_gap_node
+from min_gap_tree import MinGapTree, MinGapNode
class TestMinGapTree(unittest.TestCase):
def test_insert_one(self):
- T = min_gap_tree([50])
+ T = MinGapTree([50])
self.wrap(T, 50, float("Inf"))
+
def test_insert_two(self):
- T = min_gap_tree([50, 38])
+ T = MinGapTree([50, 38])
self.wrap(T, 50, 12)
self.wrap(T, 38, 12)
+
def test_insert_three(self):
- T = min_gap_tree([50, 38, 31])
+ T = MinGapTree([50, 38, 31])
self.wrap(T, 38, 7)
self.wrap(T, 31, 7)
self.wrap(T, 50, float("Inf"))
+
def test_insert_four(self):
- T = min_gap_tree([50, 38, 31, 12])
- self.wrap(T, 38, 7)
+ T = MinGapTree([50, 38, 31, 12])
+ self.wrap(T, 38, 7)
self.wrap(T, 31, 7)
self.wrap(T, 50, float("Inf"))
self.wrap(T, 12, 19)
+
def test_insert_five(self):
- T = min_gap_tree([50, 38, 31, 12, 19])
- self.wrap(T, 38, 7)
+ T = MinGapTree([50, 38, 31, 12, 19])
+ self.wrap(T, 38, 7)
self.wrap(T, 19, 7)
self.wrap(T, 50, float("Inf"))
self.wrap(T, 12, 7)
self.wrap(T, 31, 7)
+
def test_insert_six(self):
- T = min_gap_tree([50, 38, 31, 12, 19, 9])
+ T = MinGapTree([50, 38, 31, 12, 19, 9])
self.wrap(T, 38, 3)
self.wrap(T, 19, 3)
self.wrap(T, 50, float("Inf"))
self.wrap(T, 12, 3)
self.wrap(T, 31, 7)
self.wrap(T, 9, 3)
+
def test_delete_one(self):
- T = min_gap_tree([50, 38, 31, 12, 19, 9])
+ T = MinGapTree([50, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
self.wrap(T, 38, 7)
self.wrap(T, 19, 7)
self.wrap(T, 50, float("Inf"))
self.wrap(T, 12, 7)
self.wrap(T, 31, 7)
+
def test_delete_two(self):
- T = min_gap_tree([50, 38, 31, 12, 19, 9])
+ T = MinGapTree([50, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
self.wrap(T, 38, 7)
self.wrap(T, 19, 7)
self.wrap(T, 50, float("Inf"))
self.wrap(T, 31, 7)
+
def test_delete_three(self):
- T = min_gap_tree([50, 38, 31, 12, 19, 9])
+ T = MinGapTree([50, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
T.delete(T.iterative_tree_search(19))
self.wrap(T, 38, 7)
self.wrap(T, 31, 7)
self.wrap(T, 50, float("Inf"))
+
def test_delete_four(self):
- T = min_gap_tree([50, 38, 31, 12, 19, 9])
+ T = MinGapTree([50, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
T.delete(T.iterative_tree_search(19))
T.delete(T.iterative_tree_search(31))
self.wrap(T, 38, 12)
self.wrap(T, 50, float("Inf"))
+
def test_delete_five(self):
- T = min_gap_tree([50, 38, 31, 12, 19, 9])
+ T = MinGapTree([50, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
T.delete(T.iterative_tree_search(19))
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
self.wrap(T, 50, float("Inf"))
+
def test_delete_six(self):
- T = min_gap_tree([50, 38, 31, 12, 19, 9])
+ T = MinGapTree([50, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
T.delete(T.iterative_tree_search(19))
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
T.delete(T.iterative_tree_search(50))
- self.assertEquals(T.root, T.nil)
+ self.assertEqual(T.root, T.nil)
+
def wrap(self, tree, node, min_gap):
- self.assertEquals(tree.iterative_tree_search(node).min_gap, min_gap)
+ self.assertEqual(tree.iterative_tree_search(node).min_gap, min_gap)
+
+
if __name__ == '__main__':
unittest.main()
diff --git a/tests/min_heap_with_linked_list_test.py b/tests/min_heap_with_linked_list_test.py
new file mode 100644
index 0000000..91c7202
--- /dev/null
+++ b/tests/min_heap_with_linked_list_test.py
@@ -0,0 +1,94 @@
+import unittest
+
+from linkedlist import LinkedList, LinkedListNode
+from min_heap_with_linked_list import MinHeap, MinPriorityQueue
+
+
+class TestHeap(unittest.TestCase):
+ def test_min_heapify(self):
+ L1 = LinkedList(1)
+ L2 = LinkedList(2)
+ L2.insert(LinkedListNode(2))
+ L2.insert(LinkedListNode(2))
+ L3 = LinkedList(3)
+ L3.insert(LinkedListNode(3))
+ L3.insert(LinkedListNode(3))
+ L4 = LinkedList(4)
+ L4.insert(LinkedListNode(4))
+ L5 = LinkedList(5)
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ h = MinHeap([L5, L1, L2, L3, L4])
+ h.min_heapify(0)
+ self.assertEqual(h, [L1, L3, L2, L5, L4])
+
+ def test_build_min_heap(self):
+ L1 = LinkedList(1)
+ L2 = LinkedList(2)
+ L2.insert(LinkedListNode(2))
+ L2.insert(LinkedListNode(2))
+ L3 = LinkedList(3)
+ L3.insert(LinkedListNode(3))
+ L3.insert(LinkedListNode(3))
+ L4 = LinkedList(4)
+ L4.insert(LinkedListNode(4))
+ L5 = LinkedList(5)
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ h = MinHeap([L3, L4, L5, L2, L1])
+ h.build_min_heap()
+ self.assertEqual(h, [L1, L2, L5, L3, L4])
+
+ def test_heap_minimum(self):
+ L1 = LinkedList(1)
+ L1.insert(LinkedListNode(1))
+ L1.insert(LinkedListNode(1))
+ L2 = LinkedList(2)
+ L2.insert(LinkedListNode(2))
+ L2.insert(LinkedListNode(2))
+ L3 = LinkedList(3)
+ L3.insert(LinkedListNode(3))
+ L3.insert(LinkedListNode(3))
+ L4 = LinkedList(4)
+ L4.insert(LinkedListNode(4))
+ L5 = LinkedList(5)
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ q = MinPriorityQueue([L1, L2, L3, L4, L5])
+ self.assertEqual(q.heap_minimum().key, 1)
+
+ def test_heap_extract_min(self):
+ L1 = LinkedList(1)
+ L1.insert(LinkedListNode(1))
+ L1.insert(LinkedListNode(1))
+ L2 = LinkedList(2)
+ L2.insert(LinkedListNode(2))
+ L2.insert(LinkedListNode(2))
+ L3 = LinkedList(3)
+ L3.insert(LinkedListNode(3))
+ L3.insert(LinkedListNode(3))
+ L4 = LinkedList(4)
+ L4.insert(LinkedListNode(4))
+ L5 = LinkedList(5)
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ L3.insert(LinkedListNode(5))
+ q = MinPriorityQueue([L1, L2, L3, L4, L5])
+ self.assertEqual(q.heap_extract_min().key, 1)
+ self.assertEqual(q, [L1, L2, L3, L4, L5])
+ self.assertEqual(q.heap_extract_min().key, 1)
+ self.assertEqual(q, [L2, L4, L3, L5, L5])
+# def test_heap_decrease_key(self):
+# a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
+# q = MinPriorityQueue(a)
+# q.heap_decrease_key(8, 1)
+# self.assertEqual(q, [1, 1, 3, 2, 7, 8, 9, 10, 4, 16])
+# def test_heap_insert(self):
+# a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
+# q = MinPriorityQueue(a)
+# q.heap_extract_min()
+# q.min_heap_insert(0)
+# self.assertEqual(q, [0, 2, 3, 10, 4, 8, 9, 16, 14, 7])
diff --git a/tests/min_priority_queue_using_rb_tree_test.py b/tests/min_priority_queue_using_rb_tree_test.py
new file mode 100644
index 0000000..5bdbb4e
--- /dev/null
+++ b/tests/min_priority_queue_using_rb_tree_test.py
@@ -0,0 +1,45 @@
+#!/usr/bin/env python
+import unittest
+from min_priority_queue_using_rb_tree import min_priority_queue
+from rb_tree import RbNode
+
+
+class TestMinPriorityQueue(unittest.TestCase):
+ def test_extract_min(self):
+ q = min_priority_queue([41, 38, 31, 12, 19, 9])
+ self.assertEqual(q.heap_extract_min().key, 9)
+ self.assertEqual(q.heap_extract_min().key, 12)
+ self.assertEqual(q.heap_extract_min().key, 19)
+ self.assertEqual(q.heap_extract_min().key, 31)
+ self.assertEqual(q.heap_extract_min().key, 38)
+ self.assertEqual(q.heap_extract_min().key, 41)
+
+ def test_heap_decrease_key(self):
+ q = min_priority_queue([41, 38, 31, 12, 19, 9])
+ q.heap_decrease_key(q.iterative_tree_search(9), 5)
+ q.heap_decrease_key(q.iterative_tree_search(38), 5)
+ self.assertEqual(q.heap_extract_min().key, 5)
+ self.assertEqual(q.heap_extract_min().key, 5)
+ self.assertEqual(q.heap_extract_min().key, 12)
+ self.assertEqual(q.heap_extract_min().key, 19)
+ self.assertEqual(q.heap_extract_min().key, 31)
+ self.assertEqual(q.heap_extract_min().key, 41)
+
+ def test_heap_insert(self):
+ q = min_priority_queue([41, 38, 31, 12, 19, 9])
+ q.min_heap_insert(RbNode(5, None, None, None, 0))
+ q.min_heap_insert(RbNode(38, None, None, None, 0))
+ q.min_heap_insert(RbNode(50, None, None, None, 0))
+ self.assertEqual(q.heap_extract_min().key, 5)
+ self.assertEqual(q.heap_extract_min().key, 9)
+ self.assertEqual(q.heap_extract_min().key, 12)
+ self.assertEqual(q.heap_extract_min().key, 19)
+ self.assertEqual(q.heap_extract_min().key, 31)
+ self.assertEqual(q.heap_extract_min().key, 38)
+ self.assertEqual(q.heap_extract_min().key, 38)
+ self.assertEqual(q.heap_extract_min().key, 41)
+ self.assertEqual(q.heap_extract_min().key, 50)
+
+
+if __name__ == '__main__':
+ unittest.main()
diff --git a/most_reliable_path_test.py b/tests/most_reliable_path_test.py
similarity index 52%
rename from most_reliable_path_test.py
rename to tests/most_reliable_path_test.py
index 1383f7b..4817889 100644
--- a/most_reliable_path_test.py
+++ b/tests/most_reliable_path_test.py
@@ -2,6 +2,7 @@
import unittest
from graph import Vertex, Graph
+
class TestMostReliablePath(unittest.TestCase):
def test_most_reliable_path(self):
s = Vertex('s')
@@ -11,15 +12,17 @@ def test_most_reliable_path(self):
vertices = [s, u, v, w]
edges = [(s, u), (s, v), (s, w), (u, v), (u, w), (w, u)]
G = Graph(vertices, edges)
- probabilities = [0.2, 0.1, 0.15, 0.7, 0.6, 0.9]
+ probabilities = [0.2, 0.1, 0.15, 0.7, 0.6, 0.9]
re = dict()
- for i,j in zip(edges, probabilities):
- re[i] = j
+ for i, j in zip(edges, probabilities):
+ re[i] = j
+
def r(x, y):
- return re[(x, y)]
+ return re[(x, y)]
+
most_reliable_path(G, r, s)
- self.assertEquals([i.p for i in vertices], [None, s, u, s])
- self.assertEquals([round(i.r, 2) for i in vertices], [1, 0.2, 0.14, 0.15])
+ self.assertEqual([i.p for i in vertices], [None, s, u, s])
+ self.assertEqual([round(i.r, 2) for i in vertices], [1, 0.2, 0.14, 0.15])
most_reliable_path(G, r, u)
- self.assertEquals([i.p for i in vertices], [None, None, u, u])
- self.assertEquals([round(i.r, 2) for i in vertices], [0, 1, 0.7, 0.6])
+ self.assertEqual([i.p for i in vertices], [None, None, u, u])
+ self.assertEqual([round(i.r, 2) for i in vertices], [0, 1, 0.7, 0.6])
diff --git a/os_tree_test.py b/tests/os_tree_test.py
similarity index 50%
rename from os_tree_test.py
rename to tests/os_tree_test.py
index 83e77b2..4d99ede 100755
--- a/os_tree_test.py
+++ b/tests/os_tree_test.py
@@ -1,55 +1,61 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
-from os_tree import os_tree, os_node
+from os_tree import os_tree, OSNode
class TestOstree(unittest.TestCase):
def test_insert_one(self):
T = os_tree([41])
- print T.root.iterative_tree_search(41).p.key
- self.assertEquals(T.root, T.root.iterative_tree_search(41))
- self.assertEquals(T.nil.size, 0)
+ print(T.root.iterative_tree_search(41).p.key)
+ self.assertEqual(T.root, T.root.iterative_tree_search(41))
+ self.assertEqual(T.nil.size, 0)
self.wrap(T, 41, -1, -1, -1, 1, 1)
+
def test_insert_two(self):
T = os_tree([41, 38])
- self.assertEquals(T.root, T.iterative_tree_search(41))
- self.assertEquals(T.nil.size, 0)
+ self.assertEqual(T.root, T.iterative_tree_search(41))
+ self.assertEqual(T.nil.size, 0)
self.wrap(T, 41, 38, -1, -1, 1, 2)
self.wrap(T, 38, -1, -1, 41, 0, 1)
+
def test_insert_three(self):
T = os_tree([41, 38, 31])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.size, 0)
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.size, 0)
self.wrap(T, 38, 31, 41, -1, 1, 3)
self.wrap(T, 31, -1, -1, 38, 0, 1)
self.wrap(T, 41, -1, -1, 38, 0, 1)
+
def test_insert_four(self):
T = os_tree([41, 38, 31, 12])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.size, 0)
- self.wrap(T, 38, 31, 41, -1, 1, 4)
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.size, 0)
+ self.wrap(T, 38, 31, 41, -1, 1, 4)
self.wrap(T, 31, 12, -1, 38, 1, 2)
self.wrap(T, 41, -1, -1, 38, 1, 1)
self.wrap(T, 12, -1, -1, 31, 0, 1)
+
def test_insert_five(self):
T = os_tree([41, 38, 31, 12, 19])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.size, 0)
- self.wrap(T, 38, 19, 41, -1, 1, 5)
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.size, 0)
+ self.wrap(T, 38, 19, 41, -1, 1, 5)
self.wrap(T, 19, 12, 31, 38, 1, 3)
self.wrap(T, 41, -1, -1, 38, 1, 1)
self.wrap(T, 12, -1, -1, 19, 0, 1)
self.wrap(T, 31, -1, -1, 19, 0, 1)
+
def test_insert_six(self):
T = os_tree([41, 38, 31, 12, 19, 9])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.size, 0)
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.size, 0)
self.wrap(T, 38, 19, 41, -1, 1, 6)
self.wrap(T, 19, 12, 31, 38, 0, 4)
self.wrap(T, 41, -1, -1, 38, 1, 1)
self.wrap(T, 12, 9, -1, 19, 1, 2)
self.wrap(T, 31, -1, -1, 19, 1, 1)
self.wrap(T, 9, -1, -1, 12, 0, 1)
+
def test_delete_one(self):
T = os_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -58,6 +64,7 @@ def test_delete_one(self):
self.wrap(T, 41, -1, -1, 38, 1, 1)
self.wrap(T, 12, -1, -1, 19, 1, 1)
self.wrap(T, 31, -1, -1, 19, 1, 1)
+
def test_delete_two(self):
T = os_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -66,6 +73,7 @@ def test_delete_two(self):
self.wrap(T, 19, -1, 31, 38, 1, 2)
self.wrap(T, 41, -1, -1, 38, 1, 1)
self.wrap(T, 31, -1, -1, 19, 0, 1)
+
def test_delete_three(self):
T = os_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -74,6 +82,7 @@ def test_delete_three(self):
self.wrap(T, 38, 31, 41, -1, 1, 3)
self.wrap(T, 31, -1, -1, 38, 1, 1)
self.wrap(T, 41, -1, -1, 38, 1, 1)
+
def test_delete_four(self):
T = os_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -82,6 +91,7 @@ def test_delete_four(self):
T.delete(T.iterative_tree_search(31))
self.wrap(T, 38, -1, 41, -1, 1, 2)
self.wrap(T, 41, -1, -1, 38, 0, 1)
+
def test_delete_five(self):
T = os_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -90,6 +100,7 @@ def test_delete_five(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
self.wrap(T, 41, -1, -1, -1, 1, 1)
+
def test_delete_six(self):
T = os_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -98,62 +109,72 @@ def test_delete_six(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
T.delete(T.iterative_tree_search(41))
- self.assertEquals(T.root, T.nil)
- self.assertEquals(T.nil.size, 0)
+ self.assertEqual(T.root, T.nil)
+ self.assertEqual(T.nil.size, 0)
+
def test_key_rank(self):
T = os_tree([41, 38, 31, 12, 19, 9])
- self.assertEquals(T.root.key_rank(41), 6)
- self.assertEquals(T.root.key_rank(38), 5)
- self.assertEquals(T.root.key_rank(31), 4)
- self.assertEquals(T.root.key_rank(12), 2)
- self.assertEquals(T.root.key_rank(19), 3)
- self.assertEquals(T.root.key_rank(9), 1)
+ self.assertEqual(T.root.key_rank(41), 6)
+ self.assertEqual(T.root.key_rank(38), 5)
+ self.assertEqual(T.root.key_rank(31), 4)
+ self.assertEqual(T.root.key_rank(12), 2)
+ self.assertEqual(T.root.key_rank(19), 3)
+ self.assertEqual(T.root.key_rank(9), 1)
+
def test_rank(self):
T = os_tree([41, 38, 31, 12, 19, 9])
- self.assertEquals(T.rank(T.iterative_tree_search(41)), 6)
- self.assertEquals(T.rank(T.iterative_tree_search(38)), 5)
- self.assertEquals(T.rank(T.iterative_tree_search(31)), 4)
- self.assertEquals(T.rank(T.iterative_tree_search(12)), 2)
- self.assertEquals(T.rank(T.iterative_tree_search(19)), 3)
- self.assertEquals(T.rank(T.iterative_tree_search(9)), 1)
+ self.assertEqual(T.rank(T.iterative_tree_search(41)), 6)
+ self.assertEqual(T.rank(T.iterative_tree_search(38)), 5)
+ self.assertEqual(T.rank(T.iterative_tree_search(31)), 4)
+ self.assertEqual(T.rank(T.iterative_tree_search(12)), 2)
+ self.assertEqual(T.rank(T.iterative_tree_search(19)), 3)
+ self.assertEqual(T.rank(T.iterative_tree_search(9)), 1)
+
def test_select(self):
T = os_tree([41, 38, 31, 12, 19, 9])
- self.assertEquals(T.root.select_recursive(1).key, 9)
- self.assertEquals(T.root.select_recursive(2).key, 12)
- self.assertEquals(T.root.select_recursive(3).key, 19)
- self.assertEquals(T.root.select_recursive(4).key, 31)
- self.assertEquals(T.root.select_recursive(5).key, 38)
- self.assertEquals(T.root.select_recursive(6).key, 41)
- self.assertEquals(T.root.select_iterative(1).key, 9)
- self.assertEquals(T.root.select_iterative(2).key, 12)
- self.assertEquals(T.root.select_iterative(3).key, 19)
- self.assertEquals(T.root.select_iterative(4).key, 31)
- self.assertEquals(T.root.select_iterative(5).key, 38)
- self.assertEquals(T.root.select_iterative(6).key, 41)
+ self.assertEqual(T.root.select_recursive(1).key, 9)
+ self.assertEqual(T.root.select_recursive(2).key, 12)
+ self.assertEqual(T.root.select_recursive(3).key, 19)
+ self.assertEqual(T.root.select_recursive(4).key, 31)
+ self.assertEqual(T.root.select_recursive(5).key, 38)
+ self.assertEqual(T.root.select_recursive(6).key, 41)
+ self.assertEqual(T.root.select_iterative(1).key, 9)
+ self.assertEqual(T.root.select_iterative(2).key, 12)
+ self.assertEqual(T.root.select_iterative(3).key, 19)
+ self.assertEqual(T.root.select_iterative(4).key, 31)
+ self.assertEqual(T.root.select_iterative(5).key, 38)
+ self.assertEqual(T.root.select_iterative(6).key, 41)
+
def test_ith_successor(self):
T = os_tree([41, 38, 31, 12, 19, 9])
- self.assertEquals(T.iterative_tree_search(9).ith_successor(1).key, 12)
- self.assertEquals(T.iterative_tree_search(9).ith_successor(2).key, 19)
- self.assertEquals(T.iterative_tree_search(9).ith_successor(3).key, 31)
- self.assertEquals(T.iterative_tree_search(9).ith_successor(4).key, 38)
- self.assertEquals(T.iterative_tree_search(9).ith_successor(5).key, 41)
-# def test_insert_stack(self):
-# T = os_tree([])
-# for i in 41, 38, 31, 12, 19, 9:
-# T.insert_stack(os_node(i, None, None, None, 0))
-# self.assertEquals(T.root, T.iterative_tree_search(38))
-# self.assertEquals(T.nil.color, 1)
-# self.wrap(T, 38, 19, 41, -1, 1)
-# self.wrap(T, 19, 12, 31, 38, 0)
-# self.wrap(T, 41, -1, -1, 38, 1)
-# self.wrap(T, 12, 9, -1, 19, 1)
-# self.wrap(T, 31, -1, -1, 19, 1)
-# self.wrap(T, 9, -1, -1, 12, 0)
+ self.assertEqual(T.iterative_tree_search(9).ith_successor(1).key, 12)
+ self.assertEqual(T.iterative_tree_search(9).ith_successor(2).key, 19)
+ self.assertEqual(T.iterative_tree_search(9).ith_successor(3).key, 31)
+ self.assertEqual(T.iterative_tree_search(9).ith_successor(4).key, 38)
+ self.assertEqual(T.iterative_tree_search(9).ith_successor(5).key, 41)
+
+ # def test_insert_stack(self):
+ # T = os_tree([])
+ # for i in 41, 38, 31, 12, 19, 9:
+ # T.insert_stack(OSNode(i, None, None, None, 0))
+ # self.assertEqual(T.root, T.iterative_tree_search(38))
+ # self.assertEqual(T.nil.color, 1)
+ # self.wrap(T, 38, 19, 41, -1, 1)
+ # self.wrap(T, 19, 12, 31, 38, 0)
+ # self.wrap(T, 41, -1, -1, 38, 1)
+ # self.wrap(T, 12, 9, -1, 19, 1)
+ # self.wrap(T, 31, -1, -1, 19, 1)
+ # self.wrap(T, 9, -1, -1, 12, 0)
def wrap(self, tree, node, left, right, p, color, size):
- self.assertEquals(tree.iterative_tree_search(node).left, tree.iterative_tree_search(left))
- self.assertEquals(tree.iterative_tree_search(node).right, tree.iterative_tree_search(right))
- self.assertEquals(tree.iterative_tree_search(node).p, tree.iterative_tree_search(p))
- self.assertEquals(tree.iterative_tree_search(node).color, color)
- self.assertEquals(tree.iterative_tree_search(node).size, size)
+ self.assertEqual(tree.iterative_tree_search(
+ node).left, tree.iterative_tree_search(left))
+ self.assertEqual(tree.iterative_tree_search(
+ node).right, tree.iterative_tree_search(right))
+ self.assertEqual(tree.iterative_tree_search(
+ node).p, tree.iterative_tree_search(p))
+ self.assertEqual(tree.iterative_tree_search(node).color, color)
+ self.assertEqual(tree.iterative_tree_search(node).size, size)
+
+
if __name__ == '__main__':
unittest.main()
diff --git a/tests/partition_test.py b/tests/partition_test.py
new file mode 100644
index 0000000..b2c67ce
--- /dev/null
+++ b/tests/partition_test.py
@@ -0,0 +1,24 @@
+import unittest
+from partition import partition, partition2, partition3
+from random_array import random_arrays
+
+
+class TestPartition(unittest.TestCase):
+ def test_partition(self):
+ for array in random_arrays():
+ pivot_index = partition(array, 0, len(array) - 1)
+ pivot = array[pivot_index]
+ self.assertTrue(all(array[i] <= pivot for i in range(pivot_index)) and all(
+ array[i] > pivot for i in range(pivot_index + 1, len(array))))
+
+ def test_partition2(self):
+ a = [2, 8, 7, 1, 4, 5, 6, 4]
+ partition2(a, 0, 7)
+ self.assertEqual(a, [2, 1, 4, 4, 7, 5, 6, 8])
+
+ def test_partition3(self):
+ for array in random_arrays():
+ pivot_index = partition3(array, 0, len(array) - 1)
+ pivot = array[pivot_index]
+ self.assertTrue(all(array[i] <= pivot for i in range(pivot_index)) and all(
+ array[i] > pivot for i in range(pivot_index + 1, len(array))))
diff --git a/pointer_tree_test.py b/tests/pointer_tree_test.py
similarity index 88%
rename from pointer_tree_test.py
rename to tests/pointer_tree_test.py
index 4ef4f6c..925b129 100755
--- a/pointer_tree_test.py
+++ b/tests/pointer_tree_test.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
from pointer_tree import pointer_tree, pointer_node
@@ -7,21 +7,25 @@ class TestOstree(unittest.TestCase):
def test_insert_one(self):
T = pointer_tree([41])
self.wrap(T, 41, 41, 41, float("-Inf"), float("Inf"))
+
def test_insert_two(self):
T = pointer_tree([41, 38])
self.wrap(T, 41, 38, 41, 38, float("Inf"))
self.wrap(T, 38, 38, 38, float("-Inf"), 41)
+
def test_insert_three(self):
T = pointer_tree([41, 38, 31])
self.wrap(T, 38, 31, 41, 31, 41)
self.wrap(T, 31, 31, 31, float("-Inf"), 38)
self.wrap(T, 41, 41, 41, 38, float("Inf"))
+
def test_insert_four(self):
T = pointer_tree([41, 38, 31, 12])
self.wrap(T, 38, 12, 41, 31, 41)
self.wrap(T, 31, 12, 31, 12, 38)
self.wrap(T, 41, 41, 41, 38, float("Inf"))
self.wrap(T, 12, 12, 12, float("-Inf"), 31)
+
def test_insert_five(self):
T = pointer_tree([41, 38, 31, 12, 19])
self.wrap(T, 38, 12, 41, 31, 41)
@@ -29,6 +33,7 @@ def test_insert_five(self):
self.wrap(T, 41, 41, 41, 38, float("Inf"))
self.wrap(T, 12, 12, 12, float("-Inf"), 19)
self.wrap(T, 31, 31, 31, 19, 38)
+
def test_insert_six(self):
T = pointer_tree([41, 38, 31, 12, 19, 9])
self.wrap(T, 38, 9, 41, 31, 41)
@@ -37,6 +42,7 @@ def test_insert_six(self):
self.wrap(T, 12, 9, 12, 9, 19)
self.wrap(T, 31, 31, 31, 19, 38)
self.wrap(T, 9, 9, 9, float("-Inf"), 12)
+
def test_delete_one(self):
T = pointer_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -45,6 +51,7 @@ def test_delete_one(self):
self.wrap(T, 41, 41, 41, 38, float("Inf"))
self.wrap(T, 12, 12, 12, float("-Inf"), 19)
self.wrap(T, 31, 31, 31, 19, 38)
+
def test_delete_two(self):
T = pointer_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -53,6 +60,7 @@ def test_delete_two(self):
self.wrap(T, 19, 19, 31, float("-Inf"), 31)
self.wrap(T, 41, 41, 41, 38, float("Inf"))
self.wrap(T, 31, 31, 31, 19, 38)
+
def test_delete_three(self):
T = pointer_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -61,6 +69,7 @@ def test_delete_three(self):
self.wrap(T, 38, 31, 41, 31, 41)
self.wrap(T, 31, 31, 31, float("-Inf"), 38)
self.wrap(T, 41, 41, 41, 38, float("Inf"))
+
def test_delete_four(self):
T = pointer_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -69,6 +78,7 @@ def test_delete_four(self):
T.delete(T.iterative_tree_search(31))
self.wrap(T, 38, 38, 41, float("-Inf"), 41)
self.wrap(T, 41, 41, 41, 38, float("Inf"))
+
def test_delete_five(self):
T = pointer_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -76,7 +86,8 @@ def test_delete_five(self):
T.delete(T.iterative_tree_search(19))
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
- self.wrap(T, 41, 41, 41, float("-Inf"), float("Inf"))
+ self.wrap(T, 41, 41, 41, float("-Inf"), float("Inf"))
+
def test_delete_six(self):
T = pointer_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -85,11 +96,16 @@ def test_delete_six(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
T.delete(T.iterative_tree_search(41))
- self.assertEquals(T.root, T.nil)
+ self.assertEqual(T.root, T.nil)
+
def wrap(self, tree, node, minimum, maximum, predecessor, successor):
- self.assertEquals(tree.iterative_tree_search(node).minimum.key, minimum)
- self.assertEquals(tree.iterative_tree_search(node).maximum.key, maximum)
- self.assertEquals(tree.iterative_tree_search(node).predecessor.key, predecessor)
- self.assertEquals(tree.iterative_tree_search(node).successor.key, successor)
+ self.assertEqual(tree.iterative_tree_search(node).minimum.key, minimum)
+ self.assertEqual(tree.iterative_tree_search(node).maximum.key, maximum)
+ self.assertEqual(tree.iterative_tree_search(
+ node).predecessor.key, predecessor)
+ self.assertEqual(tree.iterative_tree_search(
+ node).successor.key, successor)
+
+
if __name__ == '__main__':
unittest.main()
diff --git a/tests/polygon_area_test.py b/tests/polygon_area_test.py
new file mode 100644
index 0000000..7afde26
--- /dev/null
+++ b/tests/polygon_area_test.py
@@ -0,0 +1,12 @@
+import unittest
+from polygon_area import polygon_area
+
+
+class TestPolygonArea(unittest.TestCase):
+ def test_rectangle_area(self):
+ rectangle = ((0, 0), (0, 2), (2, 2), (2, 0))
+ self.assertEqual(polygon_area(rectangle), 4)
+
+ def test_triangle_area(self):
+ triangle = ((0, 0), (5, 0), (2.5, 5))
+ self.assertEqual(polygon_area(triangle), 12.5)
diff --git a/tests/priority_queue_test.py b/tests/priority_queue_test.py
new file mode 100644
index 0000000..5c21b0b
--- /dev/null
+++ b/tests/priority_queue_test.py
@@ -0,0 +1,86 @@
+import unittest
+from priority_queue import MaxPriorityQueue, MinPriorityQueue
+
+
+class TestMaxPriorityQueue(unittest.TestCase):
+ def test_init(self):
+ a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
+ q = MaxPriorityQueue(a)
+ self.assertEqual(q, [16, 14, 10, 8, 7, 9, 3, 2, 4, 1])
+
+ def test_heap_maximum(self):
+ a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
+ self.assertEqual(MaxPriorityQueue(a).heap_maximum(), 16)
+
+ def test_heap_extract_max(self):
+ a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
+ h = MaxPriorityQueue(a)
+ self.assertEqual(h.heap_extract_max(), 16)
+ self.assertEqual(h, [14, 8, 10, 4, 7, 9, 3, 2, 1, 1])
+
+ def test_heap_increase_key(self):
+ a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
+ h = MaxPriorityQueue(a)
+ h.heap_increase_key(8, 15)
+ self.assertEqual(h, [16, 15, 10, 14, 7, 9, 3, 2, 8, 1])
+
+ def test_heap_insert(self):
+ a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
+ queue = MaxPriorityQueue(a)
+ queue.heap_extract_max()
+ queue.max_heap_insert(100)
+ self.assertEqual(queue, [100, 14, 10, 4, 8, 9, 3, 2, 1, 7])
+
+ def test_heap_delete(self):
+ a = [4, 1, 3, 2, 16, 9, 10, 14, 8, 7]
+ h = MaxPriorityQueue(a)
+ h.heap_delete(4)
+ self.assertEqual(h[0:h.heap_size], [16, 14, 10, 8, 1, 9, 3, 2, 4])
+ h.heap_delete(2)
+ self.assertEqual(h[0:h.heap_size], [16, 14, 9, 8, 1, 4, 3, 2])
+ h.heap_delete(0)
+ self.assertEqual(h[0:h.heap_size], [14, 8, 9, 2, 1, 4, 3])
+ h.heap_delete(5)
+ self.assertEqual(h[0:h.heap_size], [14, 8, 9, 2, 1, 3])
+ h.heap_delete(3)
+ self.assertEqual(h[0:h.heap_size], [14, 8, 9, 3, 1])
+ h.heap_delete(1)
+ self.assertEqual(h[0:h.heap_size], [14, 3, 9, 1])
+ h.heap_delete(3)
+ self.assertEqual(h[0:h.heap_size], [14, 3, 9])
+ h.heap_delete(2)
+ self.assertEqual(h[0:h.heap_size], [14, 3])
+ h.heap_delete(1)
+ self.assertEqual(h[0:h.heap_size], [14])
+ h.heap_delete(0)
+ self.assertEqual(h[0:h.heap_size], [])
+
+
+class TestMinPriorityQueue(unittest.TestCase):
+ def test_init(self):
+ a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
+ q = MinPriorityQueue(a)
+ self.assertEqual(q, [1, 2, 3, 4, 7, 8, 9, 10, 14, 16])
+
+ def test_heap_minimum(self):
+ a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
+ self.assertEqual(MinPriorityQueue(a).heap_minimum(), 1)
+
+ def test_heap_extract_min(self):
+ a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
+ q = MinPriorityQueue(a)
+ self.assertEqual(q.heap_extract_min(), 1)
+ self.assertEqual(q, [2, 4, 3, 10, 7, 8, 9, 16, 14, 16])
+
+ def test_heap_decrease_key(self):
+ a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
+ q = MinPriorityQueue(a)
+ q.heap_decrease_key(8, 1)
+ self.assertEqual(q, [1, 1, 3, 2, 7, 8, 9, 10, 4, 16])
+
+ def test_heap_insert(self):
+ a = [1, 10, 3, 2, 7, 8, 9, 4, 14, 16]
+ q = MinPriorityQueue(a)
+ q.heap_extract_min()
+ q.min_heap_insert(0)
+ self.assertEqual(q, [0, 2, 3, 10, 4, 8, 9, 16, 14, 7])
diff --git a/tests/quicksort_test.py b/tests/quicksort_test.py
new file mode 100644
index 0000000..0ebac67
--- /dev/null
+++ b/tests/quicksort_test.py
@@ -0,0 +1,34 @@
+import unittest
+from partition import partition, partition2, partition3
+import random
+from quicksort import quicksort, randomized_quicksort
+
+
+class TestQuickSort(unittest.TestCase):
+ def test_quicksort(self):
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ quicksort(array, 0, len(array) - 1, partition)
+ array_copy.sort()
+ self.assertEqual(array, array_copy)
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ quicksort(array, 0, len(array) - 1, partition2)
+ array_copy.sort()
+ self.assertEqual(array, array_copy)
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ quicksort(array, 0, len(array) - 1, partition3)
+ array_copy.sort()
+ self.assertEqual(array, array_copy)
+
+ def test_randomized_quicksort(self):
+ for _ in range(100):
+ array = [random.randint(1, 10000) for _ in range(100)]
+ array_copy = array[:]
+ randomized_quicksort(array, 0, len(array) - 1)
+ array_copy.sort()
+ self.assertEqual(array, array_copy)
diff --git a/randomized_select_test.py b/tests/randomized_select_test.py
similarity index 55%
rename from randomized_select_test.py
rename to tests/randomized_select_test.py
index 64b6d72..a500497 100644
--- a/randomized_select_test.py
+++ b/tests/randomized_select_test.py
@@ -1,12 +1,14 @@
import unittest
from randomized_select import randomized_select
+
class TestRandSelect(unittest.TestCase):
def test_randomize_select_distinct(self):
a = [10, 11, 5, 3, 2, 6, 0, 8, 100, 50]
- self.assertEquals(randomized_select(a, 0, 9, 5), 6)
+ self.assertEqual(randomized_select(a, 0, 9, 5), 6)
+
def test_randomize_select_duplicate(self):
a = [10, 11, 5, 8, 2, 6, 8, 8, 100, 50]
- self.assertEquals(randomized_select(a, 0, 9, 4), 8)
- self.assertEquals(randomized_select(a, 0, 9, 5), 8)
- self.assertEquals(randomized_select(a, 0, 9, 6), 8)
+ self.assertEqual(randomized_select(a, 0, 9, 4), 8)
+ self.assertEqual(randomized_select(a, 0, 9, 5), 8)
+ self.assertEqual(randomized_select(a, 0, 9, 6), 8)
diff --git a/rank_tree_test.py b/tests/rank_tree_test.py
similarity index 72%
rename from rank_tree_test.py
rename to tests/rank_tree_test.py
index 2aa547e..6c8c484 100755
--- a/rank_tree_test.py
+++ b/tests/rank_tree_test.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
from rank_tree import rank_tree, rank_node
@@ -6,50 +6,56 @@
class TestOstree(unittest.TestCase):
def test_insert_one(self):
T = rank_tree([41])
- print T.root.iterative_tree_search(41).p.key
- self.assertEquals(T.root, T.root.iterative_tree_search(41))
- self.assertEquals(T.nil.rank, 0)
+ print(T.root.iterative_tree_search(41).p.key)
+ self.assertEqual(T.root, T.root.iterative_tree_search(41))
+ self.assertEqual(T.nil.rank, 0)
self.wrap(T, 41, -1, -1, -1, 1, 1)
+
def test_insert_two(self):
T = rank_tree([41, 38])
- self.assertEquals(T.root, T.iterative_tree_search(41))
- self.assertEquals(T.nil.rank, 0)
+ self.assertEqual(T.root, T.iterative_tree_search(41))
+ self.assertEqual(T.nil.rank, 0)
self.wrap(T, 41, 38, -1, -1, 1, 2)
self.wrap(T, 38, -1, -1, 41, 0, 1)
+
def test_insert_three(self):
T = rank_tree([41, 38, 31])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.rank, 0)
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.rank, 0)
self.wrap(T, 38, 31, 41, -1, 1, 2)
self.wrap(T, 31, -1, -1, 38, 0, 1)
self.wrap(T, 41, -1, -1, 38, 0, 3)
+
def test_insert_four(self):
T = rank_tree([41, 38, 31, 12])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.rank, 0)
- self.wrap(T, 38, 31, 41, -1, 1, 3)
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.rank, 0)
+ self.wrap(T, 38, 31, 41, -1, 1, 3)
self.wrap(T, 31, 12, -1, 38, 1, 2)
self.wrap(T, 41, -1, -1, 38, 1, 4)
self.wrap(T, 12, -1, -1, 31, 0, 1)
+
def test_insert_five(self):
T = rank_tree([41, 38, 31, 12, 19])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.rank, 0)
- self.wrap(T, 38, 19, 41, -1, 1, 4)
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.rank, 0)
+ self.wrap(T, 38, 19, 41, -1, 1, 4)
self.wrap(T, 19, 12, 31, 38, 1, 2)
self.wrap(T, 41, -1, -1, 38, 1, 5)
self.wrap(T, 12, -1, -1, 19, 0, 1)
self.wrap(T, 31, -1, -1, 19, 0, 3)
+
def test_insert_six(self):
T = rank_tree([41, 38, 31, 12, 19, 9])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.rank, 0)
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.rank, 0)
self.wrap(T, 38, 19, 41, -1, 1, 5)
self.wrap(T, 19, 12, 31, 38, 0, 3)
self.wrap(T, 41, -1, -1, 38, 1, 6)
self.wrap(T, 12, 9, -1, 19, 1, 2)
self.wrap(T, 31, -1, -1, 19, 1, 4)
self.wrap(T, 9, -1, -1, 12, 0, 1)
+
def test_delete_one(self):
T = rank_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -58,6 +64,7 @@ def test_delete_one(self):
self.wrap(T, 41, -1, -1, 38, 1, 5)
self.wrap(T, 12, -1, -1, 19, 1, 1)
self.wrap(T, 31, -1, -1, 19, 1, 3)
+
def test_delete_two(self):
T = rank_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -66,6 +73,7 @@ def test_delete_two(self):
self.wrap(T, 19, -1, 31, 38, 1, 1)
self.wrap(T, 41, -1, -1, 38, 1, 4)
self.wrap(T, 31, -1, -1, 19, 0, 2)
+
def test_delete_three(self):
T = rank_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -74,6 +82,7 @@ def test_delete_three(self):
self.wrap(T, 38, 31, 41, -1, 1, 2)
self.wrap(T, 31, -1, -1, 38, 1, 1)
self.wrap(T, 41, -1, -1, 38, 1, 3)
+
def test_delete_four(self):
T = rank_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -82,6 +91,7 @@ def test_delete_four(self):
T.delete(T.iterative_tree_search(31))
self.wrap(T, 38, -1, 41, -1, 1, 1)
self.wrap(T, 41, -1, -1, 38, 0, 2)
+
def test_delete_five(self):
T = rank_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -90,6 +100,7 @@ def test_delete_five(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
self.wrap(T, 41, -1, -1, -1, 1, 1)
+
def test_delete_six(self):
T = rank_tree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
@@ -98,13 +109,19 @@ def test_delete_six(self):
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
T.delete(T.iterative_tree_search(41))
- self.assertEquals(T.root, T.nil)
- self.assertEquals(T.nil.rank, 0)
+ self.assertEqual(T.root, T.nil)
+ self.assertEqual(T.nil.rank, 0)
+
def wrap(self, tree, node, left, right, p, color, rank):
- self.assertEquals(tree.iterative_tree_search(node).left, tree.iterative_tree_search(left))
- self.assertEquals(tree.iterative_tree_search(node).right, tree.iterative_tree_search(right))
- self.assertEquals(tree.iterative_tree_search(node).p, tree.iterative_tree_search(p))
- self.assertEquals(tree.iterative_tree_search(node).color, color)
- self.assertEquals(tree.iterative_tree_search(node).rank, rank)
+ self.assertEqual(tree.iterative_tree_search(
+ node).left, tree.iterative_tree_search(left))
+ self.assertEqual(tree.iterative_tree_search(
+ node).right, tree.iterative_tree_search(right))
+ self.assertEqual(tree.iterative_tree_search(
+ node).p, tree.iterative_tree_search(p))
+ self.assertEqual(tree.iterative_tree_search(node).color, color)
+ self.assertEqual(tree.iterative_tree_search(node).rank, rank)
+
+
if __name__ == '__main__':
unittest.main()
diff --git a/rb_tree_test.py b/tests/rb_tree_test.py
similarity index 62%
rename from rb_tree_test.py
rename to tests/rb_tree_test.py
index 9efa1f6..36a6a58 100755
--- a/rb_tree_test.py
+++ b/tests/rb_tree_test.py
@@ -1,108 +1,125 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
-from rb_tree import rb_tree, rb_node
+from rb_tree import RbTree, RbNode
class TestRbtree(unittest.TestCase):
def test_insert_one(self):
- T = rb_tree([41])
- print T.root.iterative_tree_search(41).p.key
- self.assertEquals(T.root, T.root.iterative_tree_search(41))
- self.assertEquals(T.nil.color, 1)
+ T = RbTree([41])
+ print(T.root.iterative_tree_search(41).p.key)
+ self.assertEqual(T.root, T.root.iterative_tree_search(41))
+ self.assertEqual(T.nil.color, 1)
self.wrap(T, 41, -1, -1, -1, 1)
+
def test_insert_two(self):
- T = rb_tree([41, 38])
- self.assertEquals(T.root, T.iterative_tree_search(41))
- self.assertEquals(T.nil.color, 1)
+ T = RbTree([41, 38])
+ self.assertEqual(T.root, T.iterative_tree_search(41))
+ self.assertEqual(T.nil.color, 1)
self.wrap(T, 41, 38, -1, -1, 1)
self.wrap(T, 38, -1, -1, 41, 0)
+
def test_insert_three(self):
- T = rb_tree([41, 38, 31])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.color, 1)
+ T = RbTree([41, 38, 31])
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.color, 1)
self.wrap(T, 38, 31, 41, -1, 1)
self.wrap(T, 31, -1, -1, 38, 0)
self.wrap(T, 41, -1, -1, 38, 0)
+
def test_insert_four(self):
- T = rb_tree([41, 38, 31, 12])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.color, 1)
- self.wrap(T, 38, 31, 41, -1, 1)
+ T = RbTree([41, 38, 31, 12])
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.color, 1)
+ self.wrap(T, 38, 31, 41, -1, 1)
self.wrap(T, 31, 12, -1, 38, 1)
self.wrap(T, 41, -1, -1, 38, 1)
self.wrap(T, 12, -1, -1, 31, 0)
+
def test_insert_five(self):
- T = rb_tree([41, 38, 31, 12, 19])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.color, 1)
- self.wrap(T, 38, 19, 41, -1, 1)
+ T = RbTree([41, 38, 31, 12, 19])
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.color, 1)
+ self.wrap(T, 38, 19, 41, -1, 1)
self.wrap(T, 19, 12, 31, 38, 1)
self.wrap(T, 41, -1, -1, 38, 1)
self.wrap(T, 12, -1, -1, 19, 0)
self.wrap(T, 31, -1, -1, 19, 0)
+
def test_insert_six(self):
- T = rb_tree([41, 38, 31, 12, 19, 9])
- self.assertEquals(T.root, T.iterative_tree_search(38))
- self.assertEquals(T.nil.color, 1)
+ T = RbTree([41, 38, 31, 12, 19, 9])
+ self.assertEqual(T.root, T.iterative_tree_search(38))
+ self.assertEqual(T.nil.color, 1)
self.wrap(T, 38, 19, 41, -1, 1)
self.wrap(T, 19, 12, 31, 38, 0)
self.wrap(T, 41, -1, -1, 38, 1)
self.wrap(T, 12, 9, -1, 19, 1)
self.wrap(T, 31, -1, -1, 19, 1)
self.wrap(T, 9, -1, -1, 12, 0)
+
def test_delete_one(self):
- T = rb_tree([41, 38, 31, 12, 19, 9])
+ T = RbTree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
self.wrap(T, 38, 19, 41, -1, 1)
self.wrap(T, 19, 12, 31, 38, 0)
self.wrap(T, 41, -1, -1, 38, 1)
self.wrap(T, 12, -1, -1, 19, 1)
self.wrap(T, 31, -1, -1, 19, 1)
+
def test_delete_two(self):
- T = rb_tree([41, 38, 31, 12, 19, 9])
+ T = RbTree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
self.wrap(T, 38, 19, 41, -1, 1)
self.wrap(T, 19, -1, 31, 38, 1)
self.wrap(T, 41, -1, -1, 38, 1)
self.wrap(T, 31, -1, -1, 19, 0)
+
def test_delete_three(self):
- T = rb_tree([41, 38, 31, 12, 19, 9])
+ T = RbTree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
T.delete(T.iterative_tree_search(19))
self.wrap(T, 38, 31, 41, -1, 1)
self.wrap(T, 31, -1, -1, 38, 1)
self.wrap(T, 41, -1, -1, 38, 1)
+
def test_delete_four(self):
- T = rb_tree([41, 38, 31, 12, 19, 9])
+ T = RbTree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
T.delete(T.iterative_tree_search(19))
T.delete(T.iterative_tree_search(31))
self.wrap(T, 38, -1, 41, -1, 1)
self.wrap(T, 41, -1, -1, 38, 0)
+
def test_delete_five(self):
- T = rb_tree([41, 38, 31, 12, 19, 9])
+ T = RbTree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
T.delete(T.iterative_tree_search(19))
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
self.wrap(T, 41, -1, -1, -1, 1)
+
def test_delete_six(self):
- T = rb_tree([41, 38, 31, 12, 19, 9])
+ T = RbTree([41, 38, 31, 12, 19, 9])
T.delete(T.iterative_tree_search(9))
T.delete(T.iterative_tree_search(12))
T.delete(T.iterative_tree_search(19))
T.delete(T.iterative_tree_search(31))
T.delete(T.iterative_tree_search(38))
T.delete(T.iterative_tree_search(41))
- self.assertEquals(T.root, T.nil)
+ self.assertEqual(T.root, T.nil)
+
def wrap(self, tree, node, left, right, p, color):
- self.assertEquals(tree.iterative_tree_search(node).left, tree.iterative_tree_search(left))
- self.assertEquals(tree.iterative_tree_search(node).right, tree.iterative_tree_search(right))
- self.assertEquals(tree.iterative_tree_search(node).p, tree.iterative_tree_search(p))
- self.assertEquals(tree.iterative_tree_search(node).color, color)
+ self.assertEqual(tree.iterative_tree_search(
+ node).left, tree.iterative_tree_search(left))
+ self.assertEqual(tree.iterative_tree_search(
+ node).right, tree.iterative_tree_search(right))
+ self.assertEqual(tree.iterative_tree_search(
+ node).p, tree.iterative_tree_search(p))
+ self.assertEqual(tree.iterative_tree_search(node).color, color)
+
+
if __name__ == '__main__':
unittest.main()
diff --git a/tests/selection_sort_test.py b/tests/selection_sort_test.py
new file mode 100644
index 0000000..5f538a4
--- /dev/null
+++ b/tests/selection_sort_test.py
@@ -0,0 +1,14 @@
+#!/usr/bin/env python
+# encoding: utf-8
+
+import unittest
+from random_array import random_arrays
+from selection_sort import selection_sort
+
+
+class TestSelectionSort(unittest.TestCase):
+ def test_selection_sort(self):
+ for array in random_arrays():
+ sorted_array = sorted(array)
+ selection_sort(array)
+ self.assertEqual(array, sorted_array)
diff --git a/tests/test_binary_add.py b/tests/test_binary_add.py
new file mode 100644
index 0000000..2f9f1a6
--- /dev/null
+++ b/tests/test_binary_add.py
@@ -0,0 +1,9 @@
+from unittest import TestCase
+from binary_add import binary_add
+
+
+class Test(TestCase):
+ def test_binary_add(self):
+ array1 = [1, 0, 1, 0]
+ array2 = [0, 1, 1, 0]
+ self.assertEqual(binary_add(array1, array2), [1, 0, 0, 0, 0])
diff --git a/tests/test_deque.py b/tests/test_deque.py
new file mode 100644
index 0000000..e74d940
--- /dev/null
+++ b/tests/test_deque.py
@@ -0,0 +1,50 @@
+from unittest import TestCase
+
+from Queue import FullException, EmptyException
+from deque import Deque
+
+
+class TestDeque(TestCase):
+ def test_enqueue_tail_and_dequeue_head(self):
+ deque = Deque(3)
+ deque.enqueue_tail(1)
+ deque.enqueue_tail(2)
+ with self.assertRaises(FullException):
+ deque.enqueue_tail(3)
+ self.assertEqual(1, deque.dequeue_head())
+ self.assertEqual(2, deque.dequeue_head())
+ with self.assertRaises(EmptyException):
+ deque.dequeue_head()
+
+ def test_enqueue_head_and_dequeue_tail(self):
+ deque = Deque(3)
+ deque.enqueue_head(1)
+ deque.enqueue_head(2)
+ with self.assertRaises(FullException):
+ deque.enqueue_head(3)
+ self.assertEqual(1, deque.dequeue_tail())
+ self.assertEqual(2, deque.dequeue_tail())
+ with self.assertRaises(EmptyException):
+ deque.dequeue_tail()
+
+ def test_enqueue_tail_and_dequeue_tail(self):
+ deque = Deque(3)
+ deque.enqueue_tail(1)
+ deque.enqueue_tail(2)
+ self.assertEqual(2, deque.dequeue_tail())
+ self.assertEqual(1, deque.dequeue_tail())
+ with self.assertRaises(EmptyException):
+ deque.dequeue_tail()
+ with self.assertRaises(EmptyException):
+ deque.dequeue_head()
+
+ def test_enqueue_head_and_dequeue_head(self):
+ deque = Deque(3)
+ deque.enqueue_head(1)
+ deque.enqueue_head(2)
+ self.assertEqual(2, deque.dequeue_head())
+ self.assertEqual(1, deque.dequeue_head())
+ with self.assertRaises(EmptyException):
+ deque.dequeue_tail()
+ with self.assertRaises(EmptyException):
+ deque.dequeue_head()
diff --git a/tests/test_dynamic_array.py b/tests/test_dynamic_array.py
new file mode 100644
index 0000000..194f7fa
--- /dev/null
+++ b/tests/test_dynamic_array.py
@@ -0,0 +1,15 @@
+from unittest import TestCase
+from dynamic_array import DynamicArray
+
+
+class TestDynamicArray(TestCase):
+ def test_add_and_get_and_size(self):
+ dynamic_array = DynamicArray(2)
+ self.assertEqual(0, dynamic_array.size())
+ dynamic_array.add(1)
+ dynamic_array.add(2)
+ dynamic_array.add(3)
+ self.assertEqual(3, dynamic_array.size())
+ self.assertEqual(1, dynamic_array.get(0))
+ self.assertEqual(2, dynamic_array.get(1))
+ self.assertEqual(3, dynamic_array.get(2))
diff --git a/tests/test_euclid.py b/tests/test_euclid.py
new file mode 100644
index 0000000..0c7909c
--- /dev/null
+++ b/tests/test_euclid.py
@@ -0,0 +1,13 @@
+#!/usr/bin/env python
+# encoding: utf-8
+from unittest import TestCase
+
+from euclid import euclid
+
+
+class TestEuclid(TestCase):
+ def test_gcd(self):
+ self.assertEqual(euclid(10, 3), 1)
+ self.assertEqual(euclid(10, 4), 2)
+ self.assertEqual(euclid(10, 1), 1)
+ self.assertEqual(euclid(10, 5), 5)
diff --git a/tests/test_gcd.py b/tests/test_gcd.py
new file mode 100644
index 0000000..8a2d9f2
--- /dev/null
+++ b/tests/test_gcd.py
@@ -0,0 +1,13 @@
+#!/usr/bin/env python
+# encoding: utf-8
+from unittest import TestCase
+
+from gcd import gcd
+
+
+class TestGcd(TestCase):
+ def test_gcd(self):
+ self.assertEqual(gcd(10, 3), 1)
+ self.assertEqual(gcd(10, 4), 2)
+ self.assertEqual(gcd(10, 1), 1)
+ self.assertEqual(gcd(10, 5), 5)
diff --git a/tests/test_lowest_common_multiple.py b/tests/test_lowest_common_multiple.py
new file mode 100644
index 0000000..ed59060
--- /dev/null
+++ b/tests/test_lowest_common_multiple.py
@@ -0,0 +1,9 @@
+from unittest import TestCase
+from lowest_common_multiple import lcm
+
+
+class LcmTest(TestCase):
+ def test_lcm(self):
+ self.assertEqual(lcm(10, 1), 10)
+ self.assertEqual(lcm(10, 8), 40)
+ self.assertEqual(lcm(15, 9), 45)
diff --git a/tests/test_merge.py b/tests/test_merge.py
new file mode 100644
index 0000000..18881b8
--- /dev/null
+++ b/tests/test_merge.py
@@ -0,0 +1,25 @@
+from unittest import TestCase
+from merge import merge_without_sentinel, merge_with_sentinel
+from random_array import random_arrays
+
+
+class MergeTest(TestCase):
+ def test_merge_with_sentinel(self):
+ for array in random_arrays():
+ left_array = array[:len(array) // 2]
+ right_array = array[len(array) // 2:]
+ left_array.sort()
+ right_array.sort()
+ result_array = left_array + right_array
+ merge_with_sentinel(result_array, 0, len(array) // 2 - 1, len(array) - 1)
+ self.assertEqual(result_array, sorted(array))
+
+ def test_merge_without_sentinel(self):
+ for array in random_arrays():
+ left_array = array[:len(array) // 2]
+ right_array = array[len(array) // 2:]
+ left_array.sort()
+ right_array.sort()
+ result_array = left_array + right_array
+ merge_without_sentinel(result_array, 0, len(array) // 2 - 1, len(array) - 1)
+ self.assertEqual(result_array, sorted(array))
diff --git a/tests/test_pow.py b/tests/test_pow.py
new file mode 100644
index 0000000..48d87b0
--- /dev/null
+++ b/tests/test_pow.py
@@ -0,0 +1,16 @@
+import math
+import random
+from unittest import TestCase
+from pow import pow1, pow2
+
+
+class Test(TestCase):
+ def test_pow1(self):
+ x = random.randint(1, 10)
+ for n in range(10):
+ self.assertEqual(pow1(x, n), math.pow(x, n))
+
+ def test_pow2(self):
+ x = random.randint(1, 10)
+ for n in range(10):
+ self.assertEqual(pow2(x, n), math.pow(x, n))
diff --git a/tests/test_queue.py b/tests/test_queue.py
new file mode 100644
index 0000000..c8eb359
--- /dev/null
+++ b/tests/test_queue.py
@@ -0,0 +1,30 @@
+from unittest import TestCase
+from Queue import Queue, EmptyException, FullException
+
+
+class TestQueue(TestCase):
+ def test_enqueue_and_dequeue(self):
+ queue = Queue(3)
+ queue.enqueue(1)
+ queue.enqueue(2)
+ with self.assertRaises(FullException):
+ queue.enqueue(3)
+ self.assertEqual(1, queue.dequeue())
+ self.assertEqual(2, queue.dequeue())
+ with self.assertRaises(EmptyException):
+ queue.dequeue()
+
+ def test_empty(self):
+ queue = Queue(2)
+ self.assertTrue(queue.empty())
+
+ def test_full(self):
+ queue = Queue(2)
+ queue.enqueue(1)
+ self.assertTrue(queue.full())
+ queue = Queue(1)
+ self.assertTrue(queue.full())
+
+ def test_capacity(self):
+ queue = Queue(5)
+ self.assertEqual(4, queue.capacity())
diff --git a/tests/two_sum_test.py b/tests/two_sum_test.py
new file mode 100644
index 0000000..415afac
--- /dev/null
+++ b/tests/two_sum_test.py
@@ -0,0 +1,17 @@
+import unittest
+from random_array import random_arrays
+import random
+from two_sum import two_sum
+
+
+class TestInsertionSort(unittest.TestCase):
+ def test_two_sum(self):
+ for array in random_arrays(array_num=1000, array_size=10, array_lowerbound=1, array_upperbound=20):
+ x = random.randint(1, 100)
+ n = len(array)
+ result = False
+ for i in range(n):
+ for j in range(i + 1, n):
+ if array[i] + array[j] == x:
+ result = True
+ self.assertEqual(two_sum(x, array), result)
diff --git a/tests/universal_sink_test.py b/tests/universal_sink_test.py
new file mode 100644
index 0000000..5d7a11e
--- /dev/null
+++ b/tests/universal_sink_test.py
@@ -0,0 +1,31 @@
+import universal_sink as us
+import unittest
+import numpy
+
+
+class TestRbtree(unittest.TestCase):
+ def test_universal_sink(self):
+ data = numpy.array(
+ [[0, 0, 0, 0, 0, 0], [1, 0, 0, 0, 1, 0], [1, 0, 0, 0, 1, 1], [1, 1, 0, 0, 0, 0], [1, 0, 0, 1, 0, 0],
+ [1, 0, 0, 0, 0, 1]])
+ self.assertEqual(us.universal_sink(data), 1)
+ data = numpy.array(
+ [[0, 1, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0], [1, 1, 0, 0, 1, 1], [1, 1, 0, 0, 0, 0], [1, 1, 0, 1, 0, 0],
+ [1, 1, 0, 0, 0, 1]])
+ self.assertEqual(us.universal_sink(data), 2)
+ data = numpy.array(
+ [[0, 1, 1, 0, 0, 0], [0, 0, 1, 0, 0, 0], [0, 0, 0, 0, 0, 0], [1, 1, 1, 0, 0, 0], [1, 1, 1, 1, 0, 0],
+ [1, 1, 1, 0, 0, 1]])
+ self.assertEqual(us.universal_sink(data), 3)
+ data = numpy.array(
+ [[0, 1, 0, 1, 0, 0], [0, 0, 0, 1, 1, 0], [0, 0, 0, 1, 1, 1], [0, 0, 0, 0, 0, 0], [0, 0, 0, 1, 0, 0],
+ [0, 0, 0, 1, 0, 1]])
+ self.assertEqual(us.universal_sink(data), 4)
+ data = numpy.array(
+ [[0, 1, 1, 0, 1, 0], [0, 0, 1, 0, 1, 0], [0, 0, 0, 0, 1, 0], [1, 1, 1, 0, 1, 0], [0, 0, 0, 0, 0, 0],
+ [1, 1, 1, 0, 1, 1]])
+ self.assertEqual(us.universal_sink(data), 5)
+ data = numpy.array(
+ [[0, 1, 1, 0, 1, 1], [0, 0, 1, 0, 1, 1], [0, 0, 0, 0, 1, 1], [1, 1, 1, 0, 1, 1], [0, 0, 0, 0, 0, 1],
+ [0, 0, 0, 0, 0, 0]])
+ self.assertEqual(us.universal_sink(data), 6)
diff --git a/vEB_tree_test.py b/tests/vEB_tree_test.py
similarity index 51%
rename from vEB_tree_test.py
rename to tests/vEB_tree_test.py
index ec3dbc9..a1fb46e 100644
--- a/vEB_tree_test.py
+++ b/tests/vEB_tree_test.py
@@ -1,8 +1,9 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
from vEB_tree import vEB_node
+
class testVEB(unittest.TestCase):
def test_vEB(self):
v = vEB_node(2 ** 8)
@@ -10,10 +11,10 @@ def test_vEB(self):
for i in l:
v.insert(i)
for i in l:
- self.assertEquals(v.member(i), True)
- self.assertEquals(v.member(2), False)
- self.assertEquals(v.member(3), False)
+ self.assertEqual(v.member(i), True)
+ self.assertEqual(v.member(2), False)
+ self.assertEqual(v.member(3), False)
v.delete(1)
- self.assertEquals(v.member(1), False)
+ self.assertEqual(v.member(1), False)
v.delete(100)
- self.assertEquals(v.member(100), False)
+ self.assertEqual(v.member(100), False)
diff --git a/wrestlers_test.py b/tests/wrestlers_test.py
similarity index 57%
rename from wrestlers_test.py
rename to tests/wrestlers_test.py
index 78cf83c..a3fa9d1 100644
--- a/wrestlers_test.py
+++ b/tests/wrestlers_test.py
@@ -1,13 +1,17 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import unittest
from wrestlers import wrestlers
+
class TestWrestler(unittest.TestCase):
def testBfs(self):
wrestlersList = [1, 2, 3, 4, 5, 6, 7, 8]
- rivalriesList = [(1, 2), (1, 3), (2, 4), (3, 5), (3, 6), (5, 6), (5, 7), (5, 8), (6, 8), (7, 8)]
+ rivalriesList = [(1, 2), (1, 3), (2, 4), (3, 5), (3, 6),
+ (5, 6), (5, 7), (5, 8), (6, 8), (7, 8)]
self.assertEqual(wrestlers(wrestlersList, rivalriesList), False)
- rivalriesList = [(1, 2), (1, 3), (2, 4), (3, 5), (3, 6), (5, 7), (5, 8), (6, 8), (7, 8)]
+ rivalriesList = [(1, 2), (1, 3), (2, 4), (3, 5),
+ (3, 6), (5, 7), (5, 8), (6, 8), (7, 8)]
self.assertEqual(wrestlers(wrestlersList, rivalriesList), False)
- rivalriesList = [(1, 2), (1, 3), (2, 4), (3, 5), (3, 6), (5, 7), (5, 8), (6, 8)]
+ rivalriesList = [(1, 2), (1, 3), (2, 4), (3, 5),
+ (3, 6), (5, 7), (5, 8), (6, 8)]
self.assertEqual(wrestlers(wrestlersList, rivalriesList), True)
diff --git a/three_points_colinear.py b/three_points_colinear.py
index f1ebe7a..dd87706 100644
--- a/three_points_colinear.py
+++ b/three_points_colinear.py
@@ -1,10 +1,11 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-from heap import max_heap
+from heap import MaxHeap
-class vector(object):
- def __init__(self, p1, p2, p1_index = 0, p2_index = 0):
- # gurantee that the polar angle of this vector with respect to the origin point is in the range [0, pi)
+
+class vector:
+ def __init__(self, p1, p2, p1_index=0, p2_index=0):
+ # gurantee that the polar angle of this Vector with respect to the origin point is in the range [0, pi)
if p1[1] > p2[1]:
self.x = p1[0] - p2[0]
self.y = p1[1] - p2[1]
@@ -18,28 +19,35 @@ def __init__(self, p1, p2, p1_index = 0, p2_index = 0):
self.p2 = p2
self.p1_index = p1_index
self.p2_index = p2_index
+
def cross_product(self, v):
return self.x * v.y - v.x * self.y
+
def __lt__(self, v):
return self.cross_product(v) > 0
+
def __gt__(self, v):
return self.cross_product(v) < 0
+
def __eq__(self, v):
return self.cross_product(v) == 0
+
def __le__(self, v):
return self.cross_product(v) >= 0
+
def __ge__(self, v):
return self.cross_product(v) <= 0
+
def three_points_colinear(points_list):
- '''An algorithm to determine whether any three points in a set of n points are colinear'''
+ """ to determine whether any three points in a set of n points are colinear"""
n = len(points_list)
vectors_list = []
- for i in range(0, n):
+ for i in range(n):
for j in range(i + 1, n):
vectors_list.append(vector(points_list[i], points_list[j], i, j))
v0 = vector((1, 0), (0, 0))
- heap_vectors = max_heap(vectors_list)
+ heap_vectors = MaxHeap(vectors_list)
heap_vectors.heapsort()
status = [False] * n
v = heap_vectors[0]
@@ -61,9 +69,9 @@ def three_points_colinear(points_list):
stack.append(v.p1_index)
stack.append(v.p2_index)
else:
- print len(stack)
- print stack
- for i in range(0, len(stack)):
+ print(len(stack))
+ print(stack)
+ for i in range(len(stack)):
status[stack.pop()] = False
stack.append(v.p1_index)
stack.append(v.p2_index)
diff --git a/three_sum.py b/three_sum.py
index 4fec1d0..6387f4a 100644
--- a/three_sum.py
+++ b/three_sum.py
@@ -1,23 +1,23 @@
#!/usr/bin/env python
# coding=utf-8
-def threeSum(A):
- '''Given an array A of n integers, find one triplet
+
+def three_sum(array):
+ """
+ Given an array `array` of n integers, find one triplet
in the array which gives the sum of zero.
- A must be in increasing order'''
- n = len(A)
+ `array` must be in increasing order
+ """
+ n = len(array)
for i in range(n - 2):
j = i + 1
k = n - 1
while k >= j:
- if A[i] + A[j] + A[k] == 0:
- return (A[i], A[j], A[k])
- elif A[i] + A[j] + A[k] > 0:
+ if array[i] + array[j] + array[k] == 0:
+ return array[i], array[j], array[k]
+ elif array[i] + array[j] + array[k] > 0:
k = k - 1
else:
j = j + 1
-
-
-
diff --git a/tree.py b/tree.py
index 07327b6..deedc02 100755
--- a/tree.py
+++ b/tree.py
@@ -1,123 +1,139 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
-import random
-class Node(object):
+class Node:
def __init__(self, key, p, left, right):
self.key = key
self.p = p
self.left = left
self.right = right
+
def inorder_tree_walk(self):
- if self.left != None:
- self.left.inorder_tree_walk()
- print self.key,
- if self.right != None:
- self.right.inorder_tree_walk()
+ if self.left is not None:
+ self.left.inorder_tree_walk()
+ print(self.key, )
+ if self.right is not None:
+ self.right.inorder_tree_walk()
+
def preorder_tree_walk(self):
- print self.key,
- if self.left != None:
- self.left.preorder_tree_walk()
- if self.right != None:
- self.right.preorder_tree_walk()
+ print(self.key, )
+ if self.left is not None:
+ self.left.preorder_tree_walk()
+ if self.right is not None:
+ self.right.preorder_tree_walk()
+
def postorder_tree_walk(self):
- if self.left != None:
- self.left.postorder_tree_walk()
- if self.right != None:
- self.right.postorder_tree_walk()
- print self.key,
+ if self.left is not None:
+ self.left.postorder_tree_walk()
+ if self.right is not None:
+ self.right.postorder_tree_walk()
+ print(self.key, )
+
def inorder_tree_walk_stack(self):
- s = []
- s.append({"data": self, "status": 0})
+ s = [{"data": self, "status": 0}]
while len(s) != 0:
record = s.pop()
if record["status"] == 0:
x = record["data"]
- if x.right != None:
+ if x.right is not None:
s.append({"data": x.right, "status": 0})
s.append({"data": x, "status": 1})
- if x.left != None:
+ if x.left is not None:
s.append({"data": x.left, "status": 0})
else:
- print record["data"].key,
- print
+ print(record["data"].key, )
+ print()
+
def iterative_tree_search(self, k):
x = self
- while x != None and x.key != k:
+ while x is not None and x.key != k:
if x.key < k:
x = x.right
else:
x = x.left
return x
+
def minimum(self):
x = self
- while x.left != None:
+ while x.left is not None:
x = x.left
return x
+
def maximum(self):
x = self
- while x.right != None:
+ while x.right is not None:
x = x.right
return x
+
def successor(self):
x = self
- if x.right != None:
+ if x.right is not None:
return x.right.minimum()
else:
- while x.p != None and x.p.right == x:
+ while x.p is not None and x.p.right == x:
x = x.p
return x.p
+
def predecessor(self):
x = self
- if x.left != None:
+ if x.left is not None:
return x.left.maximum()
else:
- while x.p != None and x.p.left == x:
+ while x.p is not None and x.p.left == x:
x = x.p
return x.p
-class Tree(object):
+
+
+class Tree:
root = None
+
def __init__(self, values):
if isinstance(values, list):
for i in values:
self.insert(Node(i, None, None, None))
else:
- print "Not invalid argument"
+ print("Not invalid argument")
+
def minimum(self):
return self.root.minimum()
+
def __getitem__(self, key):
return self.root.iterative_tree_search(key)
+
def insert(self, node):
y = None
x = self.root
- while x != None:
+ while x is not None:
y = x
if node.key <= x.key:
x = x.left
else:
x = x.right
node.p = y
- if y == None:
+ if y is None:
self.root = node
elif node.key <= y.key:
y.left = node
else:
y.right = node
+
def iterative_tree_search(self, k):
pass
+
def transplant(self, u, v):
- if u.p == None:
+ if u.p is None:
self.root = v
elif u == u.p.left:
u.p.left = v
else:
u.p.right = v
- if v != None:
+ if v is not None:
v.p = u.p
+
def delete(self, z):
- if z.left == None:
+ if z.left is None:
self.transplant(z, z.right)
- elif z.right == None:
+ elif z.right is None:
self.transplant(z, z.left)
else:
y = z.right.minimum()
@@ -128,31 +144,33 @@ def delete(self, z):
self.transplant(z, y)
y.left = z.left
y.left.p = y
-#A = [random.randint(1, 100) for i in range(0, 15)]
-#A = [29, 81, 53, 51, 28, 31, 57, 30, 22, 62, 6, 50, 7, 2, 24, 55, 54, 56, 98]
-#print A
-#T = Tree(A)
-#T.delete(T.root.iterative_tree_search(57))
-#T.delete(T.root.iterative_tree_search(81))
-#T.root.postorder_tree_walk()
-#print "maximum: %d" % (T.root.maximum().key)
-#inorder_tree_walk_stack(T.root)
-#T.root.inorder_tree_walk_stack()
-#T.root.inorder_tree_walk()
-print
-#T.root.preorder_tree_walk()
-print
-#T.root.postorder_tree_walk()
-#x = T.root.iterative_tree_search(50)
-#if x == None:
-# print "None"
-#else:
-# print x.key
-#print T.root.mimimum().key
+
+
+# A = [random.randint(1, 100) for i in range(15)]
+# A = [29, 81, 53, 51, 28, 31, 57, 30, 22, 62, 6, 50, 7, 2, 24, 55, 54, 56, 98]
+# print( A)
+# T = Tree(A)
+# T.delete(T.root.iterative_tree_search(57))
+# T.delete(T.root.iterative_tree_search(81))
+# T.root.postorder_tree_walk()
+# print( "maximum: %d" % (T.root.maximum().key))
+# inorder_tree_walk_stack(T.root)
+# T.root.inorder_tree_walk_stack()
+# T.root.inorder_tree_walk()
+# print()
+# T.root.preorder_tree_walk()
+# print()
+# T.root.postorder_tree_walk()
+# x = T.root.iterative_tree_search(50)
+# if x is None:
+# print( "None")
+# else:
+# print( x.key)
+# print( T.root.mimimum().key)
#
-#su = T.root.successor()
-#if su:
-# print su.key
-#pr = T.root.predecessor()
-#if pr:
-# print "predecessor of root is %d " % (pr.key)
+# su = T.root.successor()
+# if su:
+# print( su.key)
+# pr = T.root.predecessor()
+# if pr:
+# print( "predecessor of root is %d " % (pr.key))
diff --git a/two_sum.py b/two_sum.py
new file mode 100644
index 0000000..cb906c6
--- /dev/null
+++ b/two_sum.py
@@ -0,0 +1,20 @@
+def two_sum(x: int, array: list):
+ """
+ an algorithm that, given a set S of n integers and another integer x,
+ determines whether or not there exist two elements in S whose sum is exactly x.
+ :param x:
+ :param array:
+ :return:
+ """
+ sorted_array = sorted(array)
+ i = 0
+ j = len(array) - 1
+ while i < j:
+ sum = sorted_array[i] + sorted_array[j]
+ if sum == x:
+ return True
+ elif sum < x:
+ i = i + 1
+ else:
+ j = j - 1
+ return False
diff --git a/universal_sink.py b/universal_sink.py
index 1aab58a..2768126 100644
--- a/universal_sink.py
+++ b/universal_sink.py
@@ -1,22 +1,24 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
+
def universal_sink(M):
- '''
+ """
An algorithm to determine whether a directed graph G contains
a universal sink---a vertex with in-degree |V| - 1 and
out-degree 0---in time O(V), given an adjacency matrix for G
-
+
M: numpy matrix, the adjacency matrix for the graph
rtype: vertex index if G contains a universal sink, otherwise, return None
- '''
+ """
return universal_sink_aux(M, 1)
+
def universal_sink_aux(M, i):
- '''
+ """
M: numpy matrix
i: vertex index
- '''
+ """
size = M.shape[0]
j = i
while True:
@@ -30,6 +32,6 @@ def universal_sink_aux(M, i):
for j in range(1, size + 1):
if M[j - 1][i - 1] == 0 and j != i:
return None
- return i
+ return i
else:
return universal_sink_aux(M, j)
diff --git a/universal_sink_test.py b/universal_sink_test.py
deleted file mode 100644
index de46f8a..0000000
--- a/universal_sink_test.py
+++ /dev/null
@@ -1,18 +0,0 @@
-import universal_sink as us
-import unittest
-import numpy
-
-class TestRbtree(unittest.TestCase):
- def test_universal_sink(self):
- data = numpy.array([[0, 0, 0, 0, 0, 0], [1, 0, 0, 0, 1, 0], [1, 0, 0, 0, 1, 1], [1, 1, 0, 0, 0, 0], [1, 0, 0, 1, 0, 0], [1, 0, 0, 0, 0, 1]])
- self.assertEquals(us.universal_sink(data), 1)
- data = numpy.array([[0, 1, 0, 0, 0, 0], [0, 0, 0, 0, 0, 0], [1, 1, 0, 0, 1, 1], [1, 1, 0, 0, 0, 0], [1, 1, 0, 1, 0, 0], [1, 1, 0, 0, 0, 1]])
- self.assertEquals(us.universal_sink(data), 2)
- data = numpy.array([[0, 1, 1, 0, 0, 0], [0, 0, 1, 0, 0, 0], [0, 0, 0, 0, 0, 0], [1, 1, 1, 0, 0, 0], [1, 1, 1, 1, 0, 0], [1, 1, 1, 0, 0, 1]])
- self.assertEquals(us.universal_sink(data), 3)
- data = numpy.array([[0, 1, 0, 1, 0, 0], [0, 0, 0, 1, 1, 0], [0, 0, 0, 1, 1, 1], [0, 0, 0, 0, 0, 0], [0, 0, 0, 1, 0, 0], [0, 0, 0, 1, 0, 1]])
- self.assertEquals(us.universal_sink(data), 4)
- data = numpy.array([[0, 1, 1, 0, 1, 0], [0, 0, 1, 0, 1, 0], [0, 0, 0, 0, 1, 0], [1, 1, 1, 0, 1, 0], [0, 0, 0, 0, 0, 0], [1, 1, 1, 0, 1, 1]])
- self.assertEquals(us.universal_sink(data), 5)
- data = numpy.array([[0, 1, 1, 0, 1, 1], [0, 0, 1, 0, 1, 1], [0, 0, 0, 0, 1, 1], [1, 1, 1, 0, 1, 1], [0, 0, 0, 0, 0, 1], [0, 0, 0, 0, 0, 0]])
- self.assertEquals(us.universal_sink(data), 6)
diff --git a/vEB_tree.py b/vEB_tree.py
index 08ab25c..de193fb 100644
--- a/vEB_tree.py
+++ b/vEB_tree.py
@@ -1,10 +1,11 @@
-#!/usr/bin/env ipython
+#!/usr/bin/env python
import math
-class vEB_node(object):
+
+class vEB_node:
def __init__(self, u):
- '''u must be exact power of 2, as required by CLRS; otherwise, the behavior is undefined'''
+ """u must be exact power of 2, as required by CLRS; otherwise, the behavior is undefined"""
self.u = u
self.min = None
self.max = None
@@ -12,14 +13,18 @@ def __init__(self, u):
self.root = int(math.sqrt(u))
self.cluster = [0] * self.root
self.summary = vEB_node(self.root)
- for i in range(0, self.root):
+ for i in range(self.root):
self.cluster[i] = vEB_node(self.root)
+
def high(self, x):
- return x / self.root
+ return x // self.root
+
def low(self, x):
return x % self.root
+
def index(self, x, y):
return x * self.root + y
+
def member(self, x):
if self.min == x or self.max == x:
return True
@@ -27,49 +32,53 @@ def member(self, x):
return False
else:
return self.cluster[self.high(x)].member(self.low(x))
+
def successor(self, x):
if self.u == 2:
if x == 0 and self.max == 1:
return 1
else:
return None
- elif self.min != None and x < self.min:
+ elif self.min is not None and x < self.min:
return self.min
else:
max_low = self.cluster[self.high(x)].max
- if max_low != None and self.low(x) < max_low:
+ if max_low is not None and self.low(x) < max_low:
offset = self.cluster[self.high(x)].successor(self.low(x))
return self.index(self.high(x), offset)
else:
succ_cluster = self.summary.successor(self.high(x))
- if succ_cluster == None:
+ if succ_cluster is None:
return None
else:
offset = self.cluster[succ_cluster].min
return self.index(succ_cluster, offset)
+
def empty_tree_insert(self, x):
self.min = x
self.max = x
+
def insert(self, x):
- if self.min == None:
+ if self.min is None:
self.empty_tree_insert(x)
elif (x == self.min) or (x == self.max):
return
else:
if x < self.min:
- x,self.min = self.min,x
+ x, self.min = self.min, x
if self.u > 2:
- if self.cluster[self.high(x)].min == None:
+ if self.cluster[self.high(x)].min is None:
self.summary.insert(self.high(x))
self.cluster[self.high(x)].empty_tree_insert(self.low(x))
else:
self.cluster[self.high(x)].insert(self.low(x))
if x > self.max:
self.max = x
+
def delete(self, x):
-# print "u = {}, x = {}".format(self.u, x)
+ # print( "u = {}, x = {}".format(self.u, x))
if self.min == self.max:
- # print "min = {}, max = {}".format(self.min, self.max)
+ # print( "min = {}, max = {}".format(self.min, self.max))
if x == self.min:
self.min = None
self.max = None
@@ -86,24 +95,29 @@ def delete(self, x):
x = self.index(first_cluster, self.cluster[first_cluster].min)
self.min = x
self.cluster[self.high(x)].delete(self.low(x))
- if self.cluster[self.high(x)].min == None:
+ if self.cluster[self.high(x)].min is None:
self.summary.delete(self.high(x))
if x == self.max:
summary_max = self.summary.max
- if summary_max == None:
+ if summary_max is None:
self.max = self.min
else:
- self.max = self.index(summary_max, self.cluster[summary_max].max)
+ self.max = self.index(
+ summary_max, self.cluster[summary_max].max)
elif x == self.max:
- self.max = self.index(self.high(x), self.cluster[self.high(x)].max)
+ self.max = self.index(
+ self.high(x), self.cluster[self.high(x)].max)
+
def print_veb(self):
if self.u == 2:
- print "u = {}, min = {}, max = {}".format(self.u, self.min, self.max)
+ print("u = {}, min = {}, max = {}".format(
+ self.u, self.min, self.max))
else:
- print "u = {}, min = {}, max = {}".format(self.u, self.min, self.max)
- print "Summary: \t",
+ print("u = {}, min = {}, max = {}".format(
+ self.u, self.min, self.max))
+ print("Summary: \t", )
self.summary.print_veb()
- print
- for i in range(0, self.root):
+ print()
+ for i in range(self.root):
self.cluster[i].print_veb()
- print
+ print()
diff --git a/wrestlers.py b/wrestlers.py
index 19d1d2c..fca182c 100644
--- a/wrestlers.py
+++ b/wrestlers.py
@@ -1,8 +1,9 @@
-from queue import queue
+from queue import Queue
from graph import Graph, Vertex
+
def wrestlers(wrestlersList, rivalriesList):
- '''
+ """
There are two types of professional wrestlers: "babyfaces"
("good guys") and "heels" ("bad guys"). Between any pair of
professional wrestlers, there may or may not be a rivalry.
@@ -11,7 +12,7 @@ def wrestlers(wrestlersList, rivalriesList):
possible to designate some of the wrestlers as babyfaces and There
remainder as heels such that each rivalry is between a babyfaces
and a heel.
- '''
+ """
d = dict()
vertices = [None] * len(wrestlersList)
edges = [None] * len(rivalriesList)
@@ -28,16 +29,17 @@ def wrestlers(wrestlersList, rivalriesList):
u.type = 0
for u in g.vertices:
if u.type == 0:
- if _bfs(g, u) == False:
+ if not _bfs(g, u):
return False
return True
+
def _bfs(g, s):
s.type = 1
- q = queue(2 * len(g.vertices))
- q.enqueue(s)
+ q = Queue(2 * len(g.vertices))
+ q.put(s)
while not q.empty():
- u = q.dequeue()
+ u = q.get()
for v in g.adj[u]:
if u.type == v.type:
return False
@@ -46,5 +48,5 @@ def _bfs(g, s):
v.type = 2
else:
v.type = 1
- q.enqueue(v)
+ q.put(v)
return True