PDFxTMDLib 2.0.0
Loading...
Searching...
No Matches
ICDPD.h
Go to the documentation of this file.
1#pragma once
2
3#include "PDFxTMDLib/Common/PartonUtils.h"
4
5#include <memory>
6#include <type_traits>
7#include <utility>
8
9namespace PDFxTMD
10{
11
28class ICDPD
29{
30 public:
31 template <typename DPDApproachT,
32 typename = std::enable_if_t<!std::is_same_v<std::decay_t<DPDApproachT>, ICDPD>>>
33 explicit ICDPD(DPDApproachT &&dpdApproach)
34 : pimpl_(
35 new OwningModel<std::decay_t<DPDApproachT>>(std::forward<DPDApproachT>(dpdApproach)),
36 [](void *dpdApproachBytes) {
37 using Model = OwningModel<std::decay_t<DPDApproachT>>;
38 auto *const model = static_cast<Model *>(dpdApproachBytes);
39 delete model;
40 }),
41 dpdOperation_([](void *dpdApproachBytes, PartonFlavor flavor1, PartonFlavor flavor2,
42 double x1, double mu1_2, double x2, double mu2_2) -> double {
43 using Model = OwningModel<std::decay_t<DPDApproachT>>;
44 auto *const model = static_cast<Model *>(dpdApproachBytes);
45
46 return model->dpd(flavor1, flavor2, x1, mu1_2, x2, mu2_2);
47 }),
48 clone_([](void *dpdApproachBytes) -> void * {
49 using Model = OwningModel<std::decay_t<DPDApproachT>>;
50 auto *const model = static_cast<Model *>(dpdApproachBytes);
51 return new Model(*model);
52 })
53 {
54 }
55
68 double dpd(PartonFlavor flavor1, PartonFlavor flavor2, double x1, double mu1_2, double x2,
69 double mu2_2) const
70 {
71 return dpdOperation_(pimpl_.get(), flavor1, flavor2, x1, mu1_2, x2, mu2_2);
72 }
73
74 ICDPD(const ICDPD &other)
75 : pimpl_(other.clone_(other.pimpl_.get()), other.pimpl_.get_deleter()),
76 clone_(other.clone_), dpdOperation_(other.dpdOperation_)
77 {
78 }
79
80 ICDPD &operator=(const ICDPD &other)
81 {
82 if (this == &other)
83 return *this;
84
85 ICDPD copy(other);
86
87 using std::swap;
88 swap(pimpl_, copy.pimpl_);
89 swap(clone_, copy.clone_);
90 swap(dpdOperation_, copy.dpdOperation_);
91
92 return *this;
93 }
94
95 ICDPD(ICDPD &&other) noexcept = default;
96 ICDPD &operator=(ICDPD &&other) noexcept = default;
97
98 ~ICDPD() = default;
99
100 private:
101 template <typename DPDApproachT> struct OwningModel
102 {
103 explicit OwningModel(DPDApproachT dpdApproach) : dpdApproach_(std::move(dpdApproach))
104 {
105 }
106
107 double dpd(PartonFlavor flavor1, PartonFlavor flavor2, double x1, double mu1_2, double x2,
108 double mu2_2)
109 {
110 return dpdApproach_.dpd(flavor1, flavor2, x1, mu1_2, x2, mu2_2);
111 }
112
113 DPDApproachT dpdApproach_;
114 };
115
116 using DestroyOperation = void(void *);
117 using CloneOperation = void *(void *);
118 using DPDOperation = double(void *, PartonFlavor, PartonFlavor, double, double, double, double);
119
120 std::unique_ptr<void, DestroyOperation *> pimpl_;
121 CloneOperation *clone_{nullptr};
122 DPDOperation *dpdOperation_{nullptr};
123};
124
125} // namespace PDFxTMD
Type-erased interface for collinear double parton distribution functions.
Definition ICDPD.h:29
ICDPD & operator=(ICDPD &&other) noexcept=default
double dpd(PartonFlavor flavor1, PartonFlavor flavor2, double x1, double mu1_2, double x2, double mu2_2) const
Evaluate the DPD for two flavors, two x values, and two scales.
Definition ICDPD.h:68
~ICDPD()=default
ICDPD(ICDPD &&other) noexcept=default
ICDPD(const ICDPD &other)
Definition ICDPD.h:74
ICDPD(DPDApproachT &&dpdApproach)
Definition ICDPD.h:33
ICDPD & operator=(const ICDPD &other)
Definition ICDPD.h:80
Definition Factory.h:9