【问题标题】:Deallocation 3 dimensional vector C++释放 3 维向量 C++
【发布时间】:2021-02-26 20:26:55
【问题描述】:

我在 C++ 中释放 3 维向量时遇到问题,我收到错误“CTR 检测到应用程序在堆缓冲区结束后写入内存”。 有人可以告诉我我做错了什么吗?提前谢谢你。

分配:

count = new int**[w];

        for (int i = 0; i < w; ++i)
        {
            count[i] = new int*[h];
            for (int j = 0; j < h; ++j)
            {
                count[i][j] = new int[120];
                for (int k = 20; k < 120; ++k)
                {
                    count[i][j][k] = 0;
                }
            }
        }

解除分配:

        for (int i = 0; i < w; ++i)
        {
            for (int j = 0; j < h; ++j)
            {
                delete [] count[i][j];
            }
            delete [] count[i];
        }
        delete [] count;
        count = NULL;

【问题讨论】:

  • 请提取并提供minimal reproducible example,而不仅仅是一些人们必须猜测周围环境的部分代码!作为新用户,也可以使用tour 并阅读How to Ask。顺便说一句:在大多数情况下,使用一个向量(我的意思也是std::vector)并根据三个坐标计算该向量中的索引更容易。对于 2D,它通常是 row * row_length + column,对于 3D,它是一个额外的 + plane * row_length * column_length
  • 谢谢!我会尝试更好地提出问题。也谢谢你的想法。
  • wh 提供了一些任意数字我无法重现该问题。 valgrind 也没有看到内存问题。顺便说一句,依赖 std::vector 或其他 RAII 工具(如 std::unique_ptr)很容易。
  • @UlrichEckhardt 的想法也会更有效,因为您只需分配和释放一次。它还可以避免缓存未命中。
  • @AskoldIlvento 虽然这样做更容易。我仍然认为对于新程序员来说学习如何处理原始指针和数组是有好处的。

标签: c++ pointers memory-management delete-operator


【解决方案1】:

这是我的全部代码:

#include <filesystem>
#include <stdexcept>
#include "pch.h"
#include <iostream>
#include <opencv2/core.hpp>
#include <opencv2/imgproc.hpp>
#include <opencv2/highgui.hpp>
#include <math.h>
using namespace std;
using namespace cv;

class cerc {
    int raza;
    int a;
    int b;
public:
    cerc()
    {
        a = 0;
        b = 0;
        raza = 0;
    }
    inline cerc(int raza, int a, int b)
    {
        this->a = a;
        this->b = b;
        this->raza = raza;
    }
    inline cerc(cerc& c)
    {
        a = c.a;
        b = c.b;
        raza = c.raza;
    }

    void print()
    {
        std::cout << " (" << (int)this->a << ", " << (int)this->b << ", " << (int)this->raza << ") ";
    }
    inline bool operator==(const cerc& other) const
    {
        if (this->a == other.a && this->b == other.b && this->raza == other.raza)
            return true;
        else return false;
    }
    inline bool egal(int raza, int a, int b) const
    {
        if (this->a == a && this->b == b && this->raza == raza)
            return true;
        else return false;
    }
    inline void copy(cerc &c2)
    {
        this->raza = c2.raza;
        this->a = c2.a;
        this->b = c2.b;
    }
    inline void copy(int raza, int a, int b)
    {
        this->a = a;
        this->raza = raza;
        this->b = b;
    }
    const int getA()
    {
        return a;
    }
    const int getB()
    {
        return b;
    }
    const int getRaza()
    {
        return raza;
    }
};

int min(int a, int b)
{
    if (a < b)
        return a;
    return b;
}

void createVector(int*** count, Mat img, int w, int h)
{
    int a = 0;
    int b = 0;
    int r = 0;

    int wminus = 5 * (w / 6);
    int hminus = 5 * (h / 6);

    int wstart = w / 6;
    int hstart = h / 6;

    int x, y;

    for (x = wstart; x < wminus; x++)
        for (y = hstart; y < hminus; y++)
        {
            if (((Scalar)(img.at<uchar>(Point(x, y)))).val[0] == 255)
            {
                for (a = wstart; a < wminus; a += 1)
                    for (b = hstart; b < hminus; b += 1)
                    {
                        r = (int)sqrt((b - y)*(b - y) + (a - x)*(a - x));

                        if (r >= 20 && r <= 120)
                            count[a][b][r]++;
                    }

            }
        }
}

