Skip to content

Commit 8d5232e

Browse files
committed
adding tests for chempy.cpv
1 parent 27c28cb commit 8d5232e

2 files changed

Lines changed: 568 additions & 68 deletions

File tree

modules/chempy/cpv.py

Lines changed: 58 additions & 68 deletions
Original file line numberDiff line numberDiff line change
@@ -21,43 +21,46 @@
2121
#
2222
# TODO: documentation!
2323

24+
from typing import Sequence
2425
import math
2526
import random
26-
import copy
2727

2828
RSMALL4 = 0.0001
2929

3030
#------------------------------------------------------------------------------
31-
def get_null():
31+
def get_null() -> list[float]:
3232
return [0.0,0.0,0.0]
3333

3434
#------------------------------------------------------------------------------
35-
def get_identity():
35+
def get_identity() -> list[list[float]]:
3636
return [[1.0,0.0,0.0],[0.0,1.0,0.0],[0.0,0.0,1.0]]
3737

3838
#------------------------------------------------------------------------------
39-
def distance_sq(v1, v2):
39+
def distance_sq(v1: Sequence[float], v2: Sequence[float]) -> float:
4040
d0 = v2[0] - v1[0]
4141
d1 = v2[1] - v1[1]
4242
d2 = v2[2] - v1[2]
4343
return (d0*d0) + (d1*d1) + (d2*d2)
4444

4545
#------------------------------------------------------------------------------
46-
def distance(v1, v2):
46+
def distance(v1: Sequence[float], v2: Sequence[float]) -> float:
4747
d0 = v2[0] - v1[0]
4848
d1 = v2[1] - v1[1]
4949
d2 = v2[2] - v1[2]
5050
return math.sqrt((d0*d0) + (d1*d1) + (d2*d2))
5151

5252
#------------------------------------------------------------------------------
53-
def length(v):
53+
def length(v: Sequence[float]) -> float:
5454
return math.sqrt(v[0]*v[0] + v[1]*v[1] + v[2]*v[2])
5555

5656
#------------------------------------------------------------------------------
57-
def random_displacement(v,radius):
58-
r_vect = lambda r=random.random:[r()-0.5,r()-0.5,r()-0.5]
57+
def _random_vector() -> list[float]:
58+
r = random.random
59+
return [r()-0.5,r()-0.5,r()-0.5]
60+
61+
def random_displacement(v: Sequence[float], radius: float) -> list[float]:
5962
while 1:
60-
vect = r_vect()
63+
vect = _random_vector()
6164
v_len = length(vect)
6265
if (v_len<=0.5):
6366
break;
@@ -68,92 +71,85 @@ def random_displacement(v,radius):
6871
return v
6972

7073
#------------------------------------------------------------------------------
71-
def random_sphere(v,radius):
72-
r_vect = lambda r=random.random:[r()-0.5,r()-0.5,r()-0.5]
74+
def random_sphere(v: Sequence[float], radius: float) -> list[float]:
7375
while 1:
74-
vect = r_vect()
76+
vect = _random_vector()
7577
v_len = length(vect)
7678
if (v_len<=0.5) and (v_len!=0.0):
7779
break;
7880
return add(v,scale([vect[0], vect[1], vect[2]],2*radius/v_len))
7981

8082
#------------------------------------------------------------------------------
81-
def random_vector():
82-
r_vect = lambda r=random.random:[r()-0.5,r()-0.5,r()-0.5]
83+
def random_vector() -> list[float]:
8384
while 1:
84-
vect = r_vect()
85+
vect = _random_vector()
8586
if length(vect)<=0.5:
8687
break;
8788
return scale([vect[0], vect[1], vect[2]],2.0)
8889

8990
#------------------------------------------------------------------------------
90-
def add(v1,v2):
91+
def add(v1: Sequence[float], v2: Sequence[float]) -> list[float]:
9192
return [v1[0]+v2[0],v1[1]+v2[1],v1[2]+v2[2]]
9293

9394
#------------------------------------------------------------------------------
94-
def average(v1,v2):
95+
def average(v1: Sequence[float], v2: Sequence[float]) -> list[float]:
9596
return [(v1[0]+v2[0])/2.0,(v1[1]+v2[1])/2.0,(v1[2]+v2[2])/2.0]
9697

