你能解决这个问题吗? :C ++动态数组问题 [英] Can you fix this program? : C++ Dynamic Array Problems

查看:63
本文介绍了你能解决这个问题吗? :C ++动态数组问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用VS2005编写了以下程序。该程序是一个Dynamic

数组,类似于.NET中的System.Collections.ArrayList。该程序工作

好​​,直到我达到65536,我似乎无法弄清楚为什么,因为看起来我的

逻辑工作正常。我是.NET程序员,所以我不习惯使用未托管的C ++代码处理

。如果你觉得写得不好,请批评我的代码

写的。


这是来自main()的循环,如果你改变<将会破坏程序br />
65536到更大的值。

for(int i = 0; i< 65536; i ++)

{

folder.entryID =" Testing";

fc->添加(文件夹);

}


谢谢

Russell Mangel

拉斯维加斯,NV

//开始代码

#include" stdafx.h"

#include< iostream>


using namespace std;


struct Folder

{

char * entryID;

};

class FoldersCollection

{

public:

FoldersCollection :: FoldersCollection()

{

Count = 0;

容量= 0;

}

FoldersCollection :: ~FfoldersCollection()

{

delete [] m_Folders ;

}

int计数;

int Capaci ty;

void FoldersCollection :: Add(文件夹文件夹)

{

if(Capacity == 0)

{

m_Folders =新文件夹[INITIAL_CAPACITY];

m_Folders [0] .entryID = folder.entryID;

Count ++;

容量= INITIAL_CAPACITY;

}

其他

{

if(Count< ;容量)

{

m_Folders [Count] .entryID = folder.entryID;

Count ++;

}

其他

{

printf(" Resizing Array。容量:%d。\ n",容量);

调整大小();


m_Folders [Count] .entryID = folder.entryID;

Count ++;

}

}

}

文件夹* FoldersCollection :: GetList()

{

返回m_Folders;

}

私人:

文件夹* m_Folders;

文件夹* m_Temp;

static const int INITIAL_CAPACITY = 4;

void FoldersCollection :: Resize()

{

// Double容量

int newCapacity =容量* = 2;

//创建新数组

m_Temp =新文件夹[newCapacity];

//复制元素

for(int i = 0; i< Capacity; i ++)

{

m_Temp [i ] .entryID = m_Folders [i] .entryID;

}


delete [] m_Folders;

m_Folders = m_Temp;

容量= newCapacity;

}

};

void main(void)

{

FoldersCollection * fc = new FoldersCollection;

文件夹文件夹;


//工作正常到65536,更改为更大的值到崩溃程序...

//我做错了什么...

for(int i = 0;我< 65536; i ++)

{

folder.entryID =" Testing";

fc-> Add(文件夹);

}

printf(完成...计数:%d容量:%d \ n,fc->计数,fc->容量);

删除fc;

}

I have written the following program using VS2005. The program is a Dynamic
Array similar to System.Collections.ArrayList in .NET. The program works
okay until I reach 65536, I can''t seem to figure out why, as it seems my
logic is working okay. I am a .NET programmer so I am not used to dealing
with un-managed C++ code. Please criticize my code if you think it is poorly
written.

This is the loop from main() that will blow up the program if you change
65536 to a larger value.
for(int i = 0; i < 65536; i++)
{
folder.entryID = "Testing";
fc->Add(folder);
}

Thanks
Russell Mangel
Las Vegas, NV

// Begin Code
#include "stdafx.h"
#include <iostream>

using namespace std;

