【问题标题】:Weird numbers in C++ array of objectsC ++对象数组中的奇怪数字
【发布时间】:2012-04-23 20:54:27
【问题描述】:

我一直在尝试使用动态创建的对象数组创建一个类。我重载了运算符 + 以向一组对象(类到类)添加(暂时仅此)一个新对象。问题是当我读取数组中的数据时,我得到了各种各样的大数字。代码如下:

#include<iostream.h>

class Figura {
    public: 
        int x, y, poz;
        int tip; //1 = punct ; 2 = dreapta; 3 = dreptunghi
        Figura() { };
        Figura(const Figura&) { };
};

class Grup {
    private:
        int nr_elemente;
        Figura *figuri;
    public:
        int i;
        Grup(int nr_el) {
            nr_elemente = nr_el;
            figuri = new Figura[nr_elemente];
            i = 1;
        }
        ~Grup() {};
        Grup(const Grup&) {};
        int _nr_elemente() {
            return i;
        }

        void adauga_element(Figura fig) {
            if( i <= nr_elemente)
                figuri[i++] = fig;
            else
                cout<<"Grupul a atins numarul maxim de figuri.";
        }

        void afiseaza_elemente() {
            for(int j = 1; j <= i; j++)
                cout<<"Figura nr : "<<j<<"tip: "<<figuri[j].tip<<figuri[j].x<<" "<<figuri[j].y<<" "<<figuri[j].poz;
        }
    friend Grup operator+(const Figura& fig1, const Figura& fig2) {
        return fig1.poz + fig2.poz;
    };
    friend Grup operator+(const Grup& gr1, const Grup& gr2) {};
    void operator+(const Figura& fig);
    friend Grup operator*(const Grup& fig) {};

};

void Grup::operator+(const Figura& fig) {
    Grup::adauga_element(fig);
}

class Punct : public Figura
{
    public: 
        Punct(int poz) {
            Punct::tip = 1;
            Punct::poz = poz;
        }
};

class Segment : public Figura
{
    public:
        Segment(int poz, int x) {
            Segment::tip = 2;
            Segment::poz = poz;
            Segment::x = x;
        }
};

class Dreptunghi : public Figura
{
    public:
        Dreptunghi(int poz, int x, int y) {
            Dreptunghi::tip = 3;
            Dreptunghi::poz = poz;
            Dreptunghi::x = x;
            Dreptunghi::y = y;
        }
};

void main(void) {

    Grup gr(1);
    Punct pct(1);
    Segment sgm(3, 5);

    gr + pct;
    gr + sgm;
    //cout<<gr.i;
    cout<<sgm.x;
    gr.afiseaza_elemente();

}

【问题讨论】:

  • 它将用于最多 10-15 个元素。
  • 您仍然需要为 figuri 分配更多内存,但更好的方法是将 figuri 声明为向量。你真的应该考虑使用initialization lists
  • 如果你的类应该代表一个动态数组,那么这种做法就大错特错了。如果可以,请使用std::vector 代替创建自己的类,并且只使用push_back 每个元素。

标签: c++ arrays memory-management


【解决方案1】:

N 是数组大小时,数组索引从0N - 1。以下代码将导致越界数组访问:

void adauga_element(Figura fig) {
    if( i <= nr_elemente)
        figuri[i++] = fig;
    else
        cout<<"Grupul a atins numarul maxim de figuri.";
}

改为:

    if( i < nr_elemente)

afiseaza_elemente() 中的同样问题。

由于您有动态分配的成员,因此析构函数必须delete[] 动态分配的数组,并且需要正确实现复制构造函数和赋值运算符,或声明private 以防止复制。由于这是 C++,请考虑使用 std::vector&lt;Figura&gt; 而不是数组。

【讨论】:

  • ...“打印”方法(即afiseaza_elemente)中也存在同样的问题。
【解决方案2】:

一个更简单的例子可以增进理解。

无论如何,您的问题被称为对象切片。

简而言之,您不能将派生对象放入基础对象数组中。

要解决这个问题,您可以将 figuri 数据成员更改为指向 Figura 的指针数组:

Figura ** figuri;
// ...
figuri = new Figura*[nr_elemente];

【讨论】:

  • 我根据上面的代码做了一些修改,但最后一个问题。如何调整这段代码,以便将对象添加到数组中: void add(Figura fig) { figuri[i++] = fig; }
【解决方案3】:

您没有初始化任何成员。你应该在构造函数中这样做。

例如:

Punct pct(1);

仅初始化成员tippos,但xy 将包含垃圾值,您可能最终会看到这些值。

您也不应该使用动态分配的数组作为成员 - Figura *figuri; 而是 std::vector。这也可以避免您在添加新数字时遇到的未定义行为。

另外,请注意您的析构函数和复制构造函数没有实现,这是错误的来源。

void adauga_element(Figura fig)

传递对象fig是按值传递的,所以要实现一个拷贝构造函数。

【讨论】:

  • 你能说得具体一点吗?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-12-20
  • 2015-08-07
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多