1

I'm trying to use the new operator to allocate a 2d array. This is my function new2d.

int** new2d(int r, int c)
{
    int **t = new int*[r];
    for(int i = 0; i < r; i++)
        t[i] = new int[c];
    return t;
}

I'm pretty sure this is the correct way to do it. However, when I try to print the array like below

int **a = new2d(5, 9);
for(int i = 0; i < 5; i++)
{
    for(int j = 0; j < 9; j++)
    {
        cout << a[i][j] << " ";
    }
    cout << endl;
}

it gives this weird output with random 13,10,7...

0 0 0 0 13 0 0 0 0 
0 0 0 0 10 0 0 0 0 
0 0 0 0 7 0 0 0 0 
0 0 0 0 4 0 0 0 0 
0 0 0 0 0 0 0 0 0 

Why does this happen?

The Vivandiere
  • 3,059
  • 3
  • 28
  • 50
Tony Tarng
  • 699
  • 2
  • 8
  • 17
  • 6
    You never initialized the values in each row. The data you see is *indeterminate*. Change this: `new int[c];` to this: `new int[c]();`. Better still, change the whole thing to `std::vector> a(5, std::vector(9));` – WhozCraig Jul 21 '15 at 21:53
  • It is well known that `new` is not required to initialise the allocated memory for you. If it were, and you wanted something other than its default initialisation, `new` would be making a decision for you, only to waste your time. However, by deliberately specifying a constructor on the target object, you can have _it_ perform its own defined initialisation. – underscore_d Jul 21 '15 at 21:57
  • I highly recommend doing as WhozCraig says. Playing with raw pointers is risky. – The Vivandiere Jul 21 '15 at 21:59
  • ^ Especially when C++ offers so many better solutions. – underscore_d Jul 21 '15 at 21:59
  • Got it, thanks guys! But what's the new int[c]( ); for? – Tony Tarng Jul 21 '15 at 22:05
  • `()` invokes the default ctor for `int`, which conveniently initialises to 0. – underscore_d Jul 21 '15 at 22:07
  • @TonyTarng it invokes *value-initialization*, and is covered in the standard, C++11 § 8.5,p7, and C++11 § 8.5,p10. After going on about discussion various construction models, the bailout case is simply "... otherwise, the object is **zero-initialized**." Worth reading. Get a copy. – WhozCraig Jul 21 '15 at 22:10
  • @WhozCraig Ok, thanks! – Tony Tarng Jul 21 '15 at 22:15

2 Answers2

1

Default initialization can lead to indeterminate values. Quoting from http://en.cppreference.com/w/cpp/language/default_initialization

Default initialization is performed in three situations:

1) when a variable with automatic, static, or thread-local storage duration is declared with no initializer.

2) when an object with dynamic storage duration is created by a new-expression with no initializer or when an object is created by a new-expression with the initializer consisting of an empty pair of parentheses (until C++03).

3) when a base class or a non-static data member is not mentioned in a constructor initializer list and that constructor is called.

The effects of default initialization are:

If T is a non-POD (until C++11) class type, the constructors are considered and subjected to overload resolution against the empty argument list.

The constructor selected (which is one of the default constructors) is called to provide the initial value for the new object.

If T is an array type, every element of the array is default-initialized. Otherwise, nothing is done: the objects with automatic storage duration (and their subobjects) are initialized to indeterminate values.

In your case, you meet condition 2.

The Vivandiere
  • 3,059
  • 3
  • 28
  • 50
0

It seems you do not initialize array after t[i] = new int[c]; However this is not optimal way to create arrays. Here is a bigger discussion How do I declare a 2d array in C++ using new?

Well. Usually it is better to use an approach such as

int *array = new int[sizeX*sizeY];

ary[i][j] is then rewritten as array[i*sizeY+j].

And yes, it is better to read big discussion, to understand + and - better

Community
  • 1
  • 1
mavrik
  • 11
  • 4
  • Saying "this is not optimal" implies there is a better way. Linking to a large discussion of several alternative methods does not tell us _which_ way you think is better. This does not help much. – underscore_d Jul 21 '15 at 22:14