9798
#------------------------------------------------------------------------------
98-
def scale(v,factor):
99+
def scale(v: Sequence[float], factor: float) -> list[float]:
99100
return [v[0]*factor,v[1]*factor,v[2]*factor]
100101

101102
#------------------------------------------------------------------------------
102-
def negate(v):
103+
def negate(v: Sequence[float]) -> list[float]:
103104
return [-v[0],-v[1],-v[2]]
104105

105106
#------------------------------------------------------------------------------
106-
def sub(v1,v2):
107+
def reverse(v: Sequence[float]) -> list[float]:
108+
return [ -v[0], -v[1], -v[2] ]
109+
110+
#------------------------------------------------------------------------------
111+
def sub(v1: Sequence[float], v2: Sequence[float]) -> list[float]:
107112
return [v1[0]-v2[0],v1[1]-v2[1],v1[2]-v2[2]]
108113

109114
#------------------------------------------------------------------------------
110-
def dot_product(v1,v2):
115+
def dot_product(v1: Sequence[float], v2: Sequence[float]) -> float:
111116
return v1[0]*v2[0]+v1[1]*v2[1]+v1[2]*v2[2]
112117

113118
#------------------------------------------------------------------------------
114-
def cross_product(v1,v2):
119+
def cross_product(v1: Sequence[float], v2: Sequence[float]) -> list[float]:
115120
return [(v1[1]*v2[2]) - (v1[2]*v2[1]),
116121
(v1[2]*v2[0]) - (v1[0]*v2[2]),
117122
(v1[0]*v2[1]) - (v1[1]*v2[0])]
118123

119124
#------------------------------------------------------------------------------
120-
def transform(m,v):
125+
def transform(m: Sequence[Sequence[float]], v: Sequence[float]) -> list[float]:
121126
return [m[0][0]*v[0] + m[0][1]*v[1] + m[0][2]*v[2],
122127
m[1][0]*v[0] + m[1][1]*v[1] + m[1][2]*v[2],
123128
m[2][0]*v[0] + m[2][1]*v[1] + m[2][2]*v[2]]
124129

125130
#------------------------------------------------------------------------------
126-
def inverse_transform(m,v):
131+
def inverse_transform(m: Sequence[Sequence[float]], v: Sequence[float]) -> list[float]:
127132
return [m[0][0]*v[0] + m[1][0]*v[1] + m[2][0]*v[2],
128133
m[0][1]*v[0] + m[1][1]*v[1] + m[2][1]*v[2],
129134
m[0][2]*v[0] + m[1][2]*v[1] + m[2][2]*v[2]]
130135

131136
#------------------------------------------------------------------------------
132-
def multiply(m1,m2): # HAVEN'T YET VERIFIED THAT THIS CONFORMS TO STANDARD DEFT
133-
return [[m1[0][0]*m2[0][0] + m1[0][1]*m2[1][0] + m1[0][2]*m2[2][0],
134-
m1[1][0]*m2[0][0] + m1[1][1]*m2[1][0] + m1[1][2]*m2[2][0],
135-
m1[2][0]*m2[0][0] + m1[2][1]*m2[1][0] + m1[2][2]*m2[2][0]],
136-
[m1[0][0]*m2[0][1] + m1[0][1]*m2[1][1] + m1[0][2]*m2[2][1],
137-
m1[1][0]*m2[0][1] + m1[1][1]*m2[1][1] + m1[1][2]*m2[2][1],
138-
m1[2][0]*m2[0][1] + m1[2][1]*m2[1][1] + m1[2][2]*m2[2][1]],
139-
[m1[0][0]*m2[0][2] + m1[0][1]*m2[1][2] + m1[0][2]*m2[2][2],
140-
m1[1][0]*m2[0][2] + m1[1][1]*m2[1][2] + m1[1][2]*m2[2][2],
141-
m1[2][0]*m2[0][2] + m1[2][1]*m2[1][2] + m1[2][2]*m2[2][2]]]
137+
def multiply(m1: Sequence[Sequence[float]], m2: Sequence[Sequence[float]]) -> list[list[float]]:
138+
# HAVEN'T YET VERIFIED THAT THIS CONFORMS TO STANDARD DEFT
139+
# upd: no, it's not(fixed)
142140

