Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

C++ - passing an array of unknown size [duplicate]

Trying to pass an int array of consecutive numbers starting with 1 but assuming the function receiving this array does not know it's length. When trying to calculate the length inside the function it just gives me 1 since it only finds the first element when calculating sizeof(arrayName).

#include <iostream>
using namespace std;

int Sum(int intArray[]) {
    int n = sizeof(intArray) / sizeof(*intArray);
    cout << "Array size in function: " << n << endl;
    return n * (n + 1) / 2;
}

int main() {
    int anArray[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
    int arraySum = Sum(anArray);

    cout << "Array size in main: " << sizeof(anArray) / sizeof(*anArray) << endl;
    cout << "Sum is: " << arraySum;
    int a;
    cin >> a;
    return 0;
}
like image 396
Instinct Avatar asked Jan 29 '14 23:01

Instinct


2 Answers

Your function is taking a pointer to int. All size information is lost as you pass the array into the pointer. But you can use a function template to instantiate functions that match the right array size:

template <size_t N>
int Sum(const int (&intArray)[N])
{
  cout << "Array size in function: " << N << endl;
  return std::accumulate(std::begin(intArray), std::end(intArray), 0);
}

This Sum function will accept plain arrays or size known at compile time. However, it makes more sense to use std::array for these cases, or std::vector for cases when the size is chosen at runtime.

Note that the call to std::accumulate is just an example that solves the sum problem. It does not require knowledge of N, and could replace the function entirely. The size is taken care of by std::begin and std::end. You would need headers <numeric> and <iterator> for accumulate and begin/end respectively.

like image 82
juanchopanza Avatar answered Nov 02 '22 18:11

juanchopanza


In this function declaration

int Sum(int intArray[]);

array passed to it as an argument is implicitly converted to the pointer to the first element of the array. So this declaration is equivalent to

int Sum( int *intArray );

And the expression

int n = sizeof(intArray) / sizeof(*intArray );

is equivalent to

int n = sizeof( int * ) / sizeof( int );

if sizeof( int * ) is equal to sizeof( int ) then n will be equal to 1.

If you declare the parameter such a way as you did then you should also declare a second parameter that will accept the number of elements in the array. So I would rewrite the function the following way

int Sum( int intArray[], size_t n ) 
{
    int sum = 0;

    for ( size_t i = 0; i < n; i++ ) sum += intArray[i];

    return sum;
}

and in main I would call the function the following way

int arraySum = Sum( anArray, sizeof( anArray ) / sizeof( *anArray ) );

}

Also functions ususally are written to perform some general algorithms. It is a bad idea to write a function only for arrays that has sequantial values from 1 to some N.

like image 44
Vlad from Moscow Avatar answered Nov 02 '22 19:11

Vlad from Moscow