Constructor not accepting my agruement list

I have this writen in my main;
1
2
3
4
5
6
7
8
9
double marks[18];
unsigned int Age;
unsigned int ID;
unsigned int CourseCount;
char FirstName[10];
char LastName[10];
Course Courses[18];
.....
StudentRecordData r(marks,Age,ID,CourseCount,FirstName,LastName,Courses);


This is the StudentRecordData class:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15

class StudentRecordData
{
   double Marks[MAX_COURSES];
   unsigned int Age;
   unsigned int ID;
   unsigned int CourseCount;
   char FirstName[LEN_FN];
   char LastName[LEN_FN];
   Course  Courses[MAX_COURSES];
public:
	StudentRecordData(double m[18], unsigned int age, unsigned int id, unsigned int cc, char fn[10], char ln[10], Course c);
	unsigned int getID() {return ID;}
	
};


Shouldnt that match?

Heres the cpp for the class:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
StudentRecordData::StudentRecordData(double m[18], unsigned int age, unsigned int id, unsigned int cc, char fn[10], char ln[10], Course c)
{
	for(int i=0;i<18;i++)
		Marks[i] = m[i];

	Age = age;
	ID = id;
	CourseCount = cc;
	strcpy(FirstName, fn);
	strcpy(LastName, ln);

	//
	for(int i=0; i<18; i++)
	{
		if (Marks[i] > 0)
			cout << Marks[i] << " ";
	}
	cout << endl << "Age: " << Age << " ID: " << ID << " Course Count: " << CourseCount << " First Name: " << FirstName
		<< " Last Name: " << LastName;
}
What error do you get? (PS: I am not quite sure you are allowed to have fixed length arrays as function parameters - there is no way for the function to check the length of a passed array on runtime).
Last edited on
@matthewfs
Please post your exact error message(s).

@hanst99
You can, the length is part of the type. Type promotion allows you to drop the length into a general pointer, so that you can pass things of different lengths...

Its the Course class thats being passed because when i take it out of the list is works prefect
...because the argument list expects an array of 18 Courses, but you are passing only one...
So while you are allowed to put array lengths in function parameters, does it actually achieve anything other than informing the programmer of what is expected to be passed to it?
Yes. It forces the programmer to actually pass the same type of thing to it. If he doesn't, he gets a compile error.
Thanks for the advice.

So this code wouldn't compile? (Sorry if I'm being a bit slow here...)

1
2
3
4
5
6
7
8
9
10
void do_something (int values[18]) { }

int main()
{
   int* ints = new int[10];
   do_something(ints);
   delete [] ints;
   return 0;
}


I read in a C++ book that void (int*) and void (int [some_number]) are exactly the same. But then I also read elsewhere that the book wasn't so great ;)
Er, I think you've got it.

The type of thing you pass a function must match the type of thing the function expects.

So the following will compile:

1
2
3
4
5
6
7
8
9
10
void do_something( int values[18] )
{
}

int main()
{
  int xs[18] = { 1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18 };
  do_something( xs );
  return 0;
}

The following will not:

1
2
3
4
5
6
7
8
9
10
void do_something( int values[18] )
{
}

int main()
{
  int x = -5;
  do_something( x );
  return 0;
}

Hope this helps.
What I would really care about is, would passing another int array or a pointer work?
Yeah that's what I meant. I know the types of parameters and arguments must match, but I read that the compiler ignores the numbers in arrays in the parameter list, so that
1
2
3
   do_something(int*)
   do_something(int[])
   do_something(int[some_number])
are all the same.

I just tried something out in Visual Studio. The following code compiled perfectly.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
void do_something1(int numbers[3])
{
	// etc
}

void do_something2(int numbers[])
{
	// etc
}

void do_something3(int* numbers)
{
	// etc
}


int main()
{
	int one[3];		// this array has size 3
	for (int i=0; i<3; i++)
		one[i] = 5;

	int* two = new int[5];	// this array has size 5
	for (int i=0; i<5; i++)
		two[i] = 6;

	do_something1(one);		// function expects size 3, gets size 3
	do_something1(two);		// function expects size 3, gets size 5

	do_something2(one);		// function expects pointer, gets size 3
	do_something2(two);		// function expects pointer, gets size 5

	do_something3(one);		// function expects pointer, gets size 3
	do_something3(two);		// function expects pointer, gets size 5

	return 0;
}

Last edited on
Make sure you set your compiler to the strictest level of warning and error checking.

Line 28 should have failed to compile, because do_something1() expects a specific type: an int[3].

Everything else works because lines 6 and 11 both declare an argument pointer, not an array. An array will "type promote" (or degenerate) into a pointer, as it does on lines 30 through 34.
I set the warning level to 4 and 'treat warnings as errors' to true and recompiled. (I added the cout lines because there was a warning about not using the parameters in the functions.)

This still compiled. The only higher level of warnings was 'enable all warnings' and using this just generated loads of complaints about unused inline functions in <iostream> Still nothing about type mismatches.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
#include <iostream>

void do_something1(int numbers[3])
{
	// etc
	std::cout << numbers[0];
}

void do_something2(int numbers[])
{
	// etc
	std::cout << numbers[0];
}

void do_something3(int* numbers)
{
	// etc
	std::cout << numbers[0];
}


int main()
{
	int one[3];		// this array has size 3
	for (int i=0; i<3; i++)
		one[i] = 5;

	int* two = new int[5];	// this array has size 5
	for (int i=0; i<5; i++)
		two[i] = 6;

	do_something1(one);		// function expects size 3, gets size 3
	do_something1(two);		// function expects size 3, gets size 5

	do_something2(one);		// function expects pointer, gets size 3
	do_something2(two);		// function expects pointer, gets size 5

	do_something3(one);		// function expects pointer, gets size 3
	do_something3(two);		// function expects pointer, gets size 5

	std::cin.get();

	return 0;
}


EDIT: I tried to compile code containing these two function definitions.
1
2
void fn(int*) {}
void fn(int[20]) {}

and got the compiler error
error C2084: function 'void fn(int *)' already has a body

Doesn't this suggest that the compiler sees the two function declarations
void fn(int*); and void fn(int[20]); as identical?
Last edited on
Topic archived. No new replies allowed.