2011-06-22 39 views
3

我有这样的代码大小是不知道的帮助

的main.cpp

#include <iostream> 
#include "functs.h" 

using namespace std; 

int main() 
{ 
    ArrayList *al = new ArrayList; 
    return 0; 
} 

functs.h

using namespace std; 
#ifndef FUNCTS_H_INCLUDED 
#define FUNCTS_H_INCLUDED 

class ArrayList; 
#endif // FUNCTS_H_INCLUDED 

functs.cpp

#include <iostream> 
#include "functs.h" 

class ArrayList{ 
    public: 
     void add(int num); 
     void add(int num, int index); 
     void remove(int index); 
     void removeNum(int num); 
     string toString(); 
     ArrayList(int init); 
    private: 
     void resize(); 
     int size, cap; 
     int *myList[10]; 
}; 

void ArrayList::add(int num){ 
    if (size>=cap/2) 
    { 
     resize(); 
    } 
    *myList[size] = num; 
    size++; 
} 

void ArrayList::resize(){ 
    int temp[cap*2]; 
    int i; 
    for (i = 0; i < size; i++) 
    { 
     temp[i] = *myList[i]; 
    } 
    *myList = temp; 
} 

ArrayList::ArrayList(){ 
    size = 0; 
    cap = 10; 
} 

void ArrayList::add(int num, int index){ 
    int temp = *myList[index]; 
    int i; 
    for (i = index; i < size; i++) 
    { 
     *myList[index] = num; 
     num = temp; 
     temp = *myList[i+1]; 
    } 
    add(temp); 
} 

string ArrayList::toString(){ 
    string returnString = "{"; 
    int i; 
    for (i = 0; i < size; i++) 
     returnString.append(*myList[i] +","); 
    returnString.replace(returnString.length()-1,1,"}"); 
    return returnString; 
} 

