Tutorial on the basics of using the "buffer" instruction?

Zoandar:
Why is the value of { 0 } surrounded by braces?

It creates a list of initializers...

int some_primes[5] = { 2, 3, 5, 7, 11 };

If the list is too short (not enough values), the compiler uses zeros for the remaining values.

He is setting it to zero here

He is and it is not necessary. Global / static data is automatically initialized to zero. But, there is no harm either.

Things like that are usually done to indicate an assumption made by the coder. In other words, when he wrote the "buffer_pos" code he assumed that all the elements would be initialized to zero. If they are not initialized to zero, the code will not work correctly. It's sort-of like a comment.

buffer_pos is the pointer variable for the [NUM_AXES] buffer he made, right?

buffer_pos is not a pointer type, it is a simple "int" array.

Thanks, both of you. I was mistaken in my recollection of what I had read in the book. What he actually says is "we define an array of buffer positions" in regard to that line. I presume "initializers" means "buffer positions" in the post from Coding Badly?

But I am still unclear on the braces. How is this different than just using

int buffer_pos[NUM_AXES] = 0 ;

I would like to be able to remember what the braces "mean" here. Since I was unable to find " = { 0 }" anywhere else in lengthy Google searches of Arduino and C websites, I get the feeling this may be an "uncommon" use of this syntax.

buffer positions

buffer positions is not the same as buffer pointers.

For "position", read "index".

Zoandar:
But I am still unclear on the braces. How is this different than just using

int buffer_pos[NUM_AXES] = 0 ;

...does not compile. For a simple data-type (like an "int") only one value is needed to initialize it because it can only store one value...

int iNeedOneValue = 13;

For an array data-type (like an array of "int") more than one value is needed to initialize it because it can store multiple values. The braces are used to define the list of values used to initialize the array...

int iNeedFive[5] = { 97, 1678, 6, 169, 769 };

iNeedFive[0] is initialized to 97; iNeedFive[1] is initialized to 1678; etcetera.

I would like to be able to remember what the braces "mean" here.

You are telling the compiler, here's a list a values I want you to use to initialize my array.

Since I was unable to find " = { 0 }" anywhere else in lengthy Google searches of Arduino and C websites, I get the feeling this may be an "uncommon" use of this syntax

I suspect " = { 0 }" is rather uncommon for global / static data. It is somewhat common for local / automatic arrays.

Since I was unable to find " = { 0 }" anywhere else in lengthy Google searches of Arduino and C websites, I get the feeling this may be an "uncommon" use of this syntax

It would be reasonably common. You need to search in the context of initializing arrays. Otherwise you find a lot of stuff about soccer scores.

Whilst Coding Badly is correct that static variables are automatically set to zero, automatic variables aren't*. So this could be a reasonable way of initializing an array in a function:

void foo ()
{
int buffer_pos[NUM_AXES] = { 0 };  // start with all zero

// blah blah
}

*Edit: He didn't imply they were.

Again thank you all for the information. But I think the "magic bullet" may have just come from a single word in your post, when you just said " // start with all zero".

For whatever reasons this was not clear to me before, what he is doing with this rather cryptic instruction is setting ALL THREE of the array elements to ZERO in ONE STATEMENT. Correct?

If I am right, then, knowing that he had defined the constant NUM_AXES equal to 3, in this sketch interchanging these statements would both have the exact same effect:

int buffer_pos[NUM_AXES] = { 0 };  // start with all zero

int buffer_pos[NUM_AXES] = { 0, 0, 0 };  // start with all zero

I eagerly await confirmation. :slight_smile: (While I look at that link for array initialization - thank you!)

YES!!! Your link just verified the above. I wish the book's author had mentioned this, because it looks to be a VERY handy function. However, it also seems that he could just as simply used

int buffer_pos[NUM_AXES] ;  // start with all zero

OR

int buffer_pos[NUM_AXES] = {};  // start with all zero

Thanks!!! :grin:

... this rather cryptic instruction is setting ALL THREE of the array elements to ZERO in ONE STATEMENT. Correct?

