C ++指针/堆问题 [英] C++ Pointer/Heap Problem

查看:123
本文介绍了C ++指针/堆问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

嘿,我正在努力解决以下问题.我编写了一个简单的高斯算法,但是执行完成(成功)之后,几乎所有下次尝试分配内存的程序都会使程序崩溃,并给我以下错误:

"Windows触发了......的断点.
这可能是由于堆损坏所致,这表明...

并向我显示malloc.c.

有什么想法我做错了吗?

在此先感谢

代码:

Hey, I''m struggling against the following problem. I wrote a simple gaus algorithm, but AFTER it is done executing (succesfuly), pretty much any next attempt to alocate memory crashes the program and gives me the following error:

"Windows has triggetred a breakpoint in ...
This may be due to a corruption of heap, which indicates...

and displays malloc.c to me.

Any ideas what im doing wrong?

Thanks in advance

The code:

#ifndef __GAUS_H_INCLUDED__
#define __GAUS_H_INCLUDED__
#include "Grid.h"
#include <math.h>

class Gaus
{
private:


public:

Gaus ()
{
}
Gaus ( GPA * Source, GPA * Result)
{
CallGaus(Source,Result);
}

void CallGaus( GPA * Source, GPA * Result )
{
  int xa, xe, ya, ye, sx, sy=0, T, s; //Bildcoords-Laufvariablen
  Punkt P;
   s=(*Source).X;
  Punkt*   R1;
  Punkt*   R2;
  Punkt*   R3;
  R1 = new Punkt[s];
  R2 = new Punkt[s];
  R3 = new Punkt[s];

xa=0; ya=0; xe=(*Source).X; ye=(*Source).Y;


  sy=ya;
  for (sx = xa; sx < xe; sx++)                              // Zeile 1
  { P=(*Source)[sx][sy]; R2[sx]=P; }
  for (sx = xa; sx < xe; sx++)                              // Zeile 2
  { P=(*Source)[sx][sy+1]; R3[sx]=P; }

   for (sy=ya+1; sy < ye-1; sy++) {
       int sy1=sy+1;
       int xa1=xa+1;
       R1=R2;
       R2=R3;
       R3[sx]=(*Source)[xa][sy1];
       R3[sx+1]=(*Source)[xa1][sy1];
       int r2=int(R1[xa].R+2*R2[xa].R+R3[xa].R);
       int G2=int(R1[xa].G+2*R2[xa].G+R3[xa].G);
       int B2=int(R1[xa].B+2*R2[xa].B+R3[xa].B);
       int r3=int(R1[xa1].R+2*R2[xa1].R+R3[xa1].R);
       int G3=int(R1[xa1].G+2*R2[xa1].G+R3[xa1].G);
       int B3=int(R1[xa1].B+2*R2[xa1].B+R3[xa1].B);
   for (T=(xa-1);T<(xe-1);T++)
   {
       int T1=T+1;
       R3[T1]=(*Source)[T1][sy1];
       int r1=r2;
       int G1=G2;
       int B1=B2;
       r2=r3; G2=G3; B2=B3;
       r3=int(R1[T1].R+2*R2[T1].R+R3[T1].R);
       G3=int(R1[T1].G+2*R2[T1].G+R3[T1].G);
       B3=int(R1[T1].B+2*R2[T1].B+R3[T1].B);
       int rr=(r1+2*r2+r3)/16;
       int gg=(G1+2*G2+G3)/16;
       int bb=(B1+2*B2+B3)/16;
       P.R=rr;
       P.G=gg;
       P.B=bb;

       (*Result).WriteSecure(T, sy, &P);
   }
  }



}
~Gaus()
    {

    }

};
#endif

推荐答案

您正在对指向动态分配的内存的指针进行指针操作.这有两个作用:

-您是孤立的内存块-即使您想释放R1也无法释放
-正如Albert所说,您正在某个地方超越数组.您不会为任何事情在任何地方分配xa,因此在重新分配它以保存变量之前,它会保留该内存位置中的任何内容

那么,您能做什么呢?

-使用std :: vector而不是摆弄动态内存.这将对您的内存泄漏进行排序,即使您为其分配内存,也会造成这种情况.这包括输入参数-对源使用const引用,对结果使用引用.这还包括GPA的数组部分(如果它们不仅仅是点数组的数组)

-依靠运行时库.如果您在调试模式下使用VC ++,则在向量的边界上运行时,您将获得某种异常断言.如果您不这样做,则可能有一种方法可以打开编译器的边界检查.如果没有,则断言数组索引有效.一些编译器会进行迭代器边界检查,因此也许使用迭代器而不是[]运算符-它会使您的代码更难看,但更便于运行时库捕获错误

其他一些评论...