void cercFinal(cerc &cercMax, int***count, int w, int h)
{
    int wminus = 5 * (w / 6);
    int hminus = 5 * (h / 6);

    int wstart = w / 6;
    int hstart = h / 6;

    int maxNr = count[0][0][0];

    for (int i = wstart; i < wminus; i += 1)
        for (int j = hstart; j < hminus; j += 1)
            for (int k = 20; k < 60; k++)
                if (maxNr < count[i][j][k])
                {
                    maxNr = count[i][j][k];
                    cercMax.copy(k, i, j);
                }

    cout << maxNr;
}
void cercFinalSecund(cerc &SecondCircle, cerc &FirstCircle, int***count, int w, int h)
{
    int wminus = 3 * (w / 4);
    int hminus = 3 * (h / 4);

    int wstart = w / 4;
    int hstart = h / 4;
    int minIrisRay = (int)(FirstCircle.getRaza() * 1.5);
    int maxIrisRay = FirstCircle.getRaza() * 4;
    int maxNr = count[0][0][0];

    for (int i = wstart; i < wminus; i += 1)
        for (int j = hstart; j < hminus; j += 1)
            for (int k = 40; k < 120; k++)
            {
                if (k >= minIrisRay && k <= maxIrisRay)
                {
                    if (maxNr < count[i][j][k] && !(cerc(k, i, j) == FirstCircle) && abs(j - FirstCircle.getB()) < 2 && abs(i - FirstCircle.getA()) < 2)
                    {
                        maxNr = count[i][j][k];
                        SecondCircle.copy(k, i, j);
                    }
                }
            }
}

int main()
{
    Mat imgCanny;
    Mat imgBlur;
    int ***count;
    for (int i = 10; i < 50; i++)
    {
        Mat_<uchar> img = imread("C://Users//Maria//Downloads//CASIA-IrisV2//CASIA-IrisV2//device1//00" + std::to_string(i) + "//00" + std::to_string(i) + "_000.bmp", IMREAD_GRAYSCALE);
        //img.convertTo(img, -1, 4, 0);
        //int t = img.at<uchar>(1, 2).val[0];
        int w = img.size().width;
        int h = img.size().height;

        medianBlur(img, imgBlur, 15);
        //GaussianBlur(img, imgBlur, Size(8, 8), 0);
        Canny(imgBlur, imgCanny, 30, 40);
        //imshow("canny", imgCanny);

        int m = min(w, h);

        count = new int**[w];

        for (int i = 0; i < w; ++i)
        {
            count[i] = new int*[h];
            for (int j = 0; j < h; ++j)
            {
                count[i][j] = new int[120];
                for (int k = 20; k < 120; ++k)
                {
                    count[i][j][k] = 0;
                }
            }
        }
        createVector(count, imgCanny, w, h);

        cerc final(0, 0, 0);
        cerc finalSecund(0, 0, 0);
        cercFinal(final, count, w, h);
        cercFinalSecund(finalSecund, final, count, w, h);

        cout << endl << "cerc=";
        final.print();
        Point p(final.getA(), final.getB());
        Mat imgColor = imread("C://Users//Maria//Downloads//CASIA-IrisV2//CASIA-IrisV2//device1//00" + std::to_string(i) + "//00" + std::to_string(i) + "_000.bmp", IMREAD_COLOR);
        circle(imgColor, p, final.getRaza(), Scalar(255, 0, 0), 4, 8, 0);

        Point ps(finalSecund.getA(), finalSecund.getB());
        cout << endl << "cerc=";
        finalSecund.print();
        circle(imgColor, ps, finalSecund.getRaza(), Scalar(255, 0, 0), 4, 8, 0);

        imshow("iris", imgColor);

        for (int i = 0; i < w; ++i)
        {
            for (int j = 0; j < h; ++j)
            {
                delete [] count[i][j];
            }
            delete [] count[i];
        }
        delete [] count;
        count = NULL;
        waitKey(0);
    }
    return 0;
}

如果我删除count[a][b][r]++; 行,释放工作正常。这句话有什么问题吗?

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-05-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-10-14
    • 1970-01-01
    相关资源
    最近更新 更多