struct Folder
{
char *entryID;
};
class FoldersCollection
{
public:
FoldersCollection::FoldersCollection()
{
Count = 0;
Capacity = 0;
}
FoldersCollection::~FoldersCollection()
{
delete []m_Folders;
}
int Count;
int Capacity;
void FoldersCollection::Add(Folder folder)
{
if(Capacity == 0)
{
m_Folders = new Folder[INITIAL_CAPACITY];
m_Folders[0].entryID = folder.entryID;
Count ++;
Capacity = INITIAL_CAPACITY;
}
else
{
if(Count < Capacity)
{
m_Folders[Count].entryID = folder.entryID;
Count ++;
}
else
{
printf("Resizing Array. Capacity: %d.\n", Capacity);
Resize();

m_Folders[Count].entryID = folder.entryID;
Count ++;
}
}
}
Folder* FoldersCollection::GetList()
{
return m_Folders;
}
private:
Folder *m_Folders;
Folder *m_Temp;
static const int INITIAL_CAPACITY = 4;
void FoldersCollection::Resize()
{
// Double Capacity
int newCapacity = Capacity*=2;
// Create new Array
m_Temp = new Folder[newCapacity];
// Copy elements
for(int i = 0; i < Capacity; i++)
{
m_Temp[i].entryID = m_Folders[i].entryID;
}

delete []m_Folders;
m_Folders = m_Temp;
Capacity = newCapacity;
}
};
void main(void)
{
FoldersCollection *fc = new FoldersCollection;
Folder folder;

// Works okay up to 65536, change to larger value to crash program...
// What I am doing wrong...
for(int i = 0; i < 65536; i++)
{
folder.entryID = "Testing";
fc->Add(folder);
}
printf("Finished... Count: %d Capacity: %d \n", fc->Count, fc->Capacity);
delete fc;
}

推荐答案

" Russell Mangel" < RU ***** @ tymer.net>在消息中写道

news:%2 **************** @ TK2MSFTNGP15.phx.gbl ...
"Russell Mangel" <ru*****@tymer.net> wrote in message
news:%2****************@TK2MSFTNGP15.phx.gbl...
< snip>

void FoldersCollection :: Resize()
//双倍容量
int newCapacity = Capacity * = 2;


您可能意味着:

int newCapacity =容量* 2;

//创建新数组
m_Temp =新文件夹[newCapacity];
//复制元素
for(int i = 0; i< Capacity; i ++)
{
m_Temp [i] .entryID = m_Folders [ i] .entryID;
}
<snip>