143-
#------------------------------------------------------------------------------
144-
def transpose(m1):
145-
return [[m1[0][0],
146-
m1[1][0],
147-
m1[2][0]],
148-
[m1[0][1],
149-
m1[1][1],
150-
m1[2][1]],
151-
[m1[0][2],
152-
m1[1][2],
153-
m1[2][2]]]
141+
return [[m1[0][0]*m2[0][0] + m1[0][1]*m2[1][0] + m1[0][2]*m2[2][0],
142+
m1[0][0]*m2[0][1] + m1[0][1]*m2[1][1] + m1[0][2]*m2[2][1],
143+
m1[0][0]*m2[0][2] + m1[0][1]*m2[1][2] + m1[0][2]*m2[2][2]],
144+
[m1[1][0]*m2[0][0] + m1[1][1]*m2[1][0] + m1[1][2]*m2[2][0],
145+
m1[1][0]*m2[0][1] + m1[1][1]*m2[1][1] + m1[1][2]*m2[2][1],
146+
m1[1][0]*m2[0][2] + m1[1][1]*m2[1][2] + m1[1][2]*m2[2][2]],
147+
[m1[2][0]*m2[0][0] + m1[2][1]*m2[1][0] + m1[2][2]*m2[2][0],
148+
m1[2][0]*m2[0][1] + m1[2][1]*m2[1][1] + m1[2][2]*m2[2][1],
149+
m1[2][0]*m2[0][2] + m1[2][1]*m2[1][2] + m1[2][2]*m2[2][2]]]
154150

155151
#------------------------------------------------------------------------------
156-
def get_system2(x,y):
152+
def get_system2(x: Sequence[float],y: Sequence[float]) -> list[list[float]]:
157153
z = cross_product(x,y)
158154
z = normalize(z)
159155
y = cross_product(z,x);
@@ -162,24 +158,24 @@ def get_system2(x,y):
162158
return [x,y,z]
163159

164160
#------------------------------------------------------------------------------
165-
def scale_system(s,factor):
161+
def scale_system(s: Sequence[Sequence[float]], factor: float) -> list[list[float]]:
166162
r = []
167163
for a in s:
168164
r.append([a[0]*factor,a[1]*factor,a[2]*factor])
169165
return r
170166

171167
#------------------------------------------------------------------------------
172-
def transpose(m):
168+
def transpose(m: Sequence[Sequence[float]]) -> list[list[float]]:
173169
return [[m[0][0], m[1][0], m[2][0]],
174170
[m[0][1], m[1][1], m[2][1]],
175171
[m[0][2], m[1][2], m[2][2]]]
176172

177173
#------------------------------------------------------------------------------
178-
def transform_about_point(m,v,p):
174+
def transform_about_point(m: Sequence[Sequence[float]], v: Sequence[float], p: Sequence[float]) -> list[float]:
179175
return add(transform(m,sub(v,p)),p)
180176

181177
#------------------------------------------------------------------------------
182-
def get_angle(v1,v2): # v1,v2 must be unit vectors
178+
def get_angle(v1: Sequence[float], v2: Sequence[float]) -> float: # v1,v2 must be unit vectors
183179
denom = (math.sqrt(((v1[0]*v1[0]) + (v1[1]*v1[1]) + (v1[2]*v1[2]))) *
184180
math.sqrt(((v2[0]*v2[0]) + (v2[1]*v2[1]) + (v2[2]*v2[2]))))
185181
if denom>1e-10:
@@ -190,7 +186,7 @@ def get_angle(v1,v2): # v1,v2 must be unit vectors
190186
return result
191187

192188
#------------------------------------------------------------------------------
193-
def get_angle_formed_by(p1,p2,p3): # angle formed by three positions in space
189+
def get_angle_formed_by(p1: Sequence[float], p2: Sequence[float], p3: Sequence[float]) -> float: # angle formed by three positions in space
194190

195191
# based on code submitted by Paul Sherwood
196192
r1 = distance(p1,p2)
@@ -207,37 +203,33 @@ def get_angle_formed_by(p1,p2,p3): # angle formed by three positions in space
207203
return theta;
208204

209205
#------------------------------------------------------------------------------
210-
def project(v,n):
206+
def project(v: Sequence[float], n: Sequence[float]) -> list[float]:
211207
dot = v[0]*n[0] + v[1]*n[1] + v[2]*n[2]
212208
return [ dot * n[0], dot * n[1], dot * n[2] ]
213209

