Нарушение доступа с OCCI next () и setDataBuffer () - PullRequest
0 голосов
/ 14 января 2020

к сожалению, я не вижу леса за деревьями и мне нужна помощь. Я называю результирующий набор с помощью инструкции SELECT, которая имеет 70 столбцов. Я инициализирую свой буфер для всех 70 столбцов, которые являются символами, и устанавливаю их с помощью setDataBuffer. К сожалению, я могу получить только 15-17 записей. После этого я получаю сообщение об ошибке Access Violation. Если я попробую следующий (1000), он не будет работать вообще. Я думаю, что это как-то связано с указателями, но я не вижу ошибки. Кто-нибудь знает, что я делаю не так?

            #pragma region Arrays
            char*** data_array  = new char**[70];
            for (unsigned int i = 0; i < 70; ++i)
            {
                data_array[i] = new char*[1000];
                for (unsigned int j = 0; j < 1000; ++j)
                {
                    data_array[i][j] = new char[500];
                }
            }

            ub2**   size_array  = new ub2 * [70];
            for (unsigned int i = 0; i < 70; ++i)
            {
                size_array[i] = new ub2[1000];
            }

            sb2**   ind_array   = new sb2 * [70];
            for (unsigned int i = 0; i < 70; ++i)
            {
                ind_array[i] = new sb2[1000];
            }

            ub2**   rc_array    = new ub2 * [70];
            for (unsigned int i = 0; i < 70; ++i)
            {
                rc_array[i] = new ub2[1000];
            }
            #pragma endregion

            #pragma region setDataBuffer
            for (unsigned int i = 0; i < 70; ++i)
            {
                resultSet->setDataBuffer(i + 1, data_array[i][0], OCCI_SQLT_STR, 500, size_array[i], ind_array[i], rc_array[i]);
            }
            #pragma endregion

            try
            {
                ResultSet::Status resultSetStatus = resultSet->next(25);
                if (resultSetStatus == ResultSet::Status::DATA_AVAILABLE)
                {
                    unsigned int rowCount = resultSet->getNumArrayRows();
                    for (unsigned int row = 0; row < rowCount; ++row)
                    {
                        for (unsigned int column = 0; column < 70; ++column)
                        {
                            auto value =  data_array[column][row];
                            auto vsize = *size_array[column];

                            std::string cellContent(value, vsize);
                        }
                    }
                }
            }
            catch(SQLException& sqlEx)
            {
                std::string msg = sqlEx.getMessage();
                int i = 0;
            }

1 Ответ

1 голос
/ 14 января 2020

Проблема заключается в выделении data_array, поскольку вы создаете его как зубчатый массив , а не непрерывный массив памяти, необходимый для setDataBuffer.

Если вы хотите использовать динамическое выделение c с использованием new[], я предлагаю вместо этого нечто подобное:

using data_type = int8_t[1000][500];
auto data_array = new data_type[70];

Тогда каждый элемент data_array будет смежным область памяти, 1000 * 500 байт.


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

...