Passing Array into function C++ issue

Started by
14 comments, last by SiCrane 13 years, 2 months ago
Yeah so i'm currently learning c++. Coming from programming in Java I was always used to getting the length of arrays by just putting ".length" but in C++ a little math is required. So basically what i tried to do is make a function that takes the array and returns the length. Sounds simple right? The problem is that i need the size of the whole array and the size of the data type in order to calculate the length of the array but apparently the size of the array changes when you pass it into a function.
Is there a way around this or am i screwed?


# include <iostream>

using std:: cout;
using std:: cin;
using std:: endl;

int main(){
//Adding prototype
int GetLength(int array[]);
//Initilizing Variables
int array[80];
int pause = 0;
int size =0 ;
int sizeFunc = 0;

size = (sizeof(array)/sizeof(int)) -1 ;

for (int i = 0; i < size ; i++){
array = i +1 ;
}
sizeFunc = GetLength(array);
//Sets Numbers
cout << "Size Function Returns..." << sizeFunc << endl;
cout << "Regular Calculation..." << size;
cin >> pause;
return 0;
}
int GetLength( int Array[]){
int size =0 ;
cout << "Array size that passed into function is--->" << sizeof(Array) << endl;
cout << "Array size type that passed into function is--->" << sizeof(int) << endl << endl;
size = (sizeof(Array)/sizeof(int)) - 1 ;
return size ;
}


i feel like such a noob for asking this...
the humiliation...
Advertisement
Why not a std::vector? That's why it's there is to save you these kinds of headaches.
[size=2]My Projects:
[size=2]Portfolio Map for Android - Free Visual Portfolio Tracker
[size=2]Electron Flux for Android - Free Puzzle/Logic Game
The size of the array hasn't changed at all. What you've encountered is colloquially known as array to pointer decay. In essence your array parameter has been converted to a pointer type.

There are a few things you "could" do to get the size of the array, assuming it's static at compile time, such as through the use of templates.

Realistically though, the use of std::vector is recommended, allocating fixed size arrays on the stack is generally A Bad Idea (tm).

In time the project grows, the ignorance of its devs it shows, with many a convoluted function, it plunges into deep compunction, the price of failure is high, Washu's mirth is nigh.


Why not a std::vector? That's why it's there is to save you these kinds of headaches.


I haven't made it that far into my book yet but if you say using std::vector will work then i'll take your word for it.


If you aren't that far along, and wish to still use arrays, then the answer is as follows: You pass the size in to every function that must access your array.

In time the project grows, the ignorance of its devs it shows, with many a convoluted function, it plunges into deep compunction, the price of failure is high, Washu's mirth is nigh.

For completeness, here is a function that returns the static size of an array. It will not work with an array passed to a function, but it will not compile for you in that case.

This is reasonably advanced code, if you haven't come across std::vector<> yet you might not understand how it works. Basically, it takes advantage of the fact that C++ arrays include their size as part of the type, and uses C++ templates to deduce the size of the array passed to it.


template<typename T, size_t N>
size_t array_size(T (&)[N])
{
return N;
}

As the others have mentioned, using raw arrays isn't recommended. They can be good for certain kinds of static data that cannot be externalised into a file.

Coming from a Java background, std::vector<> is similar to ArrayList<>.

For completeness, here is a function that returns the static size of an array. It will not work with an array passed to a function, but it will not compile for you in that case.

This is reasonably advanced code, if you haven't come across std::vector<> yet you might not understand how it works. Basically, it takes advantage of the fact that C++ arrays include their size as part of the type, and uses C++ templates to deduce the size of the array passed to it.


template<typename T, size_t N>
size_t array_size(T (&)[N])
{
return N;
}

As the others have mentioned, using raw arrays isn't recommended. They can be good for certain kinds of static data that cannot be externalised into a file.

Coming from a Java background, std::vector<> is similar to ArrayList<>.

Since we're going there... Let's not forget the static compile time determination:
template<class T>
struct array_size;

template<class T, size_t S>
struct array_size<T[S]> { static const int size = S; };
//or std::extent if in C++0x

In time the project grows, the ignorance of its devs it shows, with many a convoluted function, it plunges into deep compunction, the price of failure is high, Washu's mirth is nigh.

What is the utility of that? If you can only pass types to it, and not values, then how does it help? It would appear to me that writing array_size<char[400]>::size is a verbose way to write "400". The only place I can see that as being useful is when the array is a typedef. An optimising compiler will happily inline the function I provided and should generate a constant at the calling location, so you should get compile time determination of the array length too.

Unless it has some extra secret sauce I'm not aware of? Or am I missing something in my understanding?

What is the utility of that? If you can only pass types to it, and not values, then how does it help? It would appear to me that writing array_size<char[400]>::size is a verbose way to write "400". The only place I can see that as being useful is when the array is a typedef. An optimising compiler will happily inline the function I provided and should generate a constant at the calling location, so you should get compile time determination of the array length too.

Unless it has some extra secret sauce I'm not aware of? Or am I missing something in my understanding?


A compile time unrolled loop comes to mind.

In time the project grows, the ignorance of its devs it shows, with many a convoluted function, it plunges into deep compunction, the price of failure is high, Washu's mirth is nigh.

Why not just use a Boost Array? That's the closest equivalent to a Java array.

It has all the type safety and container functions without the overhead of a vector.
I trust exceptions about as far as I can throw them.

This topic is closed to new replies.

Advertisement