17#ifndef ROOT_Math_KDTree
18#error "Do not use KDTree.icc directly. #include \"KDTree.h\" instead."
32 template<
class _DataPo
int>
59 template<
class _DataPo
int>
71 template<
class _DataPo
int>
84 template<
class _DataPo
int>
102 template<
class _DataPo
int>
116 template<
class _DataPo
int>
130 template<
class _DataPo
int>
141 assert(
dynamic_cast<BinNode*
>(pNode));
146 template<
class _DataPo
int>
157 assert(
dynamic_cast<BinNode*
>(pNode));
162 template<
class _DataPo
int>
180 std::vector<TerminalNode*> vBins;
183 vBins.push_back(it.TN());
186 for(
typename std::vector<TerminalNode*>::iterator bit = vBins.begin(); bit != vBins.end(); ++bit)
188 pBin = (*bit)->ConvertToBinNode();
199 template<
class _DataPo
int>
201 std::vector<std::pair<const _DataPoint*,Double_t> >& vFoundPoints)
const
219 fHead->GetClosestPoints(rRef,nPoints,vFoundPoints);
223 template<
class _DataPo
int>
234 fSumw += it->GetBinContent();
235 fSumw2 += it->GetSumw2();
238 return ((fSumw2) ? fSumw * fSumw / fSumw2 : 0);
242 template<
class _DataPo
int>
249 iPoints += it->GetEntries();
255 template<
class _DataPo
int>
272 template<
class _DataPo
int>
285 template<
class _DataPo
int>
287 std::vector<const _DataPoint*>& vFoundPoints)
const
303 fHead->GetPointsWithinDist(rRef,fDist,vFoundPoints);
307 template<
class _DataPo
int>
314 fSumw += it->GetSumw();
320 template<
class _DataPo
int>
327 fSumw2 += it->GetSumw2();
333 template<
class _DataPo
int>
349 template<
class _DataPo
int>
360 assert(
dynamic_cast<BinNode*
>(pNode));
365 template<
class _DataPo
int>
379 delete fHead->Parent();
383 fHead->Parent() = pTerminal;
390 template<
class _DataPo
int>
404 it.TN()->SetOwner(bIsOwner);
409 template<
class _DataPo
int>
427 it.TN()->SetSplitOption(opt);
432 template<
class _DataPo
int>
451 return (pFirst->GetCoordinate(
fAxis) < pSecond->GetCoordinate(
fAxis));
455 template<
class _DataPo
int>
475 template<
class _DataPo
int>
495 template<
class _DataPo
int>
505 template<
class _DataPo
int>
519 template<
class _DataPo
int>
529 return Parent()->Parent();
531 return Parent()->LeftChild();
533 return Parent()->RightChild();
541 template<
class _DataPo
int>
555 template<
class _DataPo
int>
565 pParent->
Parent() = pHead;
571 template<
class _DataPo
int>
573 std::vector<std::pair<const _DataPoint*,Double_t> >& vFoundPoints)
const
575 Parent()->GetClosestPoints(rRef,nPoints,vFoundPoints);
579 template<
class _DataPo
int>
581 std::vector<const _DataPoint*>& vFoundPoints)
const
583 Parent()->GetPointsWithinDist(rRef,fDist,vFoundPoints);
587 template<
class _DataPo
int>
609 template<
class _DataPo
int>
618 template<
class _DataPo
int>
631 pRight->
Parent() = pSplit;
637 template<
class _DataPo
int>
644 return this->
LeftChild()->FindNode(rPoint);
651 template<
class _DataPo
int>
653 std::vector<std::pair<const _DataPoint*,Double_t> >& vFoundPoints)
const
666 this->
LeftChild()->GetClosestPoints(rRef,nPoints,vFoundPoints);
671 if((vFoundPoints.size() < nPoints) || (vFoundPoints.back().second >
fabs(rRef.GetCoordinate(
fCut->GetAxis()) -
fCut->GetCutValue())))
672 this->
RightChild()->GetClosestPoints(rRef,nPoints,vFoundPoints);
677 this->
RightChild()->GetClosestPoints(rRef,nPoints,vFoundPoints);
682 if((vFoundPoints.size() < nPoints) || (vFoundPoints.back().second >
fabs(rRef.GetCoordinate(
fCut->GetAxis()) -
fCut->GetCutValue())))
683 this->
LeftChild()->GetClosestPoints(rRef,nPoints,vFoundPoints);
688 template<
class _DataPo
int>
690 std::vector<const _DataPoint*>& vFoundPoints)
const
702 if(
fabs(rRef.GetCoordinate(
fCut->GetAxis()) -
fCut->GetCutValue()) > fDist)
706 this->
LeftChild()->GetPointsWithinDist(rRef,fDist,vFoundPoints);
709 this->
RightChild()->GetPointsWithinDist(rRef,fDist,vFoundPoints);
714 this->
RightChild()->GetPointsWithinDist(rRef,fDist,vFoundPoints);
715 this->
LeftChild()->GetPointsWithinDist(rRef,fDist,vFoundPoints);
720 template<
class _DataPo
int>
727 return this->
LeftChild()->Insert(rPoint);
734 template<
class _DataPo
int>
739 std::cout <<
"SplitNode at " <<
this <<
" in row " << iRow << std::endl;
740 std::cout <<
"cut on " <<
fCut->GetCutValue() <<
" at axis " <<
fCut->GetAxis() << std::endl;
747 template<
class _DataPo
int>
759 template<
class _DataPo
int>
778 template<
class _DataPo
int>
787 template<
class _DataPo
int>
797 template<
class _DataPo
int>
813 template<
class _DataPo
int>
825 template<
class _DataPo
int>
842 template<
class _DataPo
int>
851 for(
typename std::vector<tBoundary>::const_iterator it =
fBoundaries.begin(); it !=
fBoundaries.end(); ++it)
852 dVol *= (it->second - it->first);
859 template<
class _DataPo
int>
867 fSumw += rPoint.GetWeight();
868 fSumw2 += pow(rPoint.GetWeight(),2);
877 template<
class _DataPo
int>
883 if((rPoint.GetCoordinate(k) <
fBoundaries.at(k).first) || (
fBoundaries.at(k).second < rPoint.GetCoordinate(k)))
890 template<
class _DataPo
int>
895 std::cout <<
"BinNode at " <<
this << std::endl;
896 std::cout <<
"containing " <<
GetEntries() <<
" entries" << std::endl;
898 std::cout <<
"volume = " <<
GetVolume() <<
" and bin center at (";
902 std::cout << rBinCenter.GetCoordinate(
dim);
906 std::cout <<
")" << std::endl;
907 std::cout <<
"boundaries are ";
908 for(
typename std::vector<tBoundary>::const_iterator it =
fBoundaries.begin(); it !=
fBoundaries.end(); ++it)
909 std::cout <<
"(" << it->first <<
" ... " << it->second <<
") ";
910 std::cout << std::endl;
914 template<
class _DataPo
int>
935 template<
class _DataPo
int>
954 this->fSumw += (*it)->GetWeight();
955 this->fSumw2 += pow((*it)->GetWeight(),2);
962 template<
class _DataPo
int>
971 for(
typename std::vector<const _DataPoint*>::iterator it =
fDataPoints.begin();
978 template<
class _DataPo
int>
995 template<
class _DataPo
int>
1005 for(
typename std::vector<const _DataPoint*>::iterator it =
fDataPoints.begin();
1014 template<
class _DataPo
int>
1039 template<
class _DataPo
int>
1041 std::vector<std::pair<const _DataPoint*,Double_t> >& vFoundPoints)
const
1052 value_type fMaxDist = (vFoundPoints.size() < nPoints) ? std::numeric_limits<value_type>::max() : vFoundPoints.back().second;
1054 typedef typename std::vector<std::pair<const _DataPoint*,Double_t> >
::iterator t_pit;
1057 for(
typename std::vector<const _DataPoint*>::const_iterator it =
fDataPoints.begin(); it !=
fDataPoints.end(); ++it)
1059 fDist = (*it)->Distance(rRef);
1061 if(fDist < fMaxDist)
1064 t_pit pit = vFoundPoints.begin();
1065 while(pit != vFoundPoints.end())
1067 if(pit->second > fDist)
1073 vFoundPoints.insert(pit,std::make_pair(*it,fDist));
1075 if(vFoundPoints.size() > nPoints)
1076 vFoundPoints.resize(nPoints);
1078 fMaxDist = (vFoundPoints.size() < nPoints) ? vFoundPoints.back().second : std::numeric_limits<value_type>::max();
1084 template<
class _DataPo
int>
1086 std::vector<const _DataPoint*>& vFoundPoints)
const
1097 for(
typename std::vector<const _DataPoint*>::const_iterator it =
fDataPoints.begin(); it !=
fDataPoints.end(); ++it)
1099 if((*it)->Distance(rRef) <= fDist)
1100 vFoundPoints.push_back(*it);
1105 template<
class _DataPo
int>
1117 this->
fSumw += rPoint.GetWeight();
1118 this->
fSumw2 += pow(rPoint.GetWeight(),2);
1132 default: assert(
false);
1139 template<
class _DataPo
int>
1144 std::cout <<
"TerminalNode at " <<
this <<
" in row " << iRow << std::endl;
1147 std::cout <<
"next split axis: " <<
fSplitAxis << std::endl << std::endl;
1153 std::cout << (*it)->GetCoordinate(i);
1157 std::cout <<
"), w = " << (*it)->GetWeight() << std::endl;
1160 std::cout << std::endl;
1164 template<
class _DataPo
int>
1193 default: assert(
false);
1210 this->
fSumw += (*it)->GetWeight();
1211 this->
fSumw2 += pow((*it)->GetWeight(),2);
1235 template<
class _DataPo
int>
1259 while(((fSumwTemp * fSumwTemp)/fSumw2Temp < fEffective/2) && (step > 1))
1261 middle = first + (++step /= 2);
1262 std::partial_sort(first,middle,
fDataPoints.end(),cComp);
1264 while(((fSumwTemp * fSumwTemp)/fSumw2Temp < fEffective/2) && (cut != middle-1))
1266 fSumwTemp += (*cut)->GetWeight();
1267 fSumw2Temp += pow((*cut)->GetWeight(),2);
1277 template<
class _DataPo
int>
1300 while((fSumwTemp < fBinContent/2) && (step > 1))
1302 middle = first + (++step /= 2);
1303 std::partial_sort(first,middle,
fDataPoints.end(),cComp);
1305 while((fSumwTemp < fBinContent/2) && (cut != middle-1))
1307 fSumwTemp += (*cut)->GetWeight();
1317 template<
class _DataPo
int>
1333 const value_type fMAX = 0.4 * std::numeric_limits<value_type>::max();
1341 const Cut* pCut = 0;
1345 pSplit =
dynamic_cast<const SplitNode*
>(pNode);
1370 for(
typename std::vector<const _DataPoint*>::const_iterator it =
fDataPoints.begin();
1373 if((*it)->GetCoordinate(
dim) < this->fBoundaries.at(
dim).first)
1382 for(
typename std::vector<const _DataPoint*>::const_iterator it =
fDataPoints.begin();
1385 if((*it)->GetCoordinate(
dim) > this->fBoundaries.at(
dim).second)
1394 template<
class _DataPo
int>
1404 template<
class _DataPo
int>
1414 template<
class _DataPo
int>
1425 template<
class _DataPo
int>
1436 template<
class _DataPo
int>
1446 template<
class _DataPo
int>
1456 template<
class _DataPo
int>
1467 template<
class _DataPo
int>
1478 template<
class _DataPo
int>
1488 template<
class _DataPo
int>
1506 assert(
dynamic_cast<BinNode*
>(pNode));
1517 template<
class _DataPo
int>
1535 assert(
dynamic_cast<BinNode*
>(pNode));
unsigned int UInt_t
Unsigned integer 4 bytes (unsigned int).
bool Bool_t
Boolean (0=false, 1=true) (bool).
double Double_t
Double 8 bytes.
BaseNode *& GetParentPointer()
BaseNode * fParent
!pointer to parent node
Bool_t IsLeftChild() const
BaseNode * fRightChild
!pointer to right child
virtual Bool_t IsHeadNode() const
BaseNode(BaseNode *pParent=0)
BaseNode * fLeftChild
!pointer to left child
void Print(int iRow=0) const override
virtual const std::vector< tBoundary > & GetBoundaries() const
std::vector< tBoundary > fBoundaries
bin boundaries
BinNode * Clone() override
BinNode(BaseNode *pParent=0)
point_type GetBinCenter() const
Double_t GetSumw2() const
std::pair< value_type, value_type > tBoundary
Bool_t IsInBin(const point_type &rPoint) const
BinNode & operator=(const BinNode &rhs)
Double_t fSumw2
sum of weights^2
const BinNode * FindNode(const point_type &rPoint) const override
UInt_t fEntries
number of entries
Bool_t Insert(const point_type &rPoint) override
Double_t fSumw
sum of weights
Double_t GetBinContent() const
Double_t GetVolume() const
Bool_t operator()(const point_type *pFirst, const point_type *pSecond) const
void SetAxis(UInt_t iAxis)
value_type GetCutValue() const
Bool_t operator>(const point_type &rPoint) const
Bool_t operator<(const point_type &rPoint) const
void GetPointsWithinDist(const point_type &rRef, value_type fDist, std::vector< const _DataPoint * > &vFoundPoints) const override
void GetClosestPoints(const point_type &rRef, UInt_t nPoints, std::vector< std::pair< const _DataPoint *, Double_t > > &vFoundPoints) const override
HeadNode(BaseNode &rNode)
HeadNode * Clone() override
Bool_t Insert(const point_type &rPoint) override
SplitNode(UInt_t iAxis, Double_t fCutValue, BaseNode &rLeft, BaseNode &rRight, BaseNode *pParent=0)
void Print(Int_t iRow=0) const override
SplitNode * Clone() override
const BinNode * FindNode(const point_type &rPoint) const override
const Cut * GetCut() const
void GetClosestPoints(const point_type &rRef, UInt_t nPoints, std::vector< std::pair< const _DataPoint *, Double_t > > &vFoundPoints) const override
void GetPointsWithinDist(const point_type &rRef, value_type fDist, std::vector< const _DataPoint * > &vFoundPoints) const override
Bool_t Insert(const point_type &rPoint) override
data_it SplitBinContent()
std::vector< constpoint_type * >::iterator data_it
Double_t fBucketSize
target number of entries per bucket
void SetOwner(Bool_t bIsOwner=true)
void SetSplitOption(eSplitOption opt)
Bool_t fOwnData
terminal node owns the data objects (default = false)
BinNode * ConvertToBinNode()
TerminalNode(Double_t iBucketSize, BaseNode *pParent=0)
std::vector< constpoint_type * >::const_iterator const_data_it
const std::vector< tBoundary > & GetBoundaries() const override
UInt_t fSplitAxis
axis at which the next split will occur
void Print(int iRow=0) const override
void GetPointsWithinDist(const point_type &rRef, value_type fDist, std::vector< const _DataPoint * > &vFoundPoints) const override
data_it SplitEffectiveEntries()
void GetClosestPoints(const point_type &rRef, UInt_t nPoints, std::vector< std::pair< const _DataPoint *, Double_t > > &vFoundPoints) const override
std::vector< const _DataPoint * > fDataPoints
data points in this bucket
eSplitOption fSplitOption
according to which figure of merit the node is split
iterator & operator=(const iterator &rhs)
Double_t GetTotalSumw2() const
void SetOwner(Bool_t bIsOwner=true)
KDTree< _DataPoint > * GetFrozenCopy()
Double_t GetTotalSumw() const
_DataPoint::value_type value_type
UInt_t GetEntries() const
void GetPointsWithinDist(const point_type &rRef, value_type fDist, std::vector< const point_type * > &vFoundPoints) const
Double_t GetEffectiveEntries() const
void SetSplitOption(eSplitOption opt)
void GetClosestPoints(const point_type &rRef, UInt_t nPoints, std::vector< std::pair< const _DataPoint *, Double_t > > &vFoundPoints) const
static UInt_t Dimension()
KDTree(UInt_t iBucketSize)
Namespace for new Math classes and functions.
VecExpr< UnaryOp< Fabs< T >, VecExpr< A, T, D >, T >, T, D > fabs(const VecExpr< A, T, D > &rhs)
std::vector< std::string > Split(std::string_view str, std::string_view delims, bool skipEmpty=false)
Splits a string at each character in delims.