Yes, setting the entire array to zero. More specifically, everything beyond the stated initializers. So to be pedantic, you requested the first position to be initialized to zero, and the compiler initialized the rest to zero for you, as you have stated that the array is to be initialized in the first place (by using "= ...").

Zoandar:
However, it also seems that he could just as simply used

int buffer_pos[NUM_AXES] ;  // start with all zero

OR

int buffer_pos[NUM_AXES] = {};  // start with all zero

Your first example won't work with "auto" variables. That is, if they are defined inside a function. So it is dangerous to do that, because you might copy and paste them (from a statically defined place to inside a function). Also it relies upon you remembering that static variables are automatically initialized.

Your second example works but personally I think it is a bit cryptic.

I prefer:

int buffer_pos[NUM_AXES] = { 0 };  // start with all zero

Your second example works but personally I think it is a bit cryptic.

I prefer:

int buffer_pos[NUM_AXES] = { 0 };  // start with all zero

The important thing to keep in mind here is still that the number of explicitly valued positions in the array is limited to the number of explicit initializers provided. The rest of the positions in the array may or may not be valued with 0.

Prove this to yourself by changing where this statement is positioned (global, in a function, with and without the static keyword, etc.) and change the initial value to something other than 0, like 37. Then, use a for loop to print the index and value for each position in the array.

When the number of explicit initializers is less than the size of the array, the array values will NOT all be whatever (single) initializer is provided.

Having read this reply and that of PaulS, I agree your preference leaves the best 'bread crumbs', which I usually find to my liking. :slight_smile:

Thanks!

PaulS:

Your second example works but personally I think it is a bit cryptic.

I prefer:

int buffer_pos[NUM_AXES] = { 0 };  // start with all zero

The important thing to keep in mind here is still that the number of explicitly valued positions in the array is limited to the number of explicit initializers provided. The rest of the positions in the array may or may not be valued with 0.

Prove this to yourself by changing where this statement is positioned (global, in a function, with and without the static keyword, etc.) and change the initial value to something other than 0, like 37. Then, use a for loop to print the index and value for each position in the array.

When the number of explicit initializers is less than the size of the array, the array values will NOT all be whatever (single) initializer is provided.

Being a beginner, I find that when one relies on something happening 'automatically' and, worse, with little or no understanding of the same, it opens the door to the possibility of long and frustrating sessions trying to figure out why some end result isn't happening. Black box technology is, for me, a frustrating thing which is never fully trusted or understood. This happens to be the actual motivation I had toward Arduino. The first description of it I read spelled it out as a better alternative to a beginner approach in the world of electronics, as opposed to attemtping to learn enough about the world of discrete component interaction to be able to design and build in a hobby environment. Having traveled both paths, I find this to be quite true, although the programming involved 'can' be just as steep a learning curve, depending mostly upon the teacher being pursued. :slight_smile:

That said, I wanted to learn enough about this particular issue so that I can instantly recognize the next time I see it. And knowing what I do now, thanks to you good folks, I see his use of { 0 } as likely the best choice considering the other options just discussed. I did read in that array initialization article about the cautions you presented. Given that this sketch has only a 3 element array in this scope, might it not have been better overall to just use { 0, 0, 0 }, which I would instantly have understood?

Still, learning about using the line he did was a worthwhile lesson.

Thanks!

Given that this sketch has only a 3 element array in this scope, might it not have been better overall to just use { 0, 0, 0 }, which I would instantly have understood?

Yes. Explicitly providing the wrong number of initializers is not a good practice.

Thanks very much for helping clarify this. 24 hours ago I had no clue what that line of code meant. Now I understand it well. I was thinking this morning that back in the 70s before we had the internet, when I first took an interest in computers, and back in the 60s, when I first took an interest in electronics, there was no one to turn to for help when something did not work, was misunderstood, or worse, when a book or manual was incorrect. The internet and these forums are such invaluable tools today! I would hate to go back to the time before we had them!

But even so, they are only paths of information. Without the people using them who care to share their knowledge freely, and care enough to make sure the person they are helping understands the information provided, they are just "paths". So it is the people behind them who really make this a better world when it comes to learning things on one's own. I thank you, and all other such people here, who take time from their day to provide this knowledge and help!

