Structs and unsigned chars

I'm currently trying to program a function that allows a user to read in an image and they can either flip the image horizontally or vertically, or convert the image to grayscale. I'm having trouble getting the grayscale function to work.

An error says no match for 'operand[]' (operand types are 'Image' and 'int').
Another error says no match for 'operator=' (operand types are 'Image" and 'unsigned char').

How can I get it so the code can run correctly?

P.S. There's no main, because that will be handled in a separate file.
Last edited on
well we can't help if you do not provide the offending code.
no match for [] means you tried to treat something like a vector/array/pointer/etc that isnt:
int x;
x[23] = 11; //error, what the heck does [] mean on an int? no such thing!

you also can't assign mismatched types that are not auto-converted (eg you can assign an int a char, because char is a type of int and the compiler knows this, but you can't assign a double the value from a string directly...)
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
45
46
void toGrayScale(Image image, Pixel pixel, int width, int height)
{
	Image newImage[width][height];
	for (int i = 0; i < width; i++){
		for (int j = 0; j < height; j++) {
			unsigned char color[] = image[width][height];
			color[0] = i % 256;
			unsigned char red = color[0];
			color[1] = j % 256;
			unsigned char green = color[1];
			color[2] = (i * j) % 256;
			unsigned char blue = color[2];
			unsigned char gray = round(0.299*red + 0.587*green + 0.114*blue);
			newImage[i][j] = gray;
		}
	}
}

struct Pixel
{
	int numRows;
	int numCols;
	char color[];
	int red;
	int green;
	int blue;
};

struct Image {
	int width;
	int height;
	int size;
	Pixel pixel;
};

 // loads a "P3" PPM  formatted image from a file
void loadImage();

 // saves an image to a text file as a "P3" PPM formatted image
void saveImage();

 // filters an image by converting it to grayscale
void toGrayscale(struct Image);

 // manipulates an image by flipping it either vertically or horizontally
void flipImage(struct Image, bool horizontal);
Image image <-- what is this?
Image newImage[width][height]; <--- this one has array dimensions, the other one does not?

unsigned char color[] = image[width][height]; <--- this is your problem, most likely.

Are you aware of the 2-D array parameter passing problem? You have to lock one of the dimensions.

but you can get around that if NONE OF THEM ARE REALLY ** and are all actually 2-D C arrays.

for 2d C arrays, some magic to blow your mind will be coming shortly. (or not. Its just exploiting how pointers work in C).

The point to all this is simply that arrays in C and C++ are solid blocks of memory, and you can slice that up any way you like. These silly examples may help you pass the data to your functions. However I highly recommend you move to vectors when you get a chance.

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
45

void foo(int * ip, int r, int c, int which)
{  
   for(int i = 0; i < r; i++)
    ip[i*c+which] = 1234; //the formula for accessing 2d from a collapsed 1d pointer is
// desired row * number of columns + desired column
}

int main()
{
  int d2[4][6];
  int * magic = &d2[0][0];  //some of these can be shortcutted in c++ but I want to be explict what it IS
  for(int i = 0; i < 4*6; i++) //fill in d2, but using 1d pointer to it!
    magic[i] = i; 

   //standard print loop for d2 ignoring magic 
  for(int i = 0; i < 4; i++)
  {
  for(int j = 0; j < 6; j++)
   cout << d2[i][j]<<'\t';
   cout << endl;
  }
  
  //ok not too exciting.. but check this one out. 
  for(int i = 0; i < 3; i++)
  {
  for(int j = 0; j < 8; j++) //3*8 == 4*6 .. I changed the dimensions!
   cout << magic[i*8+j]<<'\t';
   cout << endl;
  }
  
  
 //but we still didn't use magic.  OK, fine :) 
 //foo is going to set one of the columns to 1234. 
foo(magic, 4,6,3); //its a 4x6, change column 3 (from 0, 4th real column). 
    
 //standard print loop for d2
  for(int i = 0; i < 4; i++)
  {
  for(int j = 0; j < 6; j++)
   cout << d2[i][j]<<'\t';
   cout << endl;
  }	
	
}


1
2
3
4
5
6
7
8
9
10
11
12
13

C:\c>a
0       1       2       3       4       5
6       7       8       9       10      11
12      13      14      15      16      17
18      19      20      21      22      23
0       1       2       3       4       5       6       7
8       9       10      11      12      13      14      15
16      17      18      19      20      21      22      23
0       1       2       1234    4       5
6       7       8       1234    10      11
12      13      14      1234    16      17
18      19      20      1234    22      23


edit: and I messed it up first time... which is why vectors are so much better, its easy to screw up pointers.
Last edited on
Topic archived. No new replies allowed.