|
Prev: Lesson 4, Integer Assignments, Unsigned to Signed with Mixed Sizes (4 spectacular range detection failures)
Next: Update map Object
From: TheDevil on 12 Apr 2008 19:52 Hello, See comments. Or See web link: http://members.home.nl/hbthouppermans/VS2008Analysis/Index.htm // *** Begin of Main.cpp *** #include <stdio.h> typedef char int8; typedef short int int16; typedef int int32; typedef long long int64; typedef unsigned char uint8; typedef unsigned short uint16; typedef unsigned int uint32; typedef unsigned long long uint64; /* 13 april 2008 Back to School: Lesson 5, Arrays, Static, Dynamic, Multi Dimesional. Static 1D Array example Dynamic 1D Array example Static 2D Array example Dynamic 2D Array example (Easy allocation/free, Hard usage) Dynamic 2D Array example (Hard allocation/free, Easy usage) Dynamic 3D Array example (Hard allocation/free, Easy usage) Out of range indexes in static array have some detection in the form of stack corruption runtime error. Pretty crappy. Out of range indexes for dynamic array have no detection. Laughably lame. Also for dynamic arrays programmer has to choose between: 1. Easy allocation/free and difficult usage. or 2. Slightly difficult allocation/free and easy usage, probably with some small pointer access overhead. Choice 1 adds significant overhead for programmer trying to use/access the array, he has to type a lot. Choice 2 adds no overhead for programmer trying to use/access the array but does involve some boring allocation and freeing code. People suggesting templates for something as simple concept as arrays are out of their mind, to introduce such complexities. At least dynamic arrays are possible. I shall give it a subjective rating of 1 out of 10. Conclusion: Arrays in C/C++ insanely lame and can lead to hard to find bugs pretty easily. Preventing such bugs will require lots of overhead for the programmer who would have to write lots of bound checking code or use some crappy solution adding further complexities to his project. Possible adventage could be compiler remains easy and therefore many compilers for different systems/platforms. Advice: Use solution/choice 2. Platform test intel architecture 32. Score: 1 out of 10 */ int main() { printf("Program Started \n\n"); int8 vStaticArray[100]; // static array int8 *vDynamicArray; // dynamic array int8 vIndex; int8 vJndex; int8 vKndex; // one dimensional static array, will be allocated on the stack. (Think of it as temporarely limited memory) for (vIndex=0; vIndex <= 99; vIndex++) // 100 would lead to stack corrupted warning message. { vStaticArray[vIndex] = vIndex; printf("vStaticArray[%d]: %d \n", vIndex, vStaticArray[vIndex] ); } // one dimensional dynamic array, will be allocated on the heap. (Think of it as main huge memory) vDynamicArray = new int8[100]; for (vIndex=0; vIndex <= 99; vIndex++) // 100 would lead to BEEP, and nothing else. { vDynamicArray[vIndex] = -vIndex; printf("vDynamicArray[%d]: %d \n", vIndex, vDynamicArray[vIndex] ); } delete vDynamicArray; // two dimensional arrays, allocation simple, usage hard. int8 vStaticArray2D[5][20]; int8 *vDynamicArray2D; for (vIndex=0; vIndex<=4; vIndex++) // 5 would lead to stack corrupted message after program shutdown... not too usefull. { for (vJndex=0; vJndex<=19; vJndex++) { vStaticArray2D[vIndex][vJndex] = (vIndex*20) + vJndex; printf("vStaticArray2D[%d][%d]: %d \n", vIndex, vJndex, vStaticArray2D[vIndex][vJndex] ); } } vDynamicArray2D = new int8[5 * 20]; for (vIndex=0; vIndex<=4; vIndex++) { for (vJndex=0; vJndex<=19; vJndex++) { vDynamicArray2D[vIndex*20 + vJndex] = (vIndex*20) + vJndex; printf("vDynamicArray[%d][%d]: %d \n", vIndex, vJndex, vDynamicArray2D[vIndex*20 + vJndex] ); } } delete vDynamicArray2D; // two dimensional array, allocation hard, usage simple int8 **vDynamicArray2DV2; // allocation vDynamicArray2DV2 = new int8* [5]; for (vIndex=0; vIndex <= 4; vIndex++) { vDynamicArray2DV2[vIndex] = new int8[20]; } // access/usage for (vIndex=0; vIndex<=4; vIndex++) // no range checking, 5 would cause exception. { for (vJndex=0; vJndex<=19; vJndex++) { vDynamicArray2DV2[vIndex][vJndex] = (vIndex*20) + vJndex; printf("vDynamicArray2DV2[%d][%d]: %d \n", vIndex, vJndex, vDynamicArray2DV2[vIndex][vJndex] ); } } // free for (vIndex=0; vIndex <= 4; vIndex++) { delete vDynamicArray2DV2[vIndex]; } delete vDynamicArray2DV2; // one last example showing a dynamic 3D array, simply extend the previous code with an extra pointer and extra loop for extra dimension: int8 ***vDynamicArray3D; // array will be: 2*5*10 // allocation vDynamicArray3D = new int8** [2]; // first dimension for (vIndex=0; vIndex <= 1; vIndex++) { vDynamicArray3D[vIndex] = new int8* [5]; // second dimension for (vJndex=0; vJndex<=4; vJndex++) { vDynamicArray3D[vIndex][vJndex] = new int8[10]; // third dimension } } // access/usage for (vIndex=0; vIndex<=1; vIndex++) // no range checking, 5 would cause exception. { for (vJndex=0; vJndex<=4; vJndex++) { for (vKndex=0; vKndex<=9; vKndex++) { vDynamicArray3D[vIndex][vJndex][vKndex] = (vIndex*5*10) + (vJndex*10) + vKndex; printf("vDynamicArray3D[%d][%d][%d]: %d \n", vIndex, vJndex, vKndex, vDynamicArray3D[vIndex][vJndex][vKndex] ); } } } // free for (vIndex=0; vIndex <= 1; vIndex++) { for (vJndex=0; vJndex<=4; vJndex++) { delete vDynamicArray3D[vIndex][vJndex]; // third dimension } delete vDynamicArray3D[vIndex]; // second dimension } delete vDynamicArray3D; // first dimension printf("Program finished \n"); } // *** End of Main.cpp *** Bye, The Devil.
From: Alf P. Steinbach on 12 Apr 2008 20:34 * TheDevil: > > [raw] Arrays in C/C++ ... can lead to hard to find bugs pretty easily. Yes, that's right. As a novice, preferentially use std::vector, and use 'at(i)' rather than '[i]'. When you gain more experience, look at the array classes in Boost and TR1. Cheers, & hth., - Alf
From: Hal Vaughan on 14 Apr 2008 11:36 Alf P. Steinbach wrote: > * TheDevil: >> >> [raw] Arrays in C/C++ ... can lead to hard to find bugs pretty easily. > > Yes, that's right. > > As a novice, preferentially use std::vector, and use 'at(i)' rather than > '[i]'. Why use at(i) over [i]? Hal
From: Alf P. Steinbach on 14 Apr 2008 12:16
* Hal Vaughan: > Alf P. Steinbach wrote: > >> * TheDevil: >>> [raw] Arrays in C/C++ ... can lead to hard to find bugs pretty easily. >> Yes, that's right. >> >> As a novice, preferentially use std::vector, and use 'at(i)' rather than >> '[i]'. > > Why use at(i) over [i]? Because it reacts to indexing errors by throwing an exception, instead of silently producing an incorrect result or trashing some memory area. In other words, it provides guaranteed bounds-checking. So it's much easier to detect those nefarious bugs. Cheers, & hth., - Alf |