forked from stanleybak/nn_fairness
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathvolume_test.py
133 lines (95 loc) · 3.65 KB
/
volume_test.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
# pip3 install polytope
import time
import numpy as np
from scipy.spatial import ConvexHull
from polytope import Polytope, extreme
from compute_volume import quad_integrate_polytope, rand_integrate_polytope
def test_2d_volume():
"""test 2d volume"""
# x >= -1
# y >= 0
# x + y <= 1
# corners should be (-1,0), (1, 0), (-1, 2)
# volume should be 2.0
A = np.array([[0, -1], [-1, 0], [1, 1]], dtype=float)
b = np.array([1, 0, 1], dtype=float)
start = time.perf_counter()
poly = Polytope(A, b)
vertices = extreme(poly)
hull = ConvexHull(vertices)
qhull_time = time.perf_counter() - start
print(f"qhull volume: {hull.volume}; time: {round(qhull_time * 1000, 3)}ms")
start = time.perf_counter()
v = quad_integrate_polytope(A, b)
quad_time = time.perf_counter() - start
print(f"quad volume: {v}; time: {round(quad_time * 1000, 3)}ms")
# test random
for samples in [1000, 10000, 100000]:
start = time.perf_counter()
rand_vol = rand_integrate_polytope(A, b, samples=samples)
rand_time = time.perf_counter() - start
print(f"with {samples} rand samples, volume: {rand_vol}; time: {round(rand_time * 1000, 3)}ms")
def test_4d_volume():
"""test 4d volume"""
# x >= -1
# y >= 0
# z >= 0
# w >= 0
# x + y <= 1
# x + 2y + z <= 1
# 2*x + 2*y + 2*z + w <= 1
A = np.array([[0, -1, 0, 0], [-1, 0, 0, 0], [0, 0, -1, 0], [0, 0, 0, -1],
[1, 1, 0, 0], [1, 2, 1, 0], [2, 2, 2, 1]], dtype=float)
b = np.array([1, 0, 0, 0, 1, 1, 1], dtype=float)
start = time.perf_counter()
poly = Polytope(A, b)
vertices = extreme(poly)
hull = ConvexHull(vertices)
qhull_time = time.perf_counter() - start
print(f"qhull volume: {hull.volume}; time: {round(qhull_time * 1000, 3)}ms")
start = time.perf_counter()
quad_vol = quad_integrate_polytope(A, b)
quad_time = time.perf_counter() - start
print(f"quad volume: {quad_vol}; time: {round(quad_time * 1000, 3)}ms")
# test random
for samples in [1000, 10000, 100000]:
start = time.perf_counter()
rand_vol = rand_integrate_polytope(A, b, samples=samples)
rand_time = time.perf_counter() - start
print(f"with {samples} rand samples, volume: {rand_vol}; time: {round(rand_time * 1000, 3)}ms")
def test_4d_integrate():
"""test 4d integrate. same as volume but doing f(x,y,z,w) = 1 + x*2y*2z*w"""
# x >= -1
# y >= 0
# z >= 0
# w >= 0
# x + y <= 1
# x + 2y + z <= 1
# x + y + z + w <= 1
A = np.array([[0, -1, 0, 0], [-1, 0, 0, 0], [0, 0, -1, 0], [0, 0, 0, -1],
[1, 1, 0, 0], [1, 2, 1, 0], [1, 1, 1, 1]], dtype=float)
b = np.array([1, 0, 0, 0, 1, 1, 1], dtype=float)
def integ_func(x, y, z, w):
"""function to be integrated over polytope domain"""
#print(x)
return 1+ x * 2*y + 2*z * w
start = time.perf_counter()
v = quad_integrate_polytope(A, b, integ_func)
quad_time = time.perf_counter() - start
print(f"quad volume: {v}; time: {round(quad_time * 1000, 3)}ms")
# test random
for samples in [1e3, 1e4, 1e5]:
start = time.perf_counter()
rand_vol = rand_integrate_polytope(A, b, integ_func, int(samples))
rand_time = time.perf_counter() - start
print(f"with {samples} rand samples, volume: {rand_vol}; time: {round(rand_time * 1000, 3)}ms")
def main():
"""main entry point"""
print("2d test")
test_2d_volume()
print("\n4d test")
test_4d_volume()
print("\n4d integrate test")
test_4d_integrate()
if __name__ == "__main__":
main()