-
Notifications
You must be signed in to change notification settings - Fork 0
/
auxfuns.py
89 lines (79 loc) · 2.9 KB
/
auxfuns.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
#!/usr/bin/env python
"""Auxiliary functions to manipulate data-types and and change data-formats."""
from scipy import mat, array, ones
import numpy
import subprocess #to use qhull
def splitAb(inAb, nd):
"""Split input Ab array (1d) into separate A and b."""
tmpAb = inAb.reshape(len(inAb)/(nd + 1), nd + 1)
A = tmpAb[:, :-1]
b = array([tmpAb[:, -1]]).T
return A, b
def uniqm(A, t=1e-13):
"""
Return input matrix with duplicate entries removed.
A - [matrix] input matrix (possibly containing duplicates)
t - [float] tolerance (default=1e-13)
"""
Nrows = A.shape[0]
uniquerows = [r1 for r1 in range(Nrows)
if not any(numpy.all(abs(A[r1, :] - A[r2, :]) < t)
for r2 in range(r1 + 1, Nrows))]
return A[uniquerows, :].copy()
def mat2ab(Asbmat):
"""
Transform [A s b]-form matrix to standard Ax<b notation.
Asbmat - [array] inequality matrix in the form Ax<b, matrix = [A s b]
with s the sign vector [1:>, -1:<]
"""
stmp = array([Asbmat[:, -2]])
b = Asbmat[:, -1]*-stmp
A = Asbmat[:, :-2]*-stmp.T
s = -ones(stmp.shape)
return A, s.T, b.T
def qhullstr(V):
"""
generate string qhull input format.
yields a newline separated string of format:
dimensions (columns of V)
number of points (rows of V)
one string for each row of V
"""
V = numpy.array(V)
return "%i\n%i\n" % (V.shape[1], V.shape[0]) \
+ "\n".join(" ".join(str(e) for e in row) for row in V)
def qhull(V, qstring):
"""
Use qhull to determine convex hull / volume / normals.
V - [matrix] vertices
qstring - [string] arguments to pass to qhull
"""
try:
qhullp = subprocess.Popen(["qhull", qstring],
stdin=subprocess.PIPE, stdout=subprocess.PIPE)
Vc = qhullp.communicate(qhullstr(V))[0] #qhull output to Vc
if qstring == "FS": #calc area and volume
ks = Vc.split('\n')[-2]
Vol = float(ks.split(' ')[-2]) #get volume of D-hull
return Vol
elif qstring == "Ft": #calc vertices and facets
ks = Vc.split('\n')
fms = int(ks[1].split(' ')[1]) #get size of facet matrix
fmat = ks[-fms-1:-1]
fmat = mat(';'.join(fmat)) #generate matrix
fmatv = fmat[:, 1:] #vertices on facets
return array(fmatv)
elif qstring == "n": #calc convex hull and get normals
ks = ';'.join(Vc.split('\n')[2:]) #remove leading dimension output
k = mat(ks[:-1]) #convert to martrix with vertices
return array(k)
else:
exit(1)
except:
raise NameError('QhullError')
if __name__ == "__main__":
import doctest
doctest.testfile("tests/auxfunstests.txt")
#TODO - auxfuns
# qhull error handling
# fix auxfuns tests