214210
#------------------------------------------------------------------------------
215-
def remove_component(v, n):
211+
def remove_component(v: Sequence[float], n: Sequence[float]) -> list[float]:
216212
dot = v[0]*n[0] + v[1]*n[1] + v[2]*n[2]
217213
return [v[0] - dot * n[0], v[1] - dot * n[1], v[2] - dot * n[2]]
218214

219215
#------------------------------------------------------------------------------
220-
def normalize(v):
216+
def normalize(v: Sequence[float]) -> list[float]:
221217
vlen = math.sqrt((v[0]*v[0]) + (v[1]*v[1]) + (v[2]*v[2]))
222218
if vlen>RSMALL4:
223219
return [v[0]/vlen,v[1]/vlen,v[2]/vlen]
224220
else:
225221
return get_null()
226222

227223
#------------------------------------------------------------------------------
228-
def reverse(v):
229-
return [ -v[0], -v[1], -v[2] ]
230-
231-
#------------------------------------------------------------------------------
232-
def normalize_failsafe(v):
224+
def normalize_failsafe(v: Sequence[float]) -> list[float]:
233225
vlen = math.sqrt((v[0]*v[0]) + (v[1]*v[1]) + (v[2]*v[2]))
234226
if vlen>RSMALL4:
235227
return [v[0]/vlen,v[1]/vlen,v[2]/vlen]
236228
else:
237229
return [1.0,0.0,0.0]
238230

239231
#------------------------------------------------------------------------------
240-
def rotation_matrix(angle,axis):
232+
def rotation_matrix(angle: float, axis: Sequence[float]) -> list[list[float]]:
241233

242234
x=axis[0]
243235
y=axis[1]
@@ -271,7 +263,7 @@ def rotation_matrix(angle,axis):
271263
[ (one_c * zx) - ys, (one_c * yz) + xs, (one_c * zz) + c ]]
272264

273265
#------------------------------------------------------------------------------
274-
def transform_array(rot_mtx,vec_array):
266+
def transform_array(rot_mtx: Sequence[Sequence[float]], vec_array: Sequence[Sequence[float]]) -> list[list[float]]:
275267

276268
'''transform_array( matrix, vector_array ) -> vector_array
277269
@@ -280,7 +272,7 @@ def transform_array(rot_mtx,vec_array):
280272
return [transform(rot_mtx, x) for x in vec_array]
281273

282274
#------------------------------------------------------------------------------
283-
def translate_array(trans_vec,vec_array):
275+
def translate_array(trans_vec: Sequence[float], vec_array: Sequence[Sequence[float]]) -> list[list[float]]:
284276

285277
'''translate_array(trans_vec,vec_array) -> vec_array
286278
@@ -291,17 +283,17 @@ def translate_array(trans_vec,vec_array):
291283
return [add(trans_vec, x) for x in vec_array]
292284

293285
#------------------------------------------------------------------------------
294-
def fit_apply(fit_result,vec_array):
286+
def fit_apply(fit_result: tuple[Sequence[float], Sequence[float], Sequence[Sequence[float]], float], vec_array: Sequence[Sequence[float]]) -> list[list[float]]:
295287
'''fit_apply(fir_result,vec_array) -> vec_array
296-
288+
297289
Applies a fit result to an array of vectors
298290
'''
299291

300292
t1, mt2, m = fit_result[:3]
301293
return [add(t1, transform(m, add(mt2, x))) for x in vec_array]
302294

303295
#------------------------------------------------------------------------------
304-
def fit(target_array, source_array):
296+
def fit(target_array: Sequence[Sequence[float]], source_array: Sequence[Sequence[float]]) -> tuple[list[float], list[float], list[list[float]], float]:
305297

306298
'''fit(target_array, source_array) -> (t1, t2, rot_mtx, rmsd) [fit_result]
307299
@@ -370,7 +362,6 @@ def fit(target_array, source_array):
370362
iters = 0
371363
while (iters < maxiter):
372364
iters = iters + 1
373-
ix = (iters-1)%ndim
374365
iy = iters%ndim
375366
iz = (iters+1)%ndim
376367
sig = corr_mtx[iz][iy] - corr_mtx[iy][iz]
@@ -403,5 +394,4 @@ def fit(target_array, source_array):
403394
return(t1, t2, rot_mtx, rmsd)
404395

405396
# Too many iterations; something wrong.
406-
print ("Error: Too many iterations in RMS fit.")
407-
raise ValueError
397+
raise ValueError("Error: Too many iterations in RMS fit.")

0 commit comments

Comments
 (0)