Have a great day!

PaulS:

int buffer_pos[NUM_AXES] = { 0 };  // start with all zero

The important thing to keep in mind here is still that the number of explicitly valued positions in the array is limited to the number of explicit initializers provided. The rest of the positions in the array may or may not be valued with 0.

I can't agree with you here Paul. The rest of the positions in the array are valued with zero. Check out this page:

You can also see that from this sketch:

void setup ()
{
Serial.begin (115200);
int foo [10] = { 0 };

for (int i = 0; i < 10; i++)
  Serial.println (foo [i]);
}

void loop () {}

Not only does it print 10 lots of zero, but a dissassembly shows it is moving in 20 bytes of zero to the array (not 2 bytes):

int foo [10] = { 0 };
  ec:	fe 01       	movw	r30, r28
  ee:	31 96       	adiw	r30, 0x01	; 1
  f0:	84 e1       	ldi	r24, 0x14	; 20
  f2:	df 01       	movw	r26, r30
  f4:	1d 92       	st	X+, r1
  f6:	8a 95       	dec	r24
  f8:	e9 f7       	brne	.-6      	; 0xf4 <setup+0x34>

PaulS:
When the number of explicit initializers is less than the size of the array, the array values will NOT all be whatever (single) initializer is provided.

That's correct. They will be valued with zero. And of course if the (single) initializer is zero, then they happen to be valued with it as well. But it doesn't copy that initializer into the other places.

So you are saying that if you used

 int foo [10] = { 1 };

instead, you would get the first element set to 1, and the other 9 elements set to zero as a default action of the Arduino IDE compiler?

Yes I am, and perhaps I should have clarified that. It doesn't take the value you give and "ripple" it along. The non-specified elements, if any, are set to zero.

I think this is the point Paul was making when he said "the array values will NOT all be whatever (single) initializer is provided".

However in the case of the initializer being zero, then the others happen to be zero too. This may or may not be confusing. So if the (single) initializer is zero, then the others are indeed zero, but that is not because the single provided value was zero.

So if you have an array of 1000 elements, personally I wouldn't want to do this:

int buffer_pos[1000] = { 0, 0, 0, 0, 0, 0, 0,  ... (a lot more here) ...   0, 0, 0, 0, 0 };

Indeed, it wouldn't be obvious you had all 1000 rather than 999 of them.

So I suppose you could do this:

int buffer_pos[NUM_AXES] = {  };

But visually to me, that looks like you are initializing it to "nothing".

So as I said, I prefer:

int buffer_pos[NUM_AXES] = { 0 };  // initialize all elements to zero

But I admit there is an implication that if you change the 0 to 1, they will all be initialized to 1.

But what can you do? Short of lengthy comments, you have to hope that the person reading it understands the way C works.

I guess so. Thanks for detailing this. Hopefully I'll recognize the possibilities next time I see a similar statement.

I see you are in Melbourne. Would you happen to be familiar with the Melbourne - based FSWidgets.com? They make software add-ons for flight simulators. One of the developers, Fermin Fernandez, has traded many emails with me helping me to set up a couple of their moving map display programs for FSX here on my PCs.

You should probably personal-mail me or people will complain. But briefly, no I am not familiar with them. There are a lot of good software developers in Australia. Quite a few good games developers too. :slight_smile:

When you have kangaroos hopping around in your front garden, what else is there to do but develop software? And work with electronics?

Just joking, Melbourne is just like any other big city. Actually it is pretty nice. Fantastic range of cuisines, you can eat practically any nationality food here, and they are nice and cheap. My biggest complaint about living in Australia is the exorbitant shipping charges you often pay for importing stuff. Like, you need a $10 set of parts? How about adding on $40 in shipping? Ah, now they aren't so cheap.

And then I was looking at a $200 LCR meter. Sounded pretty good. Until they quoted another $200 to ship it here. $200 for shipping? Did they employ armed guards? It's ridiculous.

OK, I'll reply to our off-topic discussion through other means. :slight_smile: Thanks for the reminder. :slight_smile: