Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-06-02 08:17:15

0001 //
0002 // APFEL++ 2017
0003 //
0004 // Author: Valerio Bertone: valerio.bertone@cern.ch
0005 //
0006 
0007 #include "apfel/apfelxx.h"
0008 #include "apfel/SIDIS.h"
0009 
0010 namespace apfel
0011 {
0012   /**
0013    * @brief Structure that contains the precomputed SIDIS polarised
0014    * hard cross sections.
0015    */
0016   struct SidisPolObjects
0017   {
0018     DoubleObject<Operator> G10qq;
0019     DoubleObject<Operator> G11qq;
0020     DoubleObject<Operator> G11gq;
0021     DoubleObject<Operator> G11qg;
0022     std::map<int, DoubleObject<Operator>> G12qq;
0023   };
0024 
0025   // Expressions needed for the computation of the SIDIS cross sections
0026   // F2
0027   class lrqqpol: public Expression
0028   {
0029   public:
0030     lrqqpol(): Expression() {}
0031     double Regular(double const& x) const
0032     {
0033       const double expr = ( 1 + x * x ) * log(x) / ( 1 - x ) + 1 - x - ( 1 + x ) * log( 1 - x );
0034       return 2 * CF * expr;
0035     }
0036   };
0037 
0038   class srqqpol: public Expression
0039   {
0040   public:
0041     srqqpol(): Expression() {}
0042     double Regular(double const& x) const { return - 2 * CF * ( 1 + x ); }
0043   };
0044 
0045   class rlqqpol: public Expression
0046   {
0047   public:
0048     rlqqpol(): Expression() {}
0049     double Regular(double const& x) const
0050     {
0051       const double expr = - ( 1 + x * x ) * log(x) / ( 1 - x ) + 1 - x - ( 1 + x ) * log( 1 - x );
0052       return 2 * CF * expr;
0053     }
0054   };
0055 
0056   class rsqqpol: public Expression
0057   {
0058   public:
0059     rsqqpol(): Expression() {}
0060     double Regular(double const& x) const { return - 2 * CF * ( 1 + x ); }
0061   };
0062 
0063   class r11qqpol: public Expression
0064   {
0065   public:
0066     r11qqpol(): Expression() {}
0067     double Regular(double const& x) const { return x; }
0068   };
0069 
0070   class r12qqpol: public Expression
0071   {
0072   public:
0073     r12qqpol(): Expression() {}
0074     double Regular(double const&) const { return 1; }
0075   };
0076 
0077   class r21qqpol: public Expression
0078   {
0079   public:
0080     r21qqpol(): Expression() {}
0081     double Regular(double const&) const { return 1; }
0082   };
0083 
0084   class r22qqpol: public Expression
0085   {
0086   public:
0087     r22qqpol(): Expression() {}
0088     double Regular(double const& x) const { return x; }
0089   };
0090 
0091   class lrgqpol: public Expression
0092   {
0093   public:
0094     lrgqpol(): Expression() {}
0095     double Regular(double const& x) const
0096     {
0097       const double omx = ( 1 - x );
0098       const double expr = ( 1 + omx * omx ) * log( x * omx ) / x + x;
0099       return 2 * CF * expr;
0100     }
0101   };
0102 
0103   class srgqpol: public Expression
0104   {
0105   public:
0106     srgqpol(): Expression() {}
0107     double Regular(double const& x) const
0108     {
0109       const double omx = ( 1 - x );
0110       const double expr = ( 1 + omx * omx ) / x;
0111       return 2 * CF * expr;
0112     }
0113   };
0114 
0115   class r11gqpol: public Expression
0116   {
0117   public:
0118     r11gqpol(): Expression() {}
0119     double Regular(double const& x) const { return 1 + x; }
0120   };
0121 
0122   class r12gqpol: public Expression
0123   {
0124   public:
0125     r12gqpol(): Expression() {}
0126     double Regular(double const& x) const { return 2 - 1 / x; }
0127   };
0128 
0129   class r21gqpol: public Expression
0130   {
0131   public:
0132     r21gqpol(): Expression() {}
0133     double Regular(double const&) const { return 1; }
0134   };
0135 
0136   class r22gqpol: public Expression
0137   {
0138   public:
0139     r22gqpol(): Expression() {}
0140     double Regular(double const& x) const { return x; }
0141   };
0142 
0143   class rlqgpol: public Expression
0144   {
0145   public:
0146     rlqgpol(): Expression() {}
0147     double Regular(double const& x) const
0148     {
0149       const double omx = ( 1 - x );
0150       const double expr = ( x * x - omx * omx ) * log( omx / x ) + 2 * omx;
0151       return expr;
0152     }
0153   };
0154 
0155   class rsqgpol: public Expression
0156   {
0157   public:
0158     rsqgpol(): Expression() {}
0159     double Regular(double const& x) const
0160     {
0161       const double omx = ( 1 - x );
0162       const double expr = ( x * x - omx * omx );
0163       return expr;
0164     }
0165   };
0166 
0167   class r11qgpol: public Expression
0168   {
0169   public:
0170     r11qgpol(): Expression() {}
0171     double Regular(double const& x) const { return x * x - ( 1 - x ) * ( 1 - x ); }
0172   };
0173 
0174   class r12qgpol: public Expression
0175   {
0176   public:
0177     r12qgpol(): Expression() {}
0178     double Regular(double const& x) const { return 1 / x - 2; }
0179   };
0180 
0181   // Functions that fills in the SIDIS hard cross sections on two
0182   // different grids.
0183   SidisPolObjects InitializeSIDISpol(Grid const& gx, Grid const& gz, std::vector<double> const& Thresholds, std::vector<int> exclude = {})
0184   {
0185     report("Initializing SIDIS longitudinally polarised hard cross sections... ");
0186     Timer t;
0187 
0188     // Compute initial and final number of active flavours according
0189     // to the vector of thresholds (it assumes that the threshold
0190     // vector entries are ordered).
0191     int nfi = 0;
0192     int nff = Thresholds.size();
0193     for (auto const& v : Thresholds)
0194       if (v <= 0)
0195         nfi++;
0196 
0197     // Define object of the structure containing the DglapObjects.
0198     SidisPolObjects SidisObj;
0199 
0200     // ====================================================
0201     // Compute SIDIS partonic cross sections.
0202     // Expressions taken from Appendix C of hep-ph/9711387.
0203     // ====================================================
0204     // LO contribution
0205     const Operator odeltax{gx, delta{}};
0206     const Operator odeltaz{gz, delta{}};
0207 
0208     if (std::find(exclude.begin(), exclude.end(), 0) == exclude.end()) SidisObj.G10qq.AddTerm({1, odeltax, odeltaz});
0209 
0210     // NLO contributions
0211     // G1
0212     const Operator oD0x{gx, DDn{0}};
0213     const Operator oD1x{gx, DDn{1}};
0214     const Operator oD0z{gz, DDn{0}};
0215     const Operator oD1z{gz, DDn{1}};
0216 
0217     const double LLqq = - 16 * CF;
0218     const double LSqq = 4 * CF;
0219     const double SLqq = 4 * CF;
0220     const double SSqq = 4 * CF;
0221     const double K1qq = 4 * CF;
0222     const double K2qq = 4 * CF;
0223 
0224     const Operator orlqqx{gx,  rlqqpol{}};
0225     const Operator orsqqx{gx,  rsqqpol{}};
0226     const Operator or11qqx{gx, r11qqpol{}};
0227     const Operator or21qqx{gx, r21qqpol{}};
0228     const Operator olrqqz{gz,  lrqqpol{}};
0229     const Operator osrqqz{gz,  srqqpol{}};
0230     const Operator or12qqz{gz, r12qqpol{}};
0231     const Operator or22qqz{gz, r22qqpol{}};
0232 
0233     if (std::find(exclude.begin(), exclude.end(), 1)  == exclude.end()) SidisObj.G11qq.AddTerm({LLqq, odeltax, odeltaz});
0234     if (std::find(exclude.begin(), exclude.end(), 2)  == exclude.end()) SidisObj.G11qq.AddTerm({LSqq, odeltax, oD1z   });
0235     if (std::find(exclude.begin(), exclude.end(), 3)  == exclude.end()) SidisObj.G11qq.AddTerm({1,    odeltax, olrqqz });
0236     if (std::find(exclude.begin(), exclude.end(), 4)  == exclude.end()) SidisObj.G11qq.AddTerm({SLqq, oD1x,    odeltaz});
0237     if (std::find(exclude.begin(), exclude.end(), 5)  == exclude.end()) SidisObj.G11qq.AddTerm({SSqq, oD0x,    oD0z   });
0238     if (std::find(exclude.begin(), exclude.end(), 6)  == exclude.end()) SidisObj.G11qq.AddTerm({1,    oD0x,    osrqqz });
0239     if (std::find(exclude.begin(), exclude.end(), 7)  == exclude.end()) SidisObj.G11qq.AddTerm({1,    orlqqx,  odeltaz});
0240     if (std::find(exclude.begin(), exclude.end(), 8)  == exclude.end()) SidisObj.G11qq.AddTerm({1,    orsqqx,  oD0z   });
0241     if (std::find(exclude.begin(), exclude.end(), 9)  == exclude.end()) SidisObj.G11qq.AddTerm({K1qq, or11qqx, or12qqz});
0242     if (std::find(exclude.begin(), exclude.end(), 10) == exclude.end()) SidisObj.G11qq.AddTerm({K2qq, or21qqx, or22qqz});
0243 
0244     const double K1gq = 2 * CF;
0245     const double K2gq = - 4 * CF;
0246 
0247     const Operator olrgqz{gz,  lrgqpol{}};
0248     const Operator osrgqz{gz,  srgqpol{}};
0249     const Operator or11gqx{gx, r11gqpol{}};
0250     const Operator or12gqz{gz, r12gqpol{}};
0251     const Operator or21gqx{gx, r21gqpol{}};
0252     const Operator or22gqz{gz, r22gqpol{}};
0253 
0254     if (std::find(exclude.begin(), exclude.end(), 11) == exclude.end()) SidisObj.G11gq.AddTerm({1,    odeltax, olrgqz });
0255     if (std::find(exclude.begin(), exclude.end(), 12) == exclude.end()) SidisObj.G11gq.AddTerm({1,    oD0x,    osrgqz });
0256     if (std::find(exclude.begin(), exclude.end(), 13) == exclude.end()) SidisObj.G11gq.AddTerm({K1gq, or11gqx, or12gqz});
0257     if (std::find(exclude.begin(), exclude.end(), 14) == exclude.end()) SidisObj.G11gq.AddTerm({K2gq, or21gqx, or22gqz});
0258 
0259     const double K1qg = 1;
0260 
0261     const Operator orlqgx{gx,  rlqgpol{}};
0262     const Operator orsqgx{gx,  rsqgpol{}};
0263     const Operator or11qgx{gx, r11qgpol{}};
0264     const Operator or12qgz{gz, r12qgpol{}};
0265 
0266     if (std::find(exclude.begin(), exclude.end(), 15) == exclude.end()) SidisObj.G11qg.AddTerm({1,    orlqgx,  odeltaz});
0267     if (std::find(exclude.begin(), exclude.end(), 16) == exclude.end()) SidisObj.G11qg.AddTerm({1,    orsqgx,  oD0z   });
0268     if (std::find(exclude.begin(), exclude.end(), 17) == exclude.end()) SidisObj.G11qg.AddTerm({K1qg, or11qgx, or12qgz});
0269 
0270     // ====================================================
0271     // Approximated NNLO corrections derived from threshold
0272     // resummation. They only contribute to the qq channel of g1.
0273     // Expressions taken from Appendix B of arXiv:2109.00847.
0274     // ====================================================
0275     // Additional singular terms
0276     const Operator oD2x{gx, DDn{2}};
0277     const Operator oD3x{gx, DDn{3}};
0278     const Operator oD2z{gz, DDn{2}};
0279     const Operator oD3z{gz, DDn{3}};
0280 
0281     // Non-singular (next-to-leading power) terms
0282     const Operator ol1x{gx, ln{1}};
0283     const Operator ol2x{gx, ln{2}};
0284     const Operator ol3x{gx, ln{3}};
0285     const Operator ol1z{gz, ln{1}};
0286     const Operator ol2z{gz, ln{2}};
0287     const Operator ol3z{gz, ln{3}};
0288 
0289     // Constant function
0290     const Operator oonex{gx, one{}};
0291     const Operator oonez{gz, one{}};
0292 
0293     // Overall constant (16 = 4^2 due to the different normalisation
0294     // of the expansion parameter)
0295     const double ovc = 16. * CF;
0296 
0297     // Loop over nf
0298     for (int nf = nfi; nf <= nff; nf++)
0299       {
0300         DoubleObject<Operator> cnf{};
0301 
0302         // CF and leading-power terms (Eq. (62))
0303         const double c1 = ovc * CF / 2.;
0304         if (std::find(exclude.begin(), exclude.end(), 18) == exclude.end()) cnf.AddTerm({c1, odeltax, oD3z});
0305         if (std::find(exclude.begin(), exclude.end(), 19) == exclude.end()) cnf.AddTerm({c1, oD3x, odeltaz});
0306 
0307         const double c2 = ovc * CF * 3. / 2.;
0308         if (std::find(exclude.begin(), exclude.end(), 20) == exclude.end()) cnf.AddTerm({c2, oD0x, oD2z});
0309         if (std::find(exclude.begin(), exclude.end(), 21) == exclude.end()) cnf.AddTerm({c2, oD2x, oD0z});
0310         if (std::find(exclude.begin(), exclude.end(), 22) == exclude.end()) cnf.AddTerm({2 * c2, oD1x, oD1z});
0311 
0312         const double c3 = - ovc * CF * ( 4. + Pi2 / 3. );
0313         if (std::find(exclude.begin(), exclude.end(), 23) == exclude.end()) cnf.AddTerm({c3, oD0x, oD0z});
0314         if (std::find(exclude.begin(), exclude.end(), 24) == exclude.end()) cnf.AddTerm({c3, odeltax, oD1z});
0315         if (std::find(exclude.begin(), exclude.end(), 25) == exclude.end()) cnf.AddTerm({c3, oD1x, odeltaz});
0316 
0317         const double c4 = ovc * CF * 2. * zeta3;
0318         if (std::find(exclude.begin(), exclude.end(), 26) == exclude.end()) cnf.AddTerm({c4, odeltax, oD0z});
0319         if (std::find(exclude.begin(), exclude.end(), 27) == exclude.end()) cnf.AddTerm({c4, oD0x, odeltaz});
0320 
0321         const double c5 = ovc * CF * ( 511. / 64. - 15. * zeta3 / 4. + 29. * Pi2 / 48. - 7. * Pi2 * Pi2 / 360. );
0322         if (std::find(exclude.begin(), exclude.end(), 28) == exclude.end()) cnf.AddTerm({c5, odeltax, odeltaz});
0323 
0324         // CF and next-to-leading-power terms (Eq. (63))
0325         const double c6 = - ovc * CF * 3. / 2.;
0326         if (std::find(exclude.begin(), exclude.end(), 29) == exclude.end()) cnf.AddTerm({c6, oD2x, oonez});
0327         if (std::find(exclude.begin(), exclude.end(), 30) == exclude.end()) cnf.AddTerm({c6, oonex, oD2z});
0328         if (std::find(exclude.begin(), exclude.end(), 31) == exclude.end()) cnf.AddTerm({2 * c6, oD1x, ol1z});
0329         if (std::find(exclude.begin(), exclude.end(), 32) == exclude.end()) cnf.AddTerm({2 * c6, ol1x, oD1z});
0330         if (std::find(exclude.begin(), exclude.end(), 33) == exclude.end()) cnf.AddTerm({c6, oD0x, ol2z});
0331         if (std::find(exclude.begin(), exclude.end(), 34) == exclude.end()) cnf.AddTerm({c6, ol2x, oD0z});
0332 
0333         const double c7 = - ovc * CF / 2.;
0334         if (std::find(exclude.begin(), exclude.end(), 35) == exclude.end()) cnf.AddTerm({c7, odeltax, ol3z});
0335         if (std::find(exclude.begin(), exclude.end(), 36) == exclude.end()) cnf.AddTerm({c7, ol3x, odeltaz});
0336 
0337         // CA terms (Eq. (64))
0338         const double c8 = - ovc * CA * 11. / 24.;
0339         if (std::find(exclude.begin(), exclude.end(), 37) == exclude.end()) cnf.AddTerm({c8, odeltax, oD2z});
0340         if (std::find(exclude.begin(), exclude.end(), 38) == exclude.end()) cnf.AddTerm({c8, oD2x, odeltaz});
0341         if (std::find(exclude.begin(), exclude.end(), 39) == exclude.end()) cnf.AddTerm({2 * c8, oD0x, oD1z});
0342         if (std::find(exclude.begin(), exclude.end(), 40) == exclude.end()) cnf.AddTerm({2 * c8, oD1x, oD0z});
0343 
0344         const double c9 = ovc * CA * ( 67. / 36. - Pi2 / 12. );
0345         if (std::find(exclude.begin(), exclude.end(), 41) == exclude.end()) cnf.AddTerm({c9, oD0x, oD0z});
0346         if (std::find(exclude.begin(), exclude.end(), 42) == exclude.end()) cnf.AddTerm({c9, odeltax, oD1z});
0347         if (std::find(exclude.begin(), exclude.end(), 43) == exclude.end()) cnf.AddTerm({c9, oD1x, odeltaz});
0348 
0349         const double c10 = ovc * CA * ( 7. * zeta3 / 4. + 11. * Pi2 / 72. - 101. / 54. );
0350         if (std::find(exclude.begin(), exclude.end(), 44) == exclude.end()) cnf.AddTerm({c10, odeltax, oD0z});
0351         if (std::find(exclude.begin(), exclude.end(), 45) == exclude.end()) cnf.AddTerm({c10, oD0x, odeltaz});
0352 
0353         const double c11 = ovc * CA * ( 43. * zeta3 / 12. + 17. * Pi2 * Pi2 / 720. - 1535. / 192. - 269. * Pi2 / 432. );
0354         if (std::find(exclude.begin(), exclude.end(), 46) == exclude.end()) cnf.AddTerm({c11, odeltax, odeltaz});
0355 
0356         // nf terms (Eq. (65))
0357         const double c12 = ovc * nf / 12.;
0358         if (std::find(exclude.begin(), exclude.end(), 47) == exclude.end()) cnf.AddTerm({c12, odeltax, oD2z});
0359         if (std::find(exclude.begin(), exclude.end(), 48) == exclude.end()) cnf.AddTerm({c12, oD2x, odeltaz});
0360         if (std::find(exclude.begin(), exclude.end(), 49) == exclude.end()) cnf.AddTerm({2 * c12, oD0x, oD1z});
0361         if (std::find(exclude.begin(), exclude.end(), 50) == exclude.end()) cnf.AddTerm({2 * c12, oD1x, oD0z});
0362 
0363         const double c13 = - ovc * nf * 5. / 18.;
0364         if (std::find(exclude.begin(), exclude.end(), 51) == exclude.end()) cnf.AddTerm({c13, oD0x, oD0z});
0365         if (std::find(exclude.begin(), exclude.end(), 52) == exclude.end()) cnf.AddTerm({c13, odeltax, oD1z});
0366         if (std::find(exclude.begin(), exclude.end(), 53) == exclude.end()) cnf.AddTerm({c13, oD1x, odeltaz});
0367 
0368         const double c14 = ovc * nf * ( 7. / 27. - Pi2 / 36. );
0369         if (std::find(exclude.begin(), exclude.end(), 54) == exclude.end()) cnf.AddTerm({c14, odeltax, oD0z});
0370         if (std::find(exclude.begin(), exclude.end(), 55) == exclude.end()) cnf.AddTerm({c14, oD0x, odeltaz});
0371 
0372         const double c15 = ovc * nf * ( zeta3 / 6. + 19. * Pi2 / 216. + 127. / 96. );
0373         if (std::find(exclude.begin(), exclude.end(), 56) == exclude.end()) cnf.AddTerm({c15, odeltax, odeltaz});
0374 
0375         SidisObj.G12qq.insert({nf, cnf});
0376       }
0377     t.stop();
0378 
0379     return SidisObj;
0380   }
0381 
0382   // Functions that fills in the SIDIS hard cross sections on one
0383   // single grid and exchanges the last defaulted arguments.
0384   SidisPolObjects InitializeSIDISpol(Grid const& gx, std::vector<double> const& Thresholds, std::vector<int> exclude = {})
0385   {
0386     return InitializeSIDISpol(gx, gx, Thresholds, exclude);
0387   }
0388 }