BornAgain  1.19.79
Open-source research software to simulate and fit neutron and x-ray reflectometry and grazing-incidence small-angle scattering
RoughMultiLayerContribution Class Referencefinal

Description

Computes the diffuse reflection from the rough interfaces of a sample. Used by DWBAComputation.

Definition at line 31 of file RoughMultiLayerContribution.h.

Collaboration diagram for RoughMultiLayerContribution:
[legend]

Public Member Functions

 RoughMultiLayerContribution (const reSample &re_sample)
 
void compute (DiffuseElement &ele) const
 

Private Member Functions

complex_t get_refractive_term (size_t i_layer, double wavelength) const
 
complex_t get_sum8terms (size_t i_layer, const DiffuseElement &ele) const
 

Private Attributes

const reSamplem_re_sample
 

Constructor & Destructor Documentation

◆ RoughMultiLayerContribution()

RoughMultiLayerContribution::RoughMultiLayerContribution ( const reSample re_sample)

Definition at line 45 of file RoughMultiLayerContribution.cpp.

46  : m_re_sample{re_sample}
47 {
48 }

Member Function Documentation

◆ compute()

void RoughMultiLayerContribution::compute ( DiffuseElement ele) const

Definition at line 50 of file RoughMultiLayerContribution.cpp.

51 {
52  if (ele.alphaMean() < 0.0)
53  return;
54  const size_t n_slices = m_re_sample.numberOfSlices();
55  R3 q = ele.meanQ();
56  double wavelength = ele.wavelength();
57  double autocorr(0.0);
58  complex_t crosscorr(0.0, 0.0);
59 
60  std::vector<complex_t> rterm(n_slices - 1);
61  std::vector<complex_t> sterm(n_slices - 1);
62 
63  for (size_t i = 0; i + 1 < n_slices; i++) {
64  rterm[i] = get_refractive_term(i, wavelength);
65  sterm[i] = get_sum8terms(i, ele);
66  }
67  for (size_t i = 0; i + 1 < n_slices; i++) {
68  const LayerRoughness* rough = m_re_sample.avgeSlice(i + 1).topRoughness();
69  if (rough)
70  autocorr += std::norm(rterm[i]) * std::norm(sterm[i]) * rough->spectralFunction(q);
71  }
72  // cross correlation between layers
73  if (m_re_sample.sample().crossCorrLength() != 0.0) {
74  for (size_t j = 0; j < n_slices - 1; j++) {
75  for (size_t k = 0; k < n_slices - 1; k++) {
76  if (j == k)
77  continue;
78  crosscorr += rterm[j] * sterm[j] * m_re_sample.crossCorrSpectralFun(q, j, k)
79  * std::conj(rterm[k]) * std::conj(sterm[k]);
80  }
81  }
82  }
83  //! @TODO clarify complex vs double
84  ele.addIntensity((autocorr + crosscorr.real()) * M_PI / 4. / wavelength / wavelength);
85 }
#define M_PI
Definition: Constants.h:44
double alphaMean() const
double wavelength() const
void addIntensity(double intensity)
A roughness of interface between two layers.
double spectralFunction(R3 kvec) const
Returns power spectral density of the surface roughness.
double crossCorrLength() const
Returns cross correlation length of roughnesses between interfaces.
Definition: MultiLayer.h:69
complex_t get_refractive_term(size_t i_layer, double wavelength) const
complex_t get_sum8terms(size_t i_layer, const DiffuseElement &ele) const
const LayerRoughness * topRoughness() const
Definition: Slice.cpp:76
const Slice & avgeSlice(size_t i) const
Definition: ReSample.cpp:346
size_t numberOfSlices() const
Definition: ReSample.cpp:336
double crossCorrSpectralFun(R3 kvec, size_t j, size_t k) const
Fourier transform of the correlation function of roughnesses between the interfaces.
Definition: ReSample.cpp:398
const MultiLayer & sample() const
Definition: ReSample.h:58

References DiffuseElement::addIntensity(), DiffuseElement::alphaMean(), reSample::avgeSlice(), MultiLayer::crossCorrLength(), reSample::crossCorrSpectralFun(), get_refractive_term(), get_sum8terms(), M_PI, m_re_sample, DiffuseElement::meanQ(), reSample::numberOfSlices(), reSample::sample(), LayerRoughness::spectralFunction(), Slice::topRoughness(), and DiffuseElement::wavelength().

Here is the call graph for this function:

◆ get_refractive_term()

complex_t RoughMultiLayerContribution::get_refractive_term ( size_t  i_layer,
double  wavelength 
) const
private

Definition at line 87 of file RoughMultiLayerContribution.cpp.

88 {
89  return m_re_sample.avgeSlice(i_layer).material().refractiveIndex2(wavelength)
90  - m_re_sample.avgeSlice(i_layer + 1).material().refractiveIndex2(wavelength);
91 }
complex_t refractiveIndex2(double wavelength) const
Returns squared refractive index.
Definition: Material.cpp:53
const Material & material() const
Definition: Slice.cpp:51

