13 #include <Eigen/Dense> 
   21 void LArPcaHelper::RunPca(
const T &t, CartesianVector ¢roid, 
EigenValues &outputEigenValues, 
EigenVectors &outputEigenVectors)
 
   25     for (
const auto &point : t)
 
   26         weightedPointVector.push_back(std::make_pair(LArObjectHelper::TypeAdaptor::GetPosition(point), 1.));
 
   28     return LArPcaHelper::RunPca(weightedPointVector, centroid, outputEigenValues, outputEigenVectors);
 
   33 void LArPcaHelper::RunPca(
const WeightedPointVector &pointVector, CartesianVector ¢roid, EigenValues &outputEigenValues, EigenVectors &outputEigenVectors)
 
   42     if (pointVector.empty())
 
   44         std::cout << 
"LArPcaHelper::RunPca - no three dimensional hits provided" << std::endl;
 
   45         throw StatusCodeException(STATUS_CODE_NOT_FOUND);
 
   48     double meanPosition[3] = {0., 0., 0.};
 
   51     for (
const WeightedPoint &weightedPoint : pointVector)
 
   53         const CartesianVector &point(weightedPoint.first);
 
   54         const double weight(weightedPoint.second);
 
   58             std::cout << 
"LArPcaHelper::RunPca - negative weight found" << std::endl;
 
   59             throw StatusCodeException(STATUS_CODE_NOT_ALLOWED);
 
   62         meanPosition[0] += 
static_cast<double>(point.GetX()) * weight;
 
   63         meanPosition[1] += 
static_cast<double>(point.GetY()) * weight;
 
   64         meanPosition[2] += 
static_cast<double>(point.GetZ()) * weight;
 
   68     if (std::fabs(sumWeight) < std::numeric_limits<double>::epsilon())
 
   70         std::cout << 
"LArPcaHelper::RunPca - sum of weights is zero" << std::endl;
 
   71         throw StatusCodeException(STATUS_CODE_NOT_FOUND);
 
   74     meanPosition[0] /= sumWeight;
 
   75     meanPosition[1] /= sumWeight;
 
   76     meanPosition[2] /= sumWeight;
 
   77     centroid = CartesianVector(meanPosition[0], meanPosition[1], meanPosition[2]);
 
   87     for (
const WeightedPoint &weightedPoint : pointVector)
 
   89         const CartesianVector &point(weightedPoint.first);
 
   90         const double weight(weightedPoint.second);
 
   91         const double x(static_cast<double>((point.GetX()) - meanPosition[0]));
 
   92         const double y(static_cast<double>((point.GetY()) - meanPosition[1]));
 
   93         const double z(static_cast<double>((point.GetZ()) - meanPosition[2]));
 
   95         xi2 += 
x * 
x * weight;
 
   96         xiyi += 
x * 
y * weight;
 
   97         xizi += 
x * 
z * weight;
 
   98         yi2 += 
y * 
y * weight;
 
   99         yizi += 
y * 
z * weight;
 
  100         zi2 += 
z * 
z * weight;
 
  106     sig << xi2, xiyi, xizi, xiyi, yi2, yizi, xizi, yizi, zi2;
 
  108     sig *= 1. / sumWeight;
 
  110     Eigen::SelfAdjointEigenSolver<Eigen::Matrix3f> eigenMat(sig);
 
  112     if (eigenMat.info() != Eigen::ComputationInfo::Success)
 
  114         std::cout << 
"LArPcaHelper::RunPca - decomposition failure, nThreeDHits = " << pointVector.size() << std::endl;
 
  115         throw StatusCodeException(STATUS_CODE_INVALID_PARAMETER);
 
  118     typedef std::pair<float, size_t> EigenValColPair;
 
  119     typedef std::vector<EigenValColPair> EigenValColVector;
 
  121     EigenValColVector eigenValColVector;
 
  122     const auto &resultEigenMat(eigenMat.eigenvalues());
 
  123     eigenValColVector.emplace_back(resultEigenMat(0), 0);
 
  124     eigenValColVector.emplace_back(resultEigenMat(1), 1);
 
  125     eigenValColVector.emplace_back(resultEigenMat(2), 2);
 
  127     std::sort(eigenValColVector.begin(), eigenValColVector.end(),
 
  128         [](
const EigenValColPair &
left, 
const EigenValColPair &
right) { 
return left.first > 
right.first; });
 
  131     outputEigenValues = CartesianVector(eigenValColVector.at(0).first, eigenValColVector.at(1).first, eigenValColVector.at(2).first);
 
  134     const Eigen::Matrix3f &eigenVecs(eigenMat.eigenvectors());
 
  136     for (
const EigenValColPair &pair : eigenValColVector)
 
  137         outputEigenVectors.emplace_back(eigenVecs(0, pair.second), eigenVecs(1, pair.second), eigenVecs(2, pair.second));
 
  142 template void LArPcaHelper::RunPca(
const CartesianPointVector &, CartesianVector &, EigenValues &, EigenVectors &);
 
  143 template void LArPcaHelper::RunPca(
const CaloHitList &, CartesianVector &, EigenValues &, EigenVectors &);
 
process_name opflash particleana ie ie ie z
 
process_name opflash particleana ie x
 
pandora::CartesianVector EigenValues
 
std::vector< WeightedPoint > WeightedPointVector
 
Header file for the principal curve analysis helper class. 
 
process_name opflash particleana ie ie y
 
Header file for the object helper class. 
 
Header file for the cluster helper class. 
 
required by fuzzyCluster table::sbnd_g4_services gaushitTruthMatch pandora
 
std::vector< pandora::CartesianVector > EigenVectors
 
BEGIN_PROLOG could also be cout