Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
cantaro86
GitHub Repository: cantaro86/Financial-Models-Numerical-Methods
Path: blob/master/src/FMNM/cython/solvers.pyx
1700 views
1
"""
2
Created on Mon Jul 29 11:13:45 2019
3
4
@author: cantaro86
5
"""
6
7
import numpy as np
8
from scipy.linalg import norm
9
cimport numpy as np
10
cimport cython
11
12
cdef np.float64_t distance2(np.float64_t[:] a, np.float64_t[:] b, unsigned int N):
13
cdef np.float64_t dist = 0
14
cdef unsigned int i
15
for i in range(N):
16
dist += (a[i] - b[i]) * (a[i] - b[i])
17
return dist
18
19
20
@cython.boundscheck(False)
21
@cython.wraparound(False)
22
def SOR(np.float64_t aa,
23
np.float64_t bb, np.float64_t cc,
24
np.float64_t[:] b,
25
np.float64_t w=1, np.float64_t eps=1e-10, unsigned int N_max = 500):
26
27
cdef unsigned int N = b.size
28
29
cdef np.float64_t[:] x0 = np.ones(N, dtype=np.float64) # initial guess
30
cdef np.float64_t[:] x_new = np.ones(N, dtype=np.float64) # new solution
31
32
33
cdef unsigned int i, k
34
cdef np.float64_t S
35
36
for k in range(1,N_max+1):
37
for i in range(N):
38
if (i==0):
39
S = cc * x_new[1]
40
elif (i==N-1):
41
S = aa * x_new[N-2]
42
else:
43
S = aa * x_new[i-1] + cc * x_new[i+1]
44
x_new[i] = (1-w)*x_new[i] + (w/bb) * (b[i] - S)
45
if distance2(x_new, x0, N) < eps*eps:
46
return x_new
47
x0[:] = x_new
48
if k==N_max:
49
print("Fail to converge in {} iterations".format(k))
50
return x_new
51
52
53
@cython.boundscheck(False)
54
@cython.wraparound(False)
55
def PSOR(np.float64_t aa,
56
np.float64_t bb, np.float64_t cc,
57
np.float64_t[:] B, np.float64_t[:] C,
58
np.float64_t w=1, np.float64_t eps=1e-10, unsigned int N_max = 500):
59
60
cdef unsigned int N = B.size
61
62
cdef np.float64_t[:] x0 = np.ones(N, dtype=np.float64) # initial guess
63
cdef np.float64_t[:] x_new = np.ones(N, dtype=np.float64) # new solution
64
65
cdef unsigned int i, k
66
cdef np.float64_t S
67
68
for k in range(1,N_max+1):
69
for i in range(N):
70
if (i==0):
71
S = cc * x_new[1]
72
elif (i==N-1):
73
S = aa * x_new[N-2]
74
else:
75
S = aa * x_new[i-1] + cc * x_new[i+1]
76
x_new[i] = (1-w)*x_new[i] + (w/bb) * (B[i] - S)
77
x_new[i] = x_new[i] if (x_new[i] > C[i]) else C[i]
78
79
if distance2(x_new, x0, N) < eps*eps:
80
print("Convergence after {} iterations".format(k))
81
return x_new
82
x0[:] = x_new
83
if k==N_max:
84
print("Fail to converge in {} iterations".format(k))
85
return x_new
86
87
88
89