How to Create an Array of Pointers

How do I create an array of pointers?

Student** db = new Student*[5];
// To allocate it statically:
Student* db[5];

Create array of pointers in C++

Hope this will help, here is a basic explanation of what the line means with some crude illustrations.
Please note that all addresses are made up, and some things are simplified in hopes of making the concept easier to see. Forgive the crude art, I am far from an artist!
const char* headers[]= {"apple","pear","tree"};

This line is telling the compiler that you would like to allocate an array. The elements in the array will be of type char*. The const keyword tells the compiler that the object or variable is not modifiable. char* is the type of elements in the array. headers is the variable name, and the brackets [] indicate that headers is an array. The rest of the line is an initializer for the array. header will have 3 elements of type char* which basically means “pointer to a string of characters”.

The compiler will also allocate memory and initialize the array by filling it with each of the 3 strings in the braces {"apple","pear","tree"}

The first element in the header array header[0] will contain a pointer to the memory where the string “apple” is located.
The second element in the header array header1 will contain a pointer to the memory where the string “pear” is located.

Sample Image

How to Create an array of pointers to structs?

If you were using C, you might do something like:

Item* items[100]; //an array of Item*

To allocate a new Item, and store a pointer to this Item in the array, you might do something like:

items[i] = malloc(sizeof(Item));

To access an element you can use the de-reference (*) or arrow (->) operators. The latter is probably prefered if you just want to access a member of the struct:

items[i]->id
*(items[i]).id

To pass the array to a function you can just pass the array items just like you would a normal array.

Before the array passes out of scope, make sure to clean up the allocated Items. So, for each value that you initialized in the array:

free(items[i])

Of course, if you are using C++, you would want to avoid using malloc/free and instead use the new and delete operators, as is standard (you cannot mix them).

c++ dynamic array of pointers

According to the C++ Standard (4.2 Array-to-pointer conversion)

1 An lvalue or rvalue of type “array of N T” or “array of unknown
bound of T” can be converted to a prvalue of type “pointer to T”. The
result is a pointer to the first element of the array.

So for example if you have an array like this

int a[] = { 1, 2, 3, 4, 5 };

then in this declaration

int *p = a;

the array designator used as the initializer is implicitly converted to pointer to its first element.

So in general if you have array

T a[N];

then in expressions with rare exceptions it is converted to pointer to its first element of the type T *.

In this declaration

int **arr = new int*[10]; 

the initializer is an array elements of which has the type int *. You can introduce a typedef or an alias declaration

typedef int * T;

or

using T = int *;

So you can write

T * arr = new T[10]; 

that is the pointer arr points to the first element of the dynamically allocated array. As the elements of the array has the type int * then the type of the pointer to an element of the array is int **.

That is the operator new returns pointer to the first element of the dynamically allocated array.

Is a 2D Array an Array of Pointers?

The way you have defined A means that the compiler will allocate for it a contiguous block of memory large enough to hold 10 x 20 (200) integers; see here (scroll down to "Multidimesional arrays"). As I'm sure you realize, if you were to do printf("%p", A); you would see the address of the beginning of that allocated block.

Now, when the compiler sees the expression A[3], it will add what it calculates as the necessary amount of "integer sizes" to the base address (that of A, or A[0][0]); in this case, it will add "3" (the index specified) multiplied by the combined size of all the other dimensions (in this case, there's only one, which is 20).

So, in your case, there is no actual array of pointers; just a memory block that the compiler can interpret according to how you described any part(s) of it.

However, in a more versatile approach, one can actually define a 2D array in terms of an actual array of pointers, like so:

int **A;
A = malloc(10 * sizeof(int*));
for (int n = 0; n < 10; ++n) A[n] = malloc(20 * sizeof(int));

In this case, using printf("%p",A[3]); would still be valid, but it would give a very different offset value from printf("%p",A); or printf("%p",A[0]);.

It's also, perhaps, worth noting that, even though these two different declarations for A can both resolve an individual element through an expression like A[i][j] (but the compiler would evaluate the addresses differently), there is here scope for major confusion! When, for example, passing such an array to a function: if the function expects data allocated in the second form, and you give it an array defined in the first form (and vice versa), you're gonna get major undefined behaviour .

How to create an array of pointers in c++

As mentioned in comments above; the array should be an Item* type. Since question is posted as C++14, using <array> allows you to access the values by reference; instead of manually indexing. This is more scalable as the for loop doesn't have to be updated in the future. It also eliminates possible bugs or errors when the array size doesn't match the 'for' loop.

In order to access the child class function using the base class pointer, a virtual function needs to be defined. The example below demonstrates how to implement the virtual function in each class.

For bonus points, it also demonstrates how to call the parent's toString within each child class.

#include <array>
#include <string>
#include <iostream>

class Item
{
public:
Item(const char* const name):
mName(name)
{}

virtual std::string toString() const
{
return mName;
}
private:
std::string mName;

};

class Equipment : public Item
{
public:
Equipment(const char* const name):
Item(name)
{}

virtual std::string toString() const override
{
const std::string extraInfo {"Equipment->"};
const std::string item {Item::toString()};
return extraInfo + item;
}
};

class Consumable : public Item
{
public:
Consumable(const char* const name):
Item(name)
{}

virtual std::string toString() const override
{
const std::string extraInfo {"Consumable->"};
const std::string item {Item::toString()};
return extraInfo + item;
}
};

class Weapon : public Equipment
{
public:
Weapon(const char* const name):
Equipment(name)
{}

virtual std::string toString() const override
{
const std::string extraInfo {"Weapon->"};
const std::string item {Equipment::toString()};
return extraInfo + item;
}
};

int main()
{
Weapon greatSword("Great Sword");
Weapon mekiChestplate("Meki's Chest Plate");
Consumable pie("Grandma's Pie");
Consumable spiderVenom("Spider's Venom");

std::array<Item*, 4> inventory
{
&greatSword,
&mekiChestplate,
&pie,
&spiderVenom
};

for (auto it : inventory)
{
std::cout << it->toString() << std::endl;
std::cout << "-----------------------------------------------------------" << std::endl;
}

return 0;
}


Related Topics



Leave a reply



Submit