Копировать Occi:: ResultSet перед закрытием Occi:: Connection
Я использую OCCI с C++ для получения данных от Oracle. Код работает хорошо, однако я заметил некоторое снижение производительности. Это происходит потому, что в итерации rset->next() некоторое вычисление занимает время. Влияние этой задержки заключается в том, что пул соединений oracle имеет одно соединение занято. Если одновременные запросы требуют одного и того же вычисления, возможно, все соединения в пуле будут заняты.
Statement *stmt = conn->createStatement (sqlQuery);
ResultSet *rset = stmt->executeQuery ();
while (rset->next ())
{
//Slow computation takes time
compute()
}
stmt->closeResultSet (rset);
conn->terminateStatement (stmt);
env->terminateConnection (conn);
Итак, мой вопрос: Могу ли я скопировать Occi:: ResultSet (используя общий указатель?) в порядке чтобы закрыть соединение после копирования и выполнить вычисления после освобождения соединения?
go_to_oracle( ResultSet &result) {
Statement *stmt = conn->createStatement (sqlQuery);
ResultSet *rset = stmt->executeQuery ();
copy_rset_to_result;
stmt->closeResultSet (rset);
conn->terminateStatement (stmt);
env->terminateConnection (conn);
}
my_method() {
ResultSet *result = NULL
go_to_oracle(result);
//here connection is closed, but we have the data
compute(result) // do this without have connection occupied
}
Есть ли примеры, доступные на GitHub?
2 ответа:
Невозможно закрыть соединение с базой данных и сохранить результирующий набор (occi::ResultSet) для последующего использования. Одна из причин заключается в том, что occi::ResultSet::next извлекает данные из базы данных. Вместо этого вы можете использовать выборку массива и буфер данных, выделенный Пользователем для хранения результатов.
Пример использования occi:: ResultSet:: setDataBuffer:
oracle::occi::ResultSet* rs=nullptr; //..... // query //..... static const size_t max_numrows=5000; char var_buf[max_numrows][7]; char sym_buf[max_numrows][9]; rs->setDataBuffer(1,var_buf,oracle::occi::OCCI_SQLT_STR,sizeof(var_buf[0]),(ub2*)0); rs->setDataBuffer(2,sym_buf,oracle::occi::OCCI_SQLT_STR,sizeof(sym_buf[0]),(ub2*)0); size_t fetch_count=0; while(rs->next(max_numrows)==ResultSet::DATA_AVAILABLE) { /* This would probably be an error as you would like the whole result to fit in the data buffer.*/ } stmt->closeResultSet (rs); conn->terminateStatement (stmt); compute(var_buf,sym_buf);
Обратите внимание, что массив fetch действует как prefetch в этом
Status next( unsigned int numRows =1);
Получает до numRows за вызов.