-不要在不需要的地方使用冗余变量,例如xa和ya未分配给. xa1和sy1只是xa + 1的别名,sy + 1,T + 1的T1 xe和s是Source-> X的别名,ye是Source-> Y的别名.在您的前两个循环中,sy始终为零. sx从0开始的前两个循环
-始终初始化变量
-如果必须强制转换,请使用C ++强制转换.如果您发现整个商店都在reinterpret_cast进行操作,则说明您的操作有问题
-使用a-> b而不是(* a).b.对我来说,这是一个少字符,但对老旧的骇客来说更明显
-为什么高斯会上课?对我来说似乎是一个功能.没有状态,构造函数/析构函数什么也不做.它甚至不可用作函子,因为它没有重载的operator()
-T在哪里宣布?不要使用全局变量!曾经.对于任何东西
-查看行R1 = R2; R2 = R3.第一次迭代R1 = R2(初始),R2 = R3(初始).第二和后续迭代R1 = R3(初始)和R2 = R3(初始).确定要吗?
-对于int r1 = r2的注释; int G1 = G2; int B1 = B2; r2 = r3; G2 = G3; B2 = B3;
-从头开始,太累了,以至于无法看到r3,G3和B3稍后在同一迭代中被修改
-不要在比它们需要的作用域更大的范围内使用声明循环变量.你们都是.
-在需要变量之前不要声明变量.例如,P的作用域范围太大,看起来可以用三个参数的构造函数来实现
-Source和Result的声明在我看来有点令人怀疑-特别是* Source和* Result是2D数组.
-确定要使用P吗?如果我没看错的话,那么三个术语的构造函数就足够了,并且在将& P传递给WriteSecure的地方,可以使用const引用

摆脱掉很多,如果错误变得非常明显,也不会令我感到惊讶!

耶稣,花了3个小时复查了这笔土地-按照我通常的培训合同费,您欠我£150.学生£75.我应将发票发送到哪里? :-)
You''re doing pointer manipulation on pointers to dynamically allocated memory. This has a couple of effects:

- you''re orphaning blocks of memory - you couldn''t free R1, even if you wanted to
- as Albert said you''re overrunning an array somewhere. You''re not assigning xa anywhere for one thing so it''s left with whatever was in that memory location before it was reallocated to hold your variable

So, what can you do about this lot?

- use std::vector instead of fiddling about with dynamic memory. This will sort your memory leaks out, cause even if you assign them. This includes the input parameters - use a const reference for Source and a reference for Result. This also includes the parts of GPA that are arrays (if they''re not just arrays of arrays of points)

- Lean on the runtime library. If you''re using VC++ in debug mode you''ll get some sort of assert of exception if you run over the bounds of a vector. If you don''t there might be a way to turn on bounds checking for your compiler. If there isn''t do a assert that array indices are valid. Some compilers do iterator bounds checking so perhaps use iterators rather than the [] operator - it''ll make your code a bit uglier but easier for the runtime library to catch errors

Some other comments...

- don''t use redundant variables where you don''t need to, e.g. xa and ya aren''t assigned to. xa1 and sy1 are just aliases for xa + 1, sy +1, T1 for T + 1 xe and s for Source->X and ye for Source->Y. sy is always zero during your first two loops. sx starts at 0 the first two loops
- always initialise variables
- if you have to cast use C++ casts. If you find you''re reinterpret_casting all over the shop there is something wrong with what you''re doing
- use a->b rather than (*a).b. It''s a character less and is a bit more obvious to jaded old hacks like me
- why''s Gaus a class? Looks like a function to me. There''s no state and the constructors/destructors don''t do anything. It can''t even be used as a functor as it doesn''t have an overloaded operator()
- where''s T declared?? Don''t use global variables! Ever. For anything
- Look at the lines R1=R2; R2=R3. First iteration R1 = R2(intial) and R2=R3(initial). Second and subsequent iterations R1=R3(initial) and R2=R3(intial). Are you sure you want that?
- same sort of comment for int r1=r2; int G1=G2; int B1=B2; r2=r3; G2=G3; B2=B3;
- scratch that, was too tired to see r3, G3 and B3 were modified later in the same iteration
- don''t use declare loop variables at a larger scope than they need to be. All of yours are.
- don''t declare variables until you need them. P for instance has way too much scope and looks like it could do with a three parameter constructor
- Source and Result''s declarations look a bit suspect to me - especially as *Source and *Result are 2D arrays.
- are you sure you need P? If I''m reading right a three term constructor would be enough and where you pass &P into WriteSecure a const reference will do

Get rid of that lot and it wouldn''t surprise me if the error became glaringly obvious!

Jesus, spent 3 hours reviewing that lot - you owe me £150 at my usual training contract rate. £75 for students. Where do I send the invoice? :-)


您正在覆盖动态分配的数组之一的边界,使用调试器通过简单地遍历循环即可找出哪个数组...或者,您可以查看调用堆栈以查看哪个调用触发了错误.

我还看到您正在分配内存,并且从不对其进行分配...您是否喜欢使内存泄漏?
You''re overriding the bounds of one of the dynamically allocated arrays, use your debugger to find out which one by simply stepping through your loops...or, you can look at the call stack to see which call triggered the error.

I also see you''re allocating memory and never deallocating it... Do you like making memory leaks?


这篇关于C ++指针/堆问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