У меня есть реализация случайного леса в C++, который я запускаю в matlab через mex. Он работает плавно, пока не достигнет функции ниже, где она застревает и начинает потреблять память, пока компьютер не замерзнет.утечка памяти, вероятно, из-за рекурсивной функции
void MyFunction(
const IDataPointCollection& data,
std::vector<std::vector<int> >& leafNodeIndices,
ProgressStream* progress=0) const
{
ProgressStream defaultProgressStream(std::cout, Interest);
progress = (progress==0)?&defaultProgressStream:progress;
leafNodeIndices.resize(TreeCount());
tbb::parallel_for<int>(0,TreeCount(),[&](int t)
{
leafNodeIndices[t].resize(data.Count());
(*progress)[Interest] << "\rApplying tree " << t << "...";
trees_[t]->Apply(data, leafNodeIndices[t]);
});
(*progress)[Interest] << "STUCK HERE" << std::endl;
return;
}
Переход через код для trees_[t]->Apply()
выше, я был в состоянии сузить ее до рекурсивной функции ниже:
void ApplyNode(
int nodeIndex,
const IDataPointCollection& data,
std::vector<unsigned int>& dataIndices,
int i0,
int i1,
std::vector<int>& leafNodeIndices,
std::vector<float>& responses_)
{
std::cout<<"applying node"<<std::endl;
assert(nodes_[nodeIndex].IsNull()==false);
Node<F,S>& node = nodes_[nodeIndex];
if (node.IsLeaf())
{
for (int i = i0; i < i1; i++)
leafNodeIndices[dataIndices[i]] = nodeIndex;
return;
}
else if (i0 == i1) // No samples left
return;
else
{
for (int i = i0; i < i1; i++)
responses_[i] = node.Feature.GetResponse(data, dataIndices[i]);
int ii = Partition(responses_, dataIndices, i0, i1, node.Threshold);
// Recurse for child nodes.
ApplyNode(nodeIndex * 2 + 1, data, dataIndices, i0, ii, leafNodeIndices, responses_);
ApplyNode(nodeIndex * 2 + 2, data, dataIndices, ii, i1, leafNodeIndices, responses_);
return;
}
}
Каждый вызов рекурсивной функции имеет разное время вычисления в зависимости от node.Feature.GetResponse()
функции. Если я сделаю так же время вычисления для всех рекурсивных вызовов (изменив GetResponse()
), код будет работать плавно.
float AxisAlignedFeatureResponse::GetResponse(const IDataPointCollection& data, int index) const {
double retArg;
// retrieve DataManager object
const DataManager& concreteData = (const DataManager&)(data);
// // retrieve data point at index
DataPoint currDataPoint = concreteData.getDataPoint(index);
//
// // get coordinates of data point
Coordinate currCoordinates = currDataPoint.getOrigPos();
//
// // get intensity image of the respective data point
int imgIndex = currDataPoint.getImageIndex();
Image currImg = concreteData.getImage(imgIndex);
Image currFeatureImg = concreteData.getFeatureImage(imgIndex);
// return respective feature
int featureNumber = (int)(this->axis*(double)concreteData.getNumberOfFeatures());
if(featureNumber>=concreteData.getNumberOfFeatures()){
cout<<"warning! trying to reach a feature that is not there!"<<endl;
featureNumber=concreteData.getNumberOfFeatures()-1;
}
std::vector<Coordinate> feature = concreteData.getFeature(featureNumber);
Coordinate tmp=currCoordinates+feature[0];
if(feature[1].x == 0) {
retArg = currCoordinates.x*feature[0].x+currCoordinates.y*feature[0].y+currCoordinates.z*feature[0].z;
//retArg = 0; //DOING THIS runs the code smoothly
}
else if(feature[1].x == 2) {
retArg = currFeatureImg.getValue(feature[0]);
} else {
retArg = currImg.mean(tmp,feature[1]);
}
return (float)(retArg);
//return (float) 0;
}
Так что, похоже, проблема не в GetResponse? Где код для этого? – xaxxon
@xaxxon добавлен сейчас, хотя я не вижу, как может быть проблема в этом, за исключением разницы во времени вычисления – Azhar