Ошибка сегментации при итерации std :: vector - PullRequest
0 голосов
/ 20 сентября 2019

У меня есть метод, который будет вызываться много раз подряд для выполнения итеративной печати объекта std :: vector, который содержит объекты std :: vectors.

class Message
{
public:
    struct Child
    {
        Child:a(0.0F),b(0.0F)
         {}
         float a;
         float b;
    };
    struct Parent
    {
          Parent:x(0U),y(0U)
          {}
          unsigned char x;
          unsigned char y;
          std::vector<Child> childList;
    };

    Message();
    ~Message();
    printingMethod();
    addParent();

private:
    unsigned int s;
    unsigned int t;
    std::vector<Message::Parent> parentList;
}

Message::addParent(Message::Parent newParent)
{
    parentList.push_back(newParent);
}

Message::printingMethod()
{
    std::cout << s << std::endl;
    std::cout << t << std::endl;

    for(unsigned int i = 0U; i < parentList.size(); i++)
    {
        const Parent myParent = parentList[i];

        std::cout << myParent.x << std::endl;
        std::cout << myParent.y << std::endl;

        for(unsigned int j = 0U; j < myParent.childList.size(); j++)
        {
            const Child mychild = myParent.childList[j];

            std::cout << mychild.a << std::endl;
            std::cout << mychild.b << std::endl;
        }
    }
}


Main()
{
    Message myMessage;
    //some code to initialise myMessage's vector by calling addParent
    //....
    //...

    int idx = 0;
    while (idx < 10000000)
    {
        myMessage.printingMethod();
        idx++;
    }

}

Если цикл while только выполняет циклскажем, 100 раз, не будет никаких проблем.Однако, если я увеличу цикл while до 10000000 раз, в этом разделе будет вероятность ошибки сегментации:

    for(unsigned int i = 0U; i < parentList.size(); i++)
    {
        const Parent myParent = parentList[i];//<-segmentation fault

        std::cout << myParent.x << std::endl;
        std::cout << myParent.y << std::endl;

        for(unsigned int j = 0U; j < myParent.childList.size(); j++)
        {
            const Child mychild = myParent.childList[j];//<-segmentation fault

            std::cout << mychild.a << std::endl;
            std::cout << mychild.b << std::endl;
        }
    }

Но если я просто изменю его на эталонный объект, сегментация не будетошибка.

    for(unsigned int i = 0U; i < parentList.size(); i++)
    {
        const Parent & myParent = parentList[i];//<-no segmentation fault

        std::cout << myParent.x << std::endl;
        std::cout << myParent.y << std::endl;

        for(unsigned int j = 0U; j < myParent.childList.size(); j++)
        {
            const Child & mychild = myParent.childList[j];//<- no segmentation fault

            std::cout << mychild.a << std::endl;
            std::cout << mychild.b << std::endl;
        }
    }

Может кто-нибудь объяснить, почему я получаю ошибку сегментации для скопированного объекта, но не для ссылочного объекта?

Или «исправление» - просто случайность, и я в конечном итоге получу ошибку сегментации?

TIA.

1 Ответ

0 голосов
/ 20 сентября 2019

Чтобы помочь вам найти причину ошибки, как указано в комментариях, вы хотите посыпать свой код несколькими символами, чтобы увидеть размер вектора и используемые вами индексы (j).

Также использование myParent.childList.at(j) приведет к тому, что вы выйдете за пределы.

В вашем случае использование ссылок просто включает некоторые оптимизации, которые могут объяснить, почему он не вызывает ошибки, но вы не должныне надейся на это.

...