和我对C++来说是非常新的东西,但每当我尝试编译时它代码给了我一个“ArrayList的大小是不知道的”。请帮我弄清楚错误。 =(

+0

从你的主题,然后看你的代码,我的第一印象是,实际上'ArrayList'的客户端没有办法根据元素的数量来确定“大小”。这看起来像是课堂界面中的一个重大遗漏! –

+1

你知道标准库已经为C++提供了一整套容器,就像Java一样,是的? –

+0

...很好理解它我不如建立它=/ –

回答

6

在代码设计/使用的问题,尽管,最明显的问题是,你想要把类定义在functs.h文件,而不是functs.cpp文件:

functs.h

// This is declaration is highly not recommended for use in header files. 
// using namespace std; 

#ifndef FUNCTS_H_INCLUDED 
#define FUNCTS_H_INCLUDED 

#include <string> 

class ArrayList{ 
    public: 
     void add(int num); 
     void add(int num, int index); 
     void remove(int index); 
     void removeNum(int num); 
     std::string toString(); 
     ArrayList(int init); 
    private: 
     void resize(); 
     int size, cap; 
     int *myList[10]; 
}; 

#endif // FUNCTS_H_INCLUDED 

functs.cpp

#include "functs.h" 

void ArrayList::add(int num){ 
    if (size>=cap/2) 
    { 
     resize(); 
    } 
    *myList[size] = num; 
    size++; 
} 

void ArrayList::resize(){ 
    int temp[cap*2]; 
    int i; 
    for (i = 0; i < size; i++) 
    { 
     temp[i] = *myList[i]; 
    } 
    *myList = temp; 
} 

ArrayList::ArrayList(){ 
    size = 0; 
    cap = 10; 
} 

void ArrayList::add(int num, int index){ 
    int temp = *myList[index]; 
    int i; 
    for (i = index; i < size; i++) 
    { 
     *myList[index] = num; 
     num = temp; 
     temp = *myList[i+1]; 
    } 
    add(temp); 
} 

std::string ArrayList::toString(){ 
    std::string returnString = "{"; 
    int i; 
    for (i = 0; i < size; i++) 
     returnString.append(*myList[i] +","); 
    returnString.replace(returnString.length()-1,1,"}"); 
    return returnString; 
} 

templatetypedef提供一个原因,这是必要的。基本上编译器需要知道需要多少空间,而class ArrayList;不提供这样的信息。


这不申报using namespace std;一个头文件里面,因为每个人都那么包含functs.h文件(包括你的客户!)也将有一个using namespace std;,增加名称冲突的可能性是一个好主意。


如果您想正确学习C++,我强烈建议您选择a good introductory C++ book。你在你的问题中展示了一个对C++编写得有多好的误解。这并不是说你作为一个人无能,但是你的代码存在一些严重的问题。仅举几例:

  • 标准C++已经提供了一个称为std::vector的完美精细的数组类。没有必要为你正在做的事情重新发明轮子。即使你不得不重新发明轮子,对C++的高级理解和丰富的C++经验也是实现适合生产使用的数组容器的先决条件。
  • 您班级的公共界面不完整。客户无法知道阵列中实际有多少元素。
  • int *myList[10];声明了一个固定数组10指针int。这不适用于数组类。特别是如果你想让数组的大小可调。
  • 这个类没有足够的内存管理在任何意义上都是有用的。没有析构函数,显然构造函数不完整(也不匹配),所以你没有真正的逻辑位置来放置new[]delete[]之类的东西。
  • 你有一个ArrayList *al = new ArrayList;但你没有相应的delete al;任何地方。这是内存泄漏。
  • 但最后一点是没有意义,因为你应该使用ArrayList a1;而不是ArrayList *al = new ArrayList;。前者会在范围​​末尾自动“删除”自己(在这种情况下,main()函数),而后者则需要delete语句。 C++不像Java那样自动收集未使用的new'ed对象。

我不能评论你使用的算法的正确性,因为(并且我很遗憾地这样说,因为它会听起来很刺耳),你根本无法工作。再次,我建议你拿起a good introductory C++ book,这将涵盖这些类型的问题。 (我必须强调的是,没有这些缺点是你的陈述作为一个人,我对你在你的问题有专门的代码说话。)

0

这多少

class ArrayList{ 
    public: 
     void add(int num); 
     void add(int num, int index); 
     void remove(int index); 
     void removeNum(int num); 
     string toString(); 
     ArrayList(int init); 
    private: 
     void resize(); 
     int size, cap; 
     int *myList[10]; 
}; 

应该在.h文件。

为什么?因为不需要类的大小(更具体的情况在C++标准中列出),所以类的声明(当您编写class ArrayList;时)就足够了。类的定义应该出现在相同的翻译单元中,其中类需要以完整的方式使用。

2

出现此错误的原因是在main.cpp中,编译器没有看到类ArrayList的定义。这只是看到了声明

class ArrayList; 

当试图通过编写

new ArrayList; 

创建ArrayList编译器不知道多少内存需要持有ArrayList因为它不看到了班级的定义。这与Java等其他语言形成鲜明对比,这些信息不必立即可用。

若要解决此问题,请通过从.cpp文件中移动类的定义来更新您的.h文件。这样,当有人#include S中的头文件,他们将获得除声明,这将允许您使用new,声明ArrayList类型的局部变量的类定义

希望这有助于!

+0

+1,很好的解释。 [C++ FAQ](http://www.parashift.com/c++-faq-lite/misc-technical-issues.html#faq-39.11)非常简洁地解释了这一点:'class ArrayList;'“只是简单地告诉编译器:名称['ArrayList']是一个类,进一步它是对编译器的承诺,您最终将提供该类的完整定义。“大多数情况下,完整的定义必须出现在同一个源文件中。 –

0

您声明myList的方式具有固定大小; *myList = temp;没有做你想做的事。

简单声明myList为int * myList;

在构造函数中使用myList = new int[10];

无处不在,你有*myList[...]它改变myList[...]

在调整大小,int temp[cap*2]需求是int *temp = new int[cap * 2]*myList = temp需要为myList = temp

你仍然有内存泄漏,但这应该让你开始。