Сохранить указатель для констант в вектор структур - PullRequest
0 голосов
/ 26 декабря 2018

У меня проблема с выполнением следующих действий:

Класс "A":

    const uint8_t arr1[] = {0x00, 0x00, 0x03, 0x00, ...};
    const uint8_t arr2[] = {0xA1, 0x00, 0xFF, 0x00, ...};    

    struct s1 {
         String name;
         uint8_t const * arr;
    };
    std::vector<s1, std::allocator<alloc1>> vect1;
    std::vector<s1>::iterator it = vect1.begin();

   privateMethod1(uint8_t const * ptr) {
      // this method receives pointer correctly, so I can doPrint(ptr)
      s1 myStruct;
      myStruct.name = "name";
      myStruct.arr = ptr;
      vect1.push_back(myStruct);
   }

    myPublicMethod(String arrName) {
        uint8_t const * ptr;
        if(arrName == "A") {
              ptr = arr1;
        } else if(arrName == "B") {
              ptr = arr2;
        }
        privateMethod1(ptr);
    }

Несколько мгновений спустя ...

  myPublicMethod2() {
      for(; it < vect1.end(); it++) {
         doPrint(it->arr);
         // here the link between pointers broken, 
         // doPrint() shows me random characters
      }
   }

Очевидно, проблема в том, чтобы правильно хранить arr1 или arr2 в myStruct.У кого-нибудь есть идея, где я ошибаюсь, используя указатели?Спасибо

Ответы [ 2 ]

0 голосов
/ 27 декабря 2018

Итак, я понял это.Следующий код близок к реальному примеру, который я публиковал ранее.

#include <iostream>
#include <string.h>
#include <vector>

const uint8_t arr1[] = {0x00, 0x00, 0x03, 0x00};
const uint8_t arr2[] = {0xA1, 0x00, 0xFF, 0x00};

class A {
public:
    struct s1 {
        std::string name;
        uint8_t const * arr;
    };
    std::vector<s1, std::allocator<s1>> vect1;

    void myPublicMethod(std::string arrName, std::string name) {
        uint8_t const * ptr;
        if(arrName == "A") {
            ptr = arr1;
        } else if(arrName == "B") {
            ptr = arr2;
        }
        privateMethod1(ptr, name);
    }

    void myPublicMethod2() {
        auto i = vect1.begin();
        for(; i < vect1.end(); i++) {
            doPrint(i->arr, i->name);
            // here the link between pointers broken,
            // doPrint() shows me random characters
        }
    }

private:
    void privateMethod1(uint8_t const * ptr, std::string name) {
        // this method receives pointer correctly, so I can doPrint(ptr)
        s1 myStruct;
        myStruct.name = name;
        myStruct.arr = ptr;
        vect1.push_back(myStruct);
    }

    void doPrint(const uint8_t arr[], std::string name) {
        for(uint16_t i = 0; i < sizeof(*arr); i++) {
            if(name.length() > 0) {
                std::cout << arr[i] << '\n';
            } else {
                std::cout << "No name\n";
            }
        }
    }
};


int main() {
    A ca;
    ca.myPublicMethod("A", "");
    ca.myPublicMethod("B", "image");
    ca.myPublicMethod2();
    return 0;
}

Этот код - лишь малая часть проекта (основной код).Я считаю невозможным / ненужным публиковать весь проект, потому что есть много ненужных материалов, которые определенно потребуют много времени, чтобы понять.

Сначала я подумал, что есть проблема с указателями, особенно в A :: myPublicMethod, который создает * ptr, который затем передается в A :: privateMethod1 для хранения в vect1.Я ошибся, думая, что при сохранении / переносе в vect1 произошла ошибка.В последнее время я не нашел никаких изменений для vect1 в основном коде.Vector vas создан хорошо, проблема была в методе doPrint, особенно в том, что if (name.length ()> 0) ... Итак, я должен был придерживаться логики основного кода, не выдумывая пример, который был далек отРеальность.

В заключение спасибо @paulmckenzie, который косвенно дал мне повод перестать мыслить указателями.Мне бы очень помогло, если бы кто-то только что подтвердил, что, следуя моему первому примеру, указатели логически верны.

Cheers,

0 голосов
/ 26 декабря 2018

Вы даете нам недопустимый код C ++, он содержит множество ошибок.

Вы не можете дать нам определение String и alloc1

Вы пропустите, чтобы дать нам выполнение, которое вы сделаликак правило, аргумент myPublicMethod

Поэтому, чтобы ответить вам, нам нужно использовать магический хрустальный шар

Одна из возможностей (arrName == "A") и (arrName == "B") ложна, поэтому выне инициализировать ptr.Эти тесты возвращают false, например, когда определение String равно typedef const char * String;

...