Arrays?
In C and C++, they are 0-based, meaning the first element is 0, and the last is n-1.
There is no such thing as "the last element could be anywhere".
However, especially in C, where the compiler doesn't care if you treat an int as a pointer and then a char(though for the char it will probably convert it automatically), you can give a negative array index, or one greater than the array bounds. The issue is that the computer didn't give all it's RAM to storing your array. There are other numbers in there as well.
Great example: I had an ASCII pong-like thing(a bouncing highlight as an example test), but it would go one over on the right side. This was not a real problem unless it hit the lower right corner.
If it did, it would overflow the array and write the background colour of a nonexistant tile to be something.
This would not be much of a problem, except that that particular memory location was used for something else: The "ball"'s X velocity.
If it was something else, for example, a pointer stored there, it could severely mess up the data, and when the program next tries to access the pointer's target, it would likely edit a random bit of the memory. This is more than likely to cause a segfault if it had a pointer of it's own and it was "relocated" to uninitialized memory, or if the change caused the program to try to write over the portion of memory where itself was stored.
In some of the worst cases, a corrupt pointer corrupts another pointer that corrupts another pointer and so on until one causes a segfault.
Just remember:
For strings, they terminate with an invisible character 0 so a 8 char string needs 9 bytes of storage, but otherwise 8 chars of binary data only needs 8 chars of array. The diffrence is that it is stored in array[0] to array[7] instead of [1] to [8].
Naturally, not all programming languages use 0-based arrays, but those that don't are generally in the category of BASIC and some script languages.
A structure is just a bunch of variables grouped in a single memory location so you can pass a pointer to the first and get access to them all(AFAYNTN(As Far As You Need To Know), just pass a pointer to a struct, or even a whole struct, and everything stays together), but more importantly, structs can be allocated/created all at once and are kept together automatically, and you can have a single array of structs rather than an array of values for each value that would be in the struct.
I'm not a teacher, so if you didn't learn anything, it's the way I explained it.