提示されたコードにはいくつかのエラーがあります。最初にそれについて説明し、次にポインターと配列のストック ディアトライブについて説明します。
struct charMap
{
unsigned int * name;
unsigned int id;
};
typedef struct charMap CharMapT;
これは、最初のメンバー (名前) として unsigned int へのポインターを含み、2 番目のメンバー (id) として int を含む構造体型を宣言します。デフォルトのバイト パッキングを使用する 32 ビット システムでは、これは8 バイト幅になります (32 ビット ポインタ = 4 バイト、32 ビット符号付き int = 4 バイト)。これが 64 ビット マシンの場合、ポインタは 8 バイト幅になり、int はおそらく 32 ビット幅になり、構造体のサイズは12 バイトになります。
問題のあるコード
void ABC::Function ()
{
CharMapT list[] =
{
{"NAME1", 1},
{"NAME2", 2},
{"NAME3", 3}
};
structList = new CharMapT[sizeof(list)];
memcpy(structList, &list, sizeof(list));
}
これにより、CharMapT 構造体の動的配列が割り当てられます。幾つか?あなたが思うよりももっと。は、配列sizeof(list)
のバイト数を返します。list[]
CharMapT 構造体は 8 バイト幅 (上記を参照) であるため、これは 3 * 8、つまり24 個の CharMapT アイテム(64 ビット ポインターを使用する場合は 36 個のアイテム) になります。
次に、 ( inは不要) からmemcpy()
24バイト(または 36 バイト)を、新しく割り当てられたメモリに移動します。これにより、3 つの CharMapT 構造がコピーされ、割り当てた残りの 21 はそのまま残ります (最初のデフォルトの構築を超えて)。list
&
&list
注: aconst char *
を として宣言されたフィールドに初期化しているunsigned int *
ため、これをコンパイルしても基本的なデータ型は異なります。構造を修正してポインターの型を に変更するとconst char *
、const データ セグメントのどこかにある静的文字列定数のアドレス ("NAME" 定数のアドレス) が、structList[0] の要素のポインター変数に割り当てられます。 .name、structList[2].name、および structList[3].name です。
これは、 が指すデータをコピーしません。ポインタ値のみをコピーします。データのコピーが必要な場合は、それらを生で割り当てる必要があります (malloc、new など)。
さらに良いのは、 を使用しstd::vector<CharMapT>
、std::string
forCharMapT::name
を使用std::copy()
し、 ソースをレプリケートするために使用します (または直接割り当ても可能です)。
あなたが探していたものを説明してくれることを願っています。
ポインター vs. アレイ Diatribe
ポインターと配列を混同しないでください。ポインタは、アドレスを保持する変数です。変数が整数値を保持するか、変数が文字型を保持するように、ポインターに保持される値はアドレスです。int
char
配列が異なります。これは (明らかに) 変数でもありますが、左辺値にすることはできず、通常使用されるほぼすべての場所で変換が行われます。概念的には、その変換により、配列のデータ型を指す一時ポインターが生成され、最初の要素のアドレスが保持されます。その概念が起こらない場合があります(address-of 演算子の適用など)。
void foo(const char * p)
{
}
char ar[] = "Hello, World!";
foo(ar); // passes 'ar', converted to `char*`, into foo.
// the parameter p in foo will *hold* this address
またはこれ:
char ar[] = "Goodbye, World!";
const char *p = ar; // ok. p now holds the address of first element in ar
++p; // ok. address in `p` changed to address (ar+1)
しかし、これではありません:
char ar[] = "Goodbye, World!";
++ar; // error. nothing to increment.