OPAL (Object Oriented Parallel Accelerator Library) 2024.2
OPAL
MultipoleTStraight.cpp
Go to the documentation of this file.
1/*
2 * Copyright (c) 2017, Titus Dascalu
3 * Copyright (c) 2018, Martin Duy Tat
4 * All rights reserved.
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * 1. Redistributions of source code must retain the above copyright notice,
8 * this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright notice,
10 * this list of conditions and the following disclaimer in the documentation
11 * and/or other materials provided with the distribution.
12 * 3. Neither the name of STFC nor the names of its contributors may be used to
13 * endorse or promote products derived from this software without specific
14 * prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
20 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26 * POSSIBILITY OF SUCH DAMAGE.
27 */
28#include "gsl/gsl_sf_gamma.h"
29#include "gsl/gsl_sf_pow_int.h"
30#include "MultipoleTStraight.h"
31#include "MultipoleT.h"
32
36
38 straightGeometry_m.setElementLength(element_m->getLength());
39}
40
42 double Bx = 0.0;
43 for(std::size_t n = 0; n <= element_m->getMaxFOrder(); n++) {
44 double f_n = 0.0;
45 for(std::size_t i = 0; i <= n; i++) {
46 f_n += gsl_sf_choose(n, i) * element_m->getTransDeriv(2 * i + 1, R[0]) *
47 element_m->getFringeDeriv(2 * n - 2 * i, R[2]);
48 }
49 f_n *= gsl_sf_pow_int(-1.0, static_cast<int>(n));
50 Bx += f_n * gsl_sf_pow_int(R[1], 2 * static_cast<int>(n) + 1) / gsl_sf_fact(2 * n + 1);
51 }
52 return Bx;
53}
54
56 double Bs = 0.0;
57 for(std::size_t n = 0; n <= element_m->getMaxFOrder(); n++) {
58 double f_n = 0.0;
59 for(std::size_t i = 0; i <= n; i++) {
60 f_n += gsl_sf_choose(n, i) * element_m->getTransDeriv(2 * i, R[0]) *
61 element_m->getFringeDeriv(2 * n - 2 * i + 1, R[2]);
62 }
63 f_n *= gsl_sf_pow_int(-1.0, static_cast<int>(n));
64 Bs += f_n * gsl_sf_pow_int(R[1], 2 * static_cast<int>(n) + 1) / gsl_sf_fact(2 * n + 1);
65 }
66 return Bs;
67}
68
69double MultipoleTStraight::getFn(size_t n, double x, double s) {
70 if (n == 0) {
71 return element_m->getTransDeriv(0, x) * element_m->getFringeDeriv(0, s);
72 }
73 double f_n = 0.0;
74 for (std::size_t i = 0; i <= n; i++) {
75 f_n += gsl_sf_choose(n, i) * element_m->getTransDeriv(2 * i, x) *
76 element_m->getFringeDeriv(2 * n - 2 * i, s);
77 }
78 f_n *= gsl_sf_pow_int(-1.0, static_cast<int>(n));
79 return f_n;
80}
81
83 return {r[0], r[1], r[2] + element_m->getLength() / 2.0};
84}
85
87 // Magnet origin at the center rather than entry
88 R[2] += element_m->getLength() / 2.0;
89}
MultipoleT * element_m
MultipoleTBase(MultipoleT *element)
double getBs(const Vector_t &R) override
double getFn(size_t n, double x, double s) override
StraightGeometry straightGeometry_m
MultipoleTStraight(MultipoleT *element)
void transformCoords(Vector_t &R) override
void initialise() override
Vector_t localCartesianToOpalCartesian(const Vector_t &r) override
double getBx(const Vector_t &R) override
Vektor< double, 3 > Vector_t