Skip to content

Commit b89f838

Browse files
committed
many fixes for transfer
1 parent fa29b61 commit b89f838

File tree

4 files changed

+52
-42
lines changed

4 files changed

+52
-42
lines changed

pySDC/implementations/problem_classes/TestEquation_0D.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -35,11 +35,11 @@ def __init__(self, problem_params, dtype_u, dtype_f):
3535

3636
assert not any(isinstance(i, list) for i in problem_params['lambdas']), \
3737
'ERROR: expect flat list here, got %s' % problem_params['lambdas']
38-
nvars = len(problem_params['lambdas'])
39-
assert nvars > 0, 'ERROR: expect at least one lambda parameter here'
38+
problem_params['nvars'] = len(problem_params['lambdas'])
39+
assert problem_params['nvars'] > 0, 'ERROR: expect at least one lambda parameter here'
4040

4141
# invoke super init, passing number of dofs, dtype_u and dtype_f
42-
super(testequation0d, self).__init__(init=nvars, dtype_u=dtype_u, dtype_f=dtype_f,
42+
super(testequation0d, self).__init__(init=problem_params['nvars'], dtype_u=dtype_u, dtype_f=dtype_f,
4343
params=problem_params)
4444

4545
self.A = self.__get_A(self.params.lambdas)

pySDC/implementations/transfer_classes/TransferMesh_NoCoarse.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
from __future__ import division
22

3+
import scipy.sparse as sp
4+
35
from pySDC.implementations.datatype_classes.mesh import mesh, rhs_imex_mesh
46
from pySDC.core.SpaceTransfer import space_transfer
57
from pySDC.core.Errors import TransferError
@@ -29,6 +31,9 @@ def __init__(self, fine_prob, coarse_prob, params):
2931
# invoke super initialization
3032
super(mesh_to_mesh, self).__init__(fine_prob, coarse_prob, params)
3133

34+
self.Rspace = sp.eye(self.coarse_prob.params.nvars)
35+
self.Pspace = sp.eye(self.fine_prob.params.nvars)
36+
3237
def restrict(self, F):
3338
"""
3439
Restriction implementation

pySDC/projects/matrixPFASST/allinclusive_matrix_nonMPI.py

Lines changed: 30 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,4 @@
11
import numpy as np
2-
import scipy.sparse as sp
3-
import scipy.sparse.linalg as spla
42

53
from pySDC.implementations.controller_classes.allinclusive_multigrid_nonMPI import allinclusive_multigrid_nonMPI
64

@@ -55,16 +53,16 @@ def __init__(self, num_procs, controller_params, description):
5553
assert self.nlevels <= 2, 'ERROR: cannot use matrix-PFASST with more than 2 levels' # TODO: fixme
5654
assert [level.dt for step in self.MS for level in step.levels].count(self.dt) == self.nlevels * self.nsteps, \
5755
'ERROR: dt must be equal for all steps and all levels'
58-
assert [level.sweep.coll.num_nodes for step in self.MS for level in step.levels].count(self.nnodes) == \
59-
self.nlevels * self.nsteps, 'ERROR: nnodes must be equal for all steps and all levels'
56+
# assert [level.sweep.coll.num_nodes for step in self.MS for level in step.levels].count(self.nnodes) == \
57+
# self.nlevels * self.nsteps, 'ERROR: nnodes must be equal for all steps and all levels'
6058
assert [type(level.prob) for step in self.MS for level in step.levels].count(type(prob)) == \
6159
self.nlevels * self.nsteps, 'ERROR: all probem classes have to be the same'
6260

6361
assert self.params.predict is False, 'ERROR: no predictor for matrix controller yet' # TODO: fixme
6462

6563
assert hasattr(prob, 'A'), 'ERROR: need system matrix A for this (and linear problems!)'
6664

67-
A = prob.A
65+
A = prob.A.todense()
6866
Q = self.MS[0].levels[0].sweep.coll.Qmat[1:, 1:]
6967
Qd = self.MS[0].levels[0].sweep.QI[1:, 1:]
7068

@@ -74,26 +72,33 @@ def __init__(self, num_procs, controller_params, description):
7472
N = np.zeros((self.nnodes, self.nnodes))
7573
N[:, -1] = 1
7674

77-
self.C = sp.eye(self.nsteps * self.nnodes * self.nspace) - \
78-
self.dt * sp.kron(sp.eye(self.nsteps), sp.kron(Q, A)) - sp.kron(E, sp.kron(N, sp.eye(self.nspace)))
79-
self.P = sp.eye(self.nsteps * self.nnodes * self.nspace) - \
80-
self.dt * sp.kron(sp.eye(self.nsteps), sp.kron(Qd, A))
75+
self.C = np.array(np.eye(self.nsteps * self.nnodes * self.nspace) - \
76+
self.dt * np.kron(np.eye(self.nsteps), np.kron(Q, A)) - np.kron(E, np.kron(N, np.eye(self.nspace))))
77+
self.P = np.array(np.eye(self.nsteps * self.nnodes * self.nspace) - \
78+
self.dt * np.kron(np.eye(self.nsteps), np.kron(Qd, A)))
8179

8280
if self.nlevels > 1:
8381
prob_c = self.MS[0].levels[1].prob
8482
self.nspace_c = prob_c.init
8583

86-
Ac = prob_c.A
84+
Ac = prob_c.A.todense()
8785
Qdc = self.MS[0].levels[1].sweep.QI[1:, 1:]
8886

89-
TcfA = self.MS[0].base_transfer.space_transfer.Pspace
90-
TfcA = self.MS[0].base_transfer.space_transfer.Rspace
87+
nnodesc = self.MS[0].levels[1].sweep.coll.num_nodes
88+
Nc = np.zeros((nnodesc, nnodesc))
89+
Nc[:, -1] = 1
9190

92-
self.Tcf = sp.kron(sp.eye(self.nsteps * self.nnodes), TcfA)
93-
self.Tfc = sp.kron(sp.eye(self.nsteps * self.nnodes), TfcA)
91+
TcfA = self.MS[0].base_transfer.space_transfer.Pspace.todense()
92+
TfcA = self.MS[0].base_transfer.space_transfer.Rspace.todense()
93+
TcfQ = self.MS[0].base_transfer.Pcoll
94+
TfcQ = self.MS[0].base_transfer.Rcoll
9495

95-
self.Pc = sp.eye(self.nsteps * self.nnodes * self.nspace_c) - \
96-
self.dt * sp.kron(sp.eye(self.nsteps), sp.kron(Qdc, Ac)) - sp.kron(E, sp.kron(N, sp.eye(self.nspace_c)))
96+
self.Tcf = np.array(np.kron(np.eye(self.nsteps), np.kron(TcfQ, TcfA)))
97+
self.Tfc = np.array(np.kron(np.eye(self.nsteps), np.kron(TfcQ, TfcA)))
98+
99+
self.Pc = np.array(np.eye(self.nsteps * nnodesc * self.nspace_c) - \
100+
self.dt * np.kron(np.eye(self.nsteps), np.kron(Qdc, Ac)) - \
101+
np.kron(E, np.kron(Nc, np.eye(self.nspace_c))))
97102

98103
self.u = np.zeros(self.nsteps * self.nnodes * self.nspace)
99104
self.res = np.zeros(self.nsteps * self.nnodes * self.nspace)
@@ -167,9 +172,9 @@ def build_propagation_matrix(self, niter):
167172
"""
168173

169174
# build smoother iteration matrix and preconditioner using nsweeps
170-
Pinv = np.linalg.inv(self.P.todense())
175+
Pinv = np.linalg.inv(self.P)
171176
precond_smoother = Pinv.copy()
172-
iter_mat_smoother = np.eye(self.nsteps * self.nnodes * self.nspace) - precond_smoother.dot(self.C.todense())
177+
iter_mat_smoother = np.eye(self.nsteps * self.nnodes * self.nspace) - precond_smoother.dot(self.C)
173178
for k in range(1, self.MS[0].levels[0].params.nsweeps):
174179
precond_smoother += np.linalg.matrix_power(iter_mat_smoother, k).dot(Pinv)
175180
iter_mat_smoother = np.linalg.matrix_power(iter_mat_smoother, self.MS[0].levels[0].params.nsweeps)
@@ -178,10 +183,10 @@ def build_propagation_matrix(self, niter):
178183

179184
# add coarse-grid correction (single sweep, though!)
180185
if self.nlevels > 1:
181-
precond_cgc = self.Tcf.todense().dot(np.linalg.inv(self.Pc.todense())).dot(self.Tfc.todense())
182-
iter_mat_cgc = np.eye(self.nsteps * self.nnodes * self.nspace) - precond_cgc.dot(self.C.todense())
186+
precond_cgc = self.Tcf.dot(np.linalg.inv(self.Pc)).dot(self.Tfc)
187+
iter_mat_cgc = np.eye(self.nsteps * self.nnodes * self.nspace) - precond_cgc.dot(self.C)
183188
iter_mat = iter_mat.dot(iter_mat_cgc)
184-
precond += precond_cgc - precond_smoother.dot(self.C.todense()).dot(precond_cgc)
189+
precond += precond_cgc - precond_smoother.dot(self.C).dot(precond_cgc)
185190

186191
# form span and reduce matrices and add to operator
187192
Tspread = np.kron(np.concatenate([[1] * (self.nsteps * self.nnodes)]), np.eye(self.nspace)).T
@@ -223,7 +228,7 @@ def restart_block(self, slots, time, u0):
223228
for lvl in self.MS[p].levels:
224229
lvl.status.time = time[p]
225230
P = lvl.prob
226-
for m in range(1, self.nnodes + 1):
231+
for m in range(1, lvl.sweep.coll.num_nodes + 1):
227232
lvl.u[m] = P.dtype_u(init=P.init, val=0)
228233
lvl.f[m] = P.dtype_f(init=P.init, val=0)
229234

@@ -288,7 +293,7 @@ def pfasst(self, MS):
288293
for S in MS:
289294
self.hooks.pre_sweep(step=S, level_number=0)
290295

291-
self.u += spla.spsolve(self.P, self.res)
296+
self.u += np.linalg.solve(self.P, self.res)
292297
self.res = self.u0 - self.C.dot(self.u)
293298

294299
MS = self.update_data(MS=MS, u=self.u, res=self.res, niter=niter, level=0, stage='POST_PRE_SWEEP')
@@ -310,7 +315,7 @@ def pfasst(self, MS):
310315
for S in MS:
311316
self.hooks.pre_sweep(step=S, level_number=1)
312317

313-
self.u += self.Tcf.dot(spla.spsolve(self.Pc, self.Tfc.dot(self.res)))
318+
self.u += self.Tcf.dot(np.linalg.solve(self.Pc, self.Tfc.dot(self.res)))
314319
self.res = self.u0 - self.C.dot(self.u)
315320

316321
MS = self.update_data(MS=MS, u=self.u, res=self.res, niter=niter, level=1,
@@ -324,7 +329,7 @@ def pfasst(self, MS):
324329
for S in MS:
325330
self.hooks.pre_sweep(step=S, level_number=0)
326331

327-
self.u += spla.spsolve(self.P, self.res)
332+
self.u += np.linalg.solve(self.P, self.res)
328333
self.res = self.u0 - self.C.dot(self.u)
329334

330335
MS = self.update_data(MS=MS, u=self.u, res=self.res, niter=niter, level=0, stage='POST_FINE_SWEEP')

pySDC/projects/matrixPFASST/compare_to_propagator.py

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -140,12 +140,12 @@ def testequation_setup():
140140
level_params = dict()
141141
level_params['restol'] = 1E-08
142142
level_params['dt'] = 0.25
143-
level_params['nsweeps'] = [3]
143+
level_params['nsweeps'] = [1, 1]
144144

145145
# initialize sweeper parameters
146146
sweeper_params = dict()
147147
sweeper_params['collocation_class'] = CollGaussRadau_Right
148-
sweeper_params['num_nodes'] = [3]
148+
sweeper_params['num_nodes'] = [3, 3]
149149
sweeper_params['QI'] = 'LU'
150150
sweeper_params['spread'] = True
151151

@@ -155,19 +155,19 @@ def testequation_setup():
155155
# use single values like this...
156156
problem_params['lambdas'] = [[-1.0]]
157157
# .. or a list of values like this ...
158-
problem_params['lambdas'] = [[-1.0, -2.0, 1j, -1j]]
158+
# problem_params['lambdas'] = [[-1.0, -2.0, 1j, -1j]]
159159
# .. or a whole block of values like this
160-
ilim_left = -11
161-
ilim_right = 0
162-
rlim_left = 0
163-
rlim_right = 11
164-
ilam = 1j * np.logspace(ilim_left, ilim_right, 11)
165-
rlam = -1 * np.logspace(rlim_left, rlim_right, 11)
166-
lambdas = []
167-
for rl in rlam:
168-
for il in ilam:
169-
lambdas.append(rl + il)
170-
problem_params['lambdas'] = [lambdas]
160+
# ilim_left = -11
161+
# ilim_right = 0
162+
# rlim_left = 0
163+
# rlim_right = 11
164+
# ilam = 1j * np.logspace(ilim_left, ilim_right, 11)
165+
# rlam = -1 * np.logspace(rlim_left, rlim_right, 11)
166+
# lambdas = []
167+
# for rl in rlam:
168+
# for il in ilam:
169+
# lambdas.append(rl + il)
170+
# problem_params['lambdas'] = [lambdas]
171171
# note: PFASST will do all of those at once, but without interaction (realized via diagonal matrix).
172172
# The propagation matrix will be diagonal too, corresponding to the respective lambda value.
173173

0 commit comments

Comments
 (0)