26 h = 2 * R / ND; n = ND + 4; self.h, self.n = h, n
27 x0 = -n * h / 2 + off[0] * h; y0 = -n * h / 2 + off[1] * h
28 self.
xe = x0 + h * np.arange(n + 1); self.ye = y0 + h * np.arange(n + 1)
29 self.
xc = 0.5 * (self.
xe[1:] + self.
xe[:-1]); self.yc = 0.5 * (self.ye[1:] + self.ye[:-1])
30 psi =
lambda x, y: 0.5 * (x * x + y * y)
31 def open_intervals(c, lo, hi):
32 sR = np.sqrt(max(R**2 - c * c, 0)); sA = np.sqrt(max(A**2 - c * c, 0))
33 ivs = [(-sR, -sA), (sA, sR)]
if sA > 0
else [(-sR, sR)]
36 l, u = max(p, lo), min(q, hi)
37 if u > l: out.append((l, u))
40 self.
Fx = np.zeros((n + 1, n)); self.ax = np.zeros((n + 1, n))
41 for i
in range(n + 1):
43 for (l, u)
in open_intervals(self.
xe[i], self.ye[j], self.ye[j + 1]):
44 self.
Fx[i, j] += psi(self.
xe[i], u) - psi(self.
xe[i], l)
45 self.ax[i, j] += (u - l) / h
46 self.
Fy = np.zeros((n, n + 1)); self.ay = np.zeros((n, n + 1))
48 for j
in range(n + 1):
49 for (l, u)
in open_intervals(self.ye[j], self.
xe[i], self.
xe[i + 1]):
50 self.
Fy[i, j] += -(psi(u, self.ye[j]) - psi(l, self.ye[j]))
51 self.ay[i, j] += (u - l) / h
52 g, w = np.polynomial.legendre.leggauss(24)
53 X, Y = np.meshgrid(self.
xc, self.yc, indexing=
"ij"); r = np.hypot(X, Y)
54 self.
kap = ((r > A) & (r < R)).astype(float)
55 cut = (np.abs(r - A) < 1.5 * h) | (np.abs(r - R) < 1.5 * h)
56 for i, j
in zip(*np.nonzero(cut)):
57 XX, YY = np.meshgrid(self.
xc[i] + 0.5 * h * g, self.yc[j] + 0.5 * h * g, indexing=
"ij")
59 self.
kap[i, j] = (np.outer(w, w) * 0.25 * ((rr > A) & (rr < R))).sum()
61 div = (self.
Fx[1:, :] - self.
Fx[:-1, :]) + (self.
Fy[:, 1:] - self.
Fy[:, :-1])