References reSample::avgeSlice(), m_re_sample, Slice::material(), and Material::refractiveIndex2().

Referenced by compute().

Here is the call graph for this function:

◆ get_sum8terms()

complex_t RoughMultiLayerContribution::get_sum8terms ( size_t  i_layer,
const DiffuseElement ele 
) const
private

Definition at line 93 of file RoughMultiLayerContribution.cpp.

95 {
96  const auto* in_plus = dynamic_cast<const ScalarFlux*>(ele.fluxIn(i_layer));
97  const auto* out_plus = dynamic_cast<const ScalarFlux*>(ele.fluxOut(i_layer));
98  const auto* in_minus = dynamic_cast<const ScalarFlux*>(ele.fluxIn(i_layer + 1));
99  const auto* out_minus = dynamic_cast<const ScalarFlux*>(ele.fluxOut(i_layer + 1));
100  ASSERT(in_plus && out_plus && in_minus && out_minus);
101 
102  const complex_t kiz_plus = in_plus->getScalarKz();
103  const complex_t kfz_plus = out_plus->getScalarKz();
104  const complex_t qz1_plus = -kiz_plus - kfz_plus;
105  const complex_t qz2_plus = -kiz_plus + kfz_plus;
106  const complex_t qz3_plus = -qz2_plus;
107  const complex_t qz4_plus = -qz1_plus;
108 
109  const double thickness = m_re_sample.avgeSlice(i_layer).thicknessOr0();
110  const complex_t T_in_plus = in_plus->getScalarT() * exp_I(kiz_plus * thickness);
111  const complex_t R_in_plus = in_plus->getScalarR() * exp_I(-kiz_plus * thickness);
112  const complex_t T_out_plus = out_plus->getScalarT() * exp_I(kfz_plus * thickness);
113  const complex_t R_out_plus = out_plus->getScalarR() * exp_I(-kfz_plus * thickness);
114 
115  const complex_t kiz_minus = in_minus->getScalarKz();
116  const complex_t kfz_minus = out_minus->getScalarKz();
117  const complex_t qz1_minus = -kiz_minus - kfz_minus;
118  const complex_t qz2_minus = -kiz_minus + kfz_minus;
119  const complex_t qz3_minus = -qz2_minus;
120  const complex_t qz4_minus = -qz1_minus;
121 
122  const LayerRoughness* roughness = m_re_sample.averageSlices().bottomRoughness(i_layer);
123  const double sigma = roughness ? roughness->sigma() : 0.;
124  const complex_t term1 = T_in_plus * T_out_plus * h_plus(qz1_plus * sigma);
125  const complex_t term2 = T_in_plus * R_out_plus * h_plus(qz2_plus * sigma);
126  const complex_t term3 = R_in_plus * T_out_plus * h_plus(qz3_plus * sigma);
127  const complex_t term4 = R_in_plus * R_out_plus * h_plus(qz4_plus * sigma);
128  const complex_t term5 =
129  in_minus->getScalarT() * out_minus->getScalarT() * h_min(qz1_minus * sigma);
130  const complex_t term6 =
131  in_minus->getScalarT() * out_minus->getScalarR() * h_min(qz2_minus * sigma);
132  const complex_t term7 =
133  in_minus->getScalarR() * out_minus->getScalarT() * h_min(qz3_minus * sigma);
134  const complex_t term8 =
135  in_minus->getScalarR() * out_minus->getScalarR() * h_min(qz4_minus * sigma);
136 
137  return term1 + term2 + term3 + term4 + term5 + term6 + term7 + term8;
138 }
#define ASSERT(condition)
Definition: Assert.h:45
const IFlux * fluxIn(size_t i_layer) const
const IFlux * fluxOut(size_t i_layer) const
double sigma() const
Returns rms of roughness.
Specular reflection and transmission coefficients in a layer in case of scalar interactions between t...
Definition: ScalarFlux.h:29
const LayerRoughness * bottomRoughness(size_t i_slice) const
Definition: SliceStack.cpp:75
double thicknessOr0() const
Definition: Slice.cpp:71
const SliceStack & averageSlices() const
Definition: ReSample.cpp:341

References ASSERT, reSample::averageSlices(), reSample::avgeSlice(), SliceStack::bottomRoughness(), DiffuseElement::fluxIn(), DiffuseElement::fluxOut(), m_re_sample, LayerRoughness::sigma(), and Slice::thicknessOr0().

Referenced by compute().

Here is the call graph for this function:

Member Data Documentation

◆ m_re_sample

const reSample& RoughMultiLayerContribution::m_re_sample
private

Definition at line 38 of file RoughMultiLayerContribution.h.

Referenced by compute(), get_refractive_term(), and get_sum8terms().


The documentation for this class was generated from the following files: