0

Ocilibを使用してOracleデータベースで一括挿入を実行していますが、文字列バッファーの入力中に問題が発生しています。

ドキュメントには次のように書かれています。

文字列/RAW配列の場合、入力配列は、ポインタの配列ではなく、データの連続ブロックである必要があります。したがって、varchar2(30)列の10個の要素の配列をバインドするには、バインドされた変数はarray[10][31]のようである必要があります。

そして、サンプルは次のようにバッファを埋めていきます。

...
char tab_str[1000][21];
...
OCI_BindArrayOfStrings(st, ":s", (char*) tab_str, 20, 0);
...

for(i=0;i<1000;i++)
{
    sprintf(tab_str[i],"Name %d",i+1);
}
...

MyClassのstd::vectorをループしながら、文字列バッファを埋めようとしています。MyClassにはstd::stringメンバーがあります。

std :: string :: copyメソッドを使用して、文字列の内容をバッファにコピーしようとしています。しかし、それを行うためにバッファにインデックスを付ける方法を正確に知りません。

...
OCI_BindArrayOfStrings(st, ":f2", NULL, VCHAR_SIZE, 0);
char** vc_buffer = (char**)OCI_BindGetData(OCI_GetBind(st, 2));
...
int i = 0;
for(vector<MyClass>::const_iterator it = myVec.begin(); it != myVec.end(); ++it)
{
    /* 1st try */ it->m_string.copy((vc_buffer + (i * VCHAR_SIZE)), VCHAR_SIZE);
    /* 2nd try */ it->m_string.copy(vc_buffer[i], VCHAR_SIZE);
    ++i;
    ...
}
...

最初の方法では、データベース内のバグのあるデータが得られます。2つ目は、nullポインタをヒットさせます。

私が間違っているのは何ですか?

PS

2番目のアプローチは、以下のAlessandro Verganiによって提案されたアプローチに沿っており、null文字列が挿入されます。最初のアプローチでは、この(やや奇妙な)結果が得られます。

データベースの内容

gvimウィンドウには、どのように表示されるかが表示され、apex画面には、データベースに保存される内容が表示されます。

4

1 に答える 1

1

(試す:

std::vector<char> tab_str(myVec.size() * (VCHAR_SIZE + 1));
...
OCI_BindArrayOfStrings(st, ":s", &tab_str[0], VCHAR_SIZE, 0);
...
int offset = 0;
for(vector<MyClass>::const_iterator it = myVec.begin(); it != myVec.end(); ++it, offset += VCHAR_SIZE)
{
    it->m_string.copy(&tab_str[offset], VCHAR_SIZE);
    ...        
}
...

nullターミネータを追加する必要があるかどうかはわかりません。追加しない場合は-1、コピーからを削除して2行目を削除してください。

于 2011-02-03T15:52:44.097 に答える