void FoldersCollection::Resize()
{
// Double Capacity
int newCapacity = Capacity*=2;
You probably meant:
int newCapacity = Capacity*2;
// Create new Array
m_Temp = new Folder[newCapacity];
// Copy elements
for(int i = 0; i < Capacity; i++)
{
m_Temp[i].entryID = m_Folders[i].entryID;
}



就像现在一样,索引在循环中途超出了m_Folders

的分配容量。


As it is now, the index goes beyond the allocated capacity of m_Folders
after midway through the loop.


> int newCapacity = Capacity * = 2;
> int newCapacity = Capacity*=2;
//创建新数组
m_Temp = new文件夹[newCapacity];
//复制元素
for(int i = 0; i< Capacity; i ++)
{
m_Temp [i] .entryID = m_Folders [i] .entryID;
}
// Create new Array
m_Temp = new Folder[newCapacity];
// Copy elements
for(int i = 0; i < Capacity; i++)
{
m_Temp[i].entryID = m_Folders[i].entryID;
}







你将容量变量加倍,然后将原始数组索引到其边界之外的



事实直到65536才有效。


我的个人意见是你不应该在一行上合并多个陈述和

分配。犯错很容易。


如果你这样写的话,你可能会看到这个问题几乎可能是b
立即可能。

容量* = 2

int newCapacity =容量;


-


亲切的问候,

Bruno。
br**********************@hotmail.com

仅删除_nos_pam



Hi,

you double the capacity variable and then index the original array beyond
its boundaries.
the fact that it worked until 65536 is pure luck.

My personal opinion is that you should never combine multiple statements and
assignments on 1 line. it is much too easy to make mistakes.

Had you written it like this, you would have seen the problem almost
immediatly probably.
Capacity*=2
int newCapacity = Capacity;

--

Kind regards,
Bruno.
br**********************@hotmail.com
Remove only "_nos_pam"


Russell Mangel写道:
Russell Mangel wrote:
我使用VS2005编写了以下程序。该程序是一个类似于.NET中的System.Collections.ArrayList的动态数组。
程序工作正常,直到达到65536,我似乎无法弄明白为什么,因为看起来我的逻辑工作正常。我是.NET程序员所以
我不习惯处理未管理的C ++代码。如果您认为编写得不好,请批评我的代码。


主要的批评是为什么要写它?此代码拼写为

std :: vector< T>在C ++中。除了学习练习之外,根本不需要编写这样的代码

。其他一些批评内联

以下。

这是来自main()的循环,如果你将65536更改为更大的值,它会炸毁程序。
for(int i = 0; i< 65536; i ++)
{
folder.entryID =" Testing";
fc-> Add(folder);
}
谢谢
Russell Mangel
拉斯维加斯,NV

//开始代码

#include" ; stdafx.h"
#include< iostream>
使用命名空间std;

struct文件夹
{
char * entryID;
};


以上是否有析构函数?在你的例子中,你只是为entryID分配

字符文字,所以答案是否定的,但在现实世界中,

可能是另一回事。如果entryID需要删除[]'',那么

你应该为这个类定义一个析构函数,赋值运算符和复制构造函数



class FoldersCollection
{
公开:
FoldersCollection :: FoldersCollection()
{
数= 0;
容量= 0;
}
FoldersCollection :: ~FoldersCollection()
{
删除[] m_Folders;
}
int Count;
int capacity;


您可能希望将这些字段包装在存取器中。因此,客户可以简单地改变你的计数或容量,从外面打破你的班级。

void FoldersCollection :: Add(Folder folder)
{
if(容量== 0)
{
m_Folders =新文件夹[INITIAL_CAPACITY];
m_Folders [0] .entryID = folder.entryID;
Count ++ ;
容量= INITIAL_CAPACITY;
}

{
if(Count< Capacity)
{
m_Folders [Count] .entryID = folder.entryID;
Count ++;
}

{/> printf(" Resizing Array。容量:%d。\ n",容量);
调整大小();

m_Folders [Count] .entryID = folder.entryID;
Count ++;
}
}
}


重写以上内容:


void FoldersCollection :: Add(文件夹文件夹)

{

EnsureCapacity(Count + 1);

m_Folders [Count ++] =文件夹;

}

文件夹* FoldersCollection :: GetList()
{
retu mnFolders;
}


如果你想简单地暴露内部数组,那么即使是制作也没有什么意义一个类,因为一旦你返回一个指针,客户端可以简单地在你的

数组中运行粗暴。我会重新考虑这个设计。

private:
Folder * m_Folders;
Folder * m_Temp;


消除上述成员varialbe-m_Temp

static const int INITIAL_CAPACITY = 4;
void FoldersCollection :: Resize()
{
//双容量
int newCapacity =容量* = 2;
//创建新数组
m_Temp =新文件夹[newCapacity];
//复制元素
for(int i = 0; i< Capacity; i ++)
{
m_Temp [i] .entryID = m_Folders [i] .entryID;
}

delete [] m_Folders;
m_Folders = m_Temp;
容量= newCapacity;
}


重写:


void FoldersCollection :: EnusreCapacity(int requiredCapacity)

{

if(requiredCapacity< = Capacity)

return;


int newCapacity =容量* 2;

if(newCapacity< INITIAL_CAPACITY)

newCapacity = INITIAL_CAPACITY;

if(newCapacity< requiredCapacity)

newCapacity = requiredCapacity;


文件夹* temp = new文件夹[newCa pacity];


if(Count> 0)

{

for(int i = 0; i< Count; ++ i)

temp [i] = m_Folders [ i];

删除[] m_Folders;

}


m_Folders = temp;

}

};
void main(void)
{
FoldersCollection * fc = new FoldersCollection;
文件夹文件夹;

//可以正常工作到65536,更改为更大的值来崩溃程序...
//我做错了什么...
for(int i = 0; i< 65536; i ++)
{
folder.entryID =" Testing";
fc-> Add(文件夹);
}
printf(" Finished ... Count: %d容量:%d \ n",fc->计数,
fc->容量);删除fc;
}
I have written the following program using VS2005. The program is a
Dynamic Array similar to System.Collections.ArrayList in .NET. The
program works okay until I reach 65536, I can''t seem to figure out
why, as it seems my logic is working okay. I am a .NET programmer so
I am not used to dealing with un-managed C++ code. Please criticize
my code if you think it is poorly written.
The main criticism would be why write it at all? This code is spelled
std::vector<T> in C++. There''s simply no need to write code like this
except for the learning exercise of it. A few other criticisms inline
below.

This is the loop from main() that will blow up the program if you
change 65536 to a larger value.
for(int i = 0; i < 65536; i++)
{
folder.entryID = "Testing";
fc->Add(folder);
}

Thanks
Russell Mangel
Las Vegas, NV

// Begin Code
#include "stdafx.h"
#include <iostream>

using namespace std;

struct Folder
{
char *entryID;
};
Should the above have a destructor? In your example, you''re only assigning
character literals to entryID, so the answer is NO, but in the real world,
that might be a different story. If entryID needs to be delete[]''d, then
you should define a destructor, assignment operator and copy constructor for
this class.
class FoldersCollection
{
public:
FoldersCollection::FoldersCollection()
{
Count = 0;
Capacity = 0;
}
FoldersCollection::~FoldersCollection()
{
delete []m_Folders;
}
int Count;
int Capacity;
You might want to wrap these fields in accessors. As is, a client can
simply change your Count or Capacity, breaking your class from the outside.
void FoldersCollection::Add(Folder folder)
{
if(Capacity == 0)
{
m_Folders = new Folder[INITIAL_CAPACITY];
m_Folders[0].entryID = folder.entryID;
Count ++;
Capacity = INITIAL_CAPACITY;
}
else
{
if(Count < Capacity)
{
m_Folders[Count].entryID = folder.entryID;
Count ++;
}
else
{
printf("Resizing Array. Capacity: %d.\n", Capacity);
Resize();

m_Folders[Count].entryID = folder.entryID;
Count ++;
}
}
}
Rewrite the above:

void FoldersCollection::Add(Folder folder)
{
EnsureCapacity(Count+1);
m_Folders[Count++] = folder;
}
Folder* FoldersCollection::GetList()
{
return m_Folders;
}
If you''re going to simply expose the inner array, there''s little point in
even making a class since a client can simply run roughshod all over your
array once you''ve returned a pointer. I''d reconsider this design.
private:
Folder *m_Folders;
Folder *m_Temp;
Eliminiate the above member varialbe- m_Temp
static const int INITIAL_CAPACITY = 4;
void FoldersCollection::Resize()
{
// Double Capacity
int newCapacity = Capacity*=2;
// Create new Array
m_Temp = new Folder[newCapacity];
// Copy elements
for(int i = 0; i < Capacity; i++)
{
m_Temp[i].entryID = m_Folders[i].entryID;
}

delete []m_Folders;
m_Folders = m_Temp;
Capacity = newCapacity;
}
Rewrite this:

void FoldersCollection::EnusreCapacity(int requiredCapacity)
{
if (requiredCapacity <= Capacity)
return;

int newCapacity = Capacity*2;
if (newCapacity < INITIAL_CAPACITY)
newCapacity = INITIAL_CAPACITY;
if (newCapacity < requiredCapacity)
newCapacity = requiredCapacity;

Folder* temp = new Folder[newCapacity];

if (Count > 0)
{
for (int i = 0; i < Count; ++i)
temp[i] = m_Folders[i];
delete[] m_Folders;
}

m_Folders = temp;
}
};
void main(void)
{
FoldersCollection *fc = new FoldersCollection;
Folder folder;

// Works okay up to 65536, change to larger value to crash program...
// What I am doing wrong...
for(int i = 0; i < 65536; i++)
{
folder.entryID = "Testing";
fc->Add(folder);
}
printf("Finished... Count: %d Capacity: %d \n", fc->Count,
fc->Capacity); delete fc;
}



这篇关于你能解决这个问题吗? :C ++动态数组问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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