440 likes | 540 Views
Chapter 15 - Arrays and Pointers. Lab 8 – Etch-a-Sketch. An analog-to-digital converter converts continuous analog signals to discrete digital numbers. Jitter is the physical phenomenon that results from "noise" associated with a analog signal.
E N D
Lab 8 – Etch-a-Sketch • An analog-to-digital converter converts continuous analog signals to discrete digital numbers. • Jitter is the physical phenomenon that results from "noise" associated with a analog signal. • manifests itself by the return values "dancing around“ • Eliminate noise and smooth out input data using • A lowpass filter... • Oversampling... • Thresholds... Arrays and Pointers
Lab 8 – Etch-a-Sketch • Digital equivalent of an analog low pass RC filter unsigned int lowpass_filter(unsigned int input, unsigned int* delay) { // Update filter with current sample. *delay = *delay - (*delay >> FILTER_SHIFT) + input; // Scale output for unity gain. return *delay >> FILTER_SHIFT; } Arrays and Pointers
Lab 8 – Etch-a-Sketch • Digital equivalent of an analog low pass RC filter delay_element += Input – (delay_element >> 4)) Arrays and Pointers
Lab 8 – Etch-a-Sketch #define FILTER_SHIFT 3 // Parameter K // initial lowpass filter delay values oldx = ADC_read(LEFT_POT); oldy = ADC_read(RIGHT_POT); pot1_delay = (oldx << FILTER_SHIFT) + (oldx >> FILTER_SHIFT);; pot2_delay = (oldy << FILTER_SHIFT) + (oldy >> FILTER_SHIFT);; while(1) { // pass through low-pass filter x = lowpass_filter(ADC_read(LEFT_POT), &pot1_delay); y = lowpass_filter(ADC_read(RIGHT_POT), &pot2_delay); } unsigned int lowpass_filter(unsigned int input, unsigned int* delay) { // Update filter with current sample. *delay += input - (*delay >> FILTER_SHIFT); // Scale output for unity gain. return (*delay >> FILTER_SHIFT); } Arrays and Pointers
Concepts to Learn… • Arrays • C Strings • Array Arguments • Pointers • Pointer Arithmetic • Swap Example w/Pointers • Null Pointers • Arrays and Pointers • Pointers to Pointers • Multi-dimensional Arrays • Command-line Arguments • Function Pointers Arrays and Pointers
Arrays Arrays • Allocate a sequence of memory locations. • For example - table of numbers • Problems • What if there are 1000 numbers? • Write a loop to process each number? • Use an array • Declare a sequence of four integers. • int num[4]; • num[0], num[1], num[2], num[3]. • An array is a sequence of like items. int num0;int num1;int num2;int num3; Arrays and Pointers
Arrays Array Syntax • Like any other variable, arrays must be declared before they are used. • General form: type variable-name[number_of_elements]; • The array size must be explicit at compile time – needed to reserve memory space • Array elements individually accessed. • General form: variable-name[index]; • Zero based subscripts • No compile-time or run-time limit checking Arrays and Pointers
Arrays Initialization of Arrays • Elements can be initialized in the same way as the ordinary variables when they are declared. • type array_name[size]={ list of values }; int number[3] = {0, 0, 0}; • Remaining uninitialized elements will be set to zero automatically. • Array declarations may omit the size. int counter[] = {1, 1, 1, 1}; • Problems with C initialization of arrays • No convenient way to initialize selected elements. • No shortcut to initialize large number of elements. Arrays and Pointers
Arrays Local Array Example SP int main() { int array[10]; int x; x = array[3] + 1; array[6] = 5; return 0; } main: 0x87a2: 8031 0016 SUB.W #0x0016,SP 0x87a6: 431F MOV.W #1,R15 0x87a8: 511F 0006 ADD.W 0x0006(SP),R15 0x87ac: 4F81 0014 MOV.W R15,0x0014(SP) 0x87b0: 40B1 0005 000C MOV.W #0x0005,0x000c(SP) 0x87b6: 430C CLR.W R12 0x87b8: 5031 0016 ADD.W #0x0016,SP 0x87bc: 4130 RET Arrays and Pointers
Arrays Local Array Example SP int main() { int array[10]; int x; for (x = 0; x < 10; x++) { array[x] = x; } return 0; } main: 0x8040: 8031 0016 SUB.W #0x0016,SP 0x8044: 4381 0014 CLR.W 0x0014(SP) 0x8048: 90B1 000A 0014 CMP.W #0x000a,0x0014(SP) 0x804e: 340D JGE (C$DW$L$main$2$E) C$DW$L$main$2$B, C$L1: 0x8050: 411F 0014 MOV.W 0x0014(SP),R15 0x8054: 5F0F RLA.W R15 0x8056: 510F ADD.W SP,R15 0x8058: 419F 0014 0000 MOV.W 0x0014(SP),0x0000(R15) 0x805e: 5391 0014 INC.W 0x0014(SP) 0x8062: 90B1 000A 0014 CMP.W #0x000a,0x0014(SP) 0x8068: 3BF3 JL (C$L1) C$L2, C$DW$L$main$2$E: 0x806a: 430C CLR.W R12 0x806c: 5031 0016 ADD.W #0x0016,SP 0x8070: 4130 RET Arrays and Pointers
Arrays Global Array Example int array[10]; int x; int main() { for (x = 0; x < 10; x++) { array[x] = x; } return 0; } main: 0x806a: 4382 0214 CLR.W &x 0x806e: 90B2 000A 0214 CMP.W #0x000a,&x 0x8074: 340C JGE (C$DW$L$main$2$E) C$DW$L$main$2$B, C$L1: 0x8076: 421F 0214 MOV.W &x,R15 0x807a: 5F0F RLA.W R15 0x807c: 429F 0214 0200 MOV.W &x,0x0200(R15) 0x8082: 5392 0214 INC.W &x 0x8086: 90B2 000A 0214 CMP.W #0x000a,&x 0x808c: 3BF4 JL (C$L1) C$L2, C$DW$L$main$2$E: 0x808e: 430C CLR.W R12 0x8090: 4130 RET Arrays and Pointers
Arrays Array Example SP int array[10]; int x; grid[x+1] = grid[x] + 2; 0x86aa: 411F 0014 MOV.W 0x0014(SP),R15 0x86ae: 5F0F RLA.W R15 0x86b0: 510F ADD.W SP,R15 0x86b2: 432E MOV.W #2,R14 0x86b4: 5F2E ADD.W @R15,R14 0x86b6: 411F 0014 MOV.W 0x0014(SP),R15 0x86ba: 5F0F RLA.W R15 0x86bc: 532F INCD.W R15 0x86be: 510F ADD.W SP,R15 0x86c0: 4E8F 0000 MOV.W R14,0x0000(R15) Arrays and Pointers
C Strings C Strings • A C string is an array of characters: • char outputString[16]; • C strings are terminated with a zero byte. • C strings can be initialized when defined: • char outputString[] = "Text"; which is the same as: outputString[0] = 'T'; outputString[1] = 'e'; outputString[2] = 'x'; outputString[3] = 't'; outputString[4] = 0; • C has no string operators. • String functions in <string.h> library Compiler computes the size of the array (4 + 1 = 5 bytes) Arrays and Pointers
C Strings Strings are Arrays int main() { char string[] = "\nhello!"; printf("%s", string); } 0x61/0x0a SP 0x6c/0x65 0x6f/0x6c 0x00/0x21 Arrays and Pointers
Array Arguments Passing Arrays as Arguments • C passes parameters to functions by value. • C passes the address of the 1st element by value. #define MAX_NUMS 5 int average(int values[]) { int i, sum = 0; for (i = 0; i < MAX_NUMS; i++) sum = sum + values[i]; return (sum / MAX_NUMS); } int main() { int nums[MAX_NUMS] = { 1, 2, 3, 4, 5 }; int mean = average(nums); return 0; } 0x05f2 SP 5 15 1 SP 2 3 4 5 3 Arrays and Pointers
Pointers Pointers • A pointer is a variable that contains an address. • With pointers • functions can indirectly access variables. • functions can modify the arguments passed by the caller function. • sophisticated data structures can grow and shrink at run-time. • Arrays and pointers are closely related. • Array pointers enable us to conveniently process groups of data such as vectors, lists, and strings. Arrays and Pointers
Pointers Swap Function Example int main() { int a = 3; int b = 4; swap(a, b); } void swap(int a, int b) { int temp = a; a = b; b = temp; } Stack after call to swap(): 4 a 3 b swap temp 3 Return Adr main Arrays and Pointers
Pointers Pointer Variables • Pointer variables contain memory addresses. • Associated with a pointer variable is the type of value to which it points. • The asterisk (*) indicates that the following identifier is a pointer variable. • The ampersand (&) returns a pointer (address) to the following identifier. Pointer examples: int* ptr; char* cp; double* dp; int** p_ptr = &ptr; char *strings[10]; Arrays and Pointers
Pointers Syntax for Pointer Operators • A pointer variable is declared with the asterisk operator (*) type *var; // same - whitespace doesn’t matter type* var; • Dereferencing any expression returns a value *var returns contents of the memory location pointed to by var **var returns contents of the memory location pointed to by the memory location pointed to by var *3 returns the contents of memory location 3 • A pointer is created with the reference operator (&) &var • Reference must be applied to a memory object • &3 is illegal as it would return a pointer to a constant Arrays and Pointers
0x05fa 0x05fc Pointers Pointers int *ptr1; int *ptr2; int i = 4; int j; ptr1 = &i; ptr2 = &j; // What will these print? printf("\n%04x", ptr1); printf("\n%04x", ptr2); printf("\n%04x", *ptr1); printf("\n%04x", *ptr2); j = *ptr1; printf("\n%04x", j); 4 4 0x05fa 0x05fc 0x0004 ?????? 0x0004 Arrays and Pointers
* =dereference & = reference Pointers Operator Precedence and Associativity Arrays and Pointers
Pointer Arithmetic Pointer Arithmetic • Address calculations depend on size of elements • ints are 16-bits or 2 bytes per element. • e.g., to find 4th element, we add 4*2 to base address • If double, we'd have to add 16 (4*4) to find address of 4th element. • C does size calculations under the covers,depending on size of item being pointed to: double x[10]; double *y = x; *(y + 3) = 13; Allocates 40 bytes (4 per element) Same as x[3] (base address plus 12) Arrays and Pointers
Pointer Arithmetic Incrementing Pointers • A pointer increments according to its type. • The unary operators * and & bind more tightly than arithmetic operators. int y = 0; int a[5] = {1, 5, 9, 13, 17}; int* ip = &a[0]; y = *ip + 1; *ip += 1; y = ++*ip; y = *ip++; y = (*ip)++; 1 5 9 // y=0, ip=0x05f2 // y = a[0]+1 y=2, ip=0x05f2 // a[0] = a[0]+1 y=2, ip=0x05f2 // a[0] = a[0]+1 y=3, ip=0x05f2 // ip = ip+1 y=3, ip=0x05f4 // a[1] = a[1]+1 y=5, ip=0x05f4 13 17 0x05f2 Arrays and Pointers
Pointer Arithmetic *ip++ • Form used by “experienced” C programmers // strcpy: copy s to d; version 1 void strcpy(char* d, char* s) { while ((*d = *s) != ‘\0’) { d++; s++; } } // strcpy: copy s to d; version 2 void strcpy(char* d, char* s) { while ((*d++ = *s++) != ‘\0’); } • The value of *s++ is the character that s pointed to before s was incremented; the postfix ++ does not change s until after this character has been fetched. Arrays and Pointers
Pointer Arithmetic Incrementing Pointers int main() { char *cptr; double *fptr; char buffer[10]; double array[10]; cptr = buffer; // cptr = &buffer[0]; fptr = array; // fptr = &array[0]; printf("\n0x%04d, 0x%04d", cptr++, fptr++); printf("\n0x%04d, 0x%04d", cptr, fptr); return 0; } 0x05cc, 0x05d6 0x05cd, 0x05da Arrays and Pointers
3 4 Swap Example w/Pointers Swap Example Fixed! • Stack after call to swap() int main() { int a = 3; int b = 4; swap(&a, &b); } void swap(int* a, int* b) { int temp = *a; *a = *b; *b = temp; } 0x05fa a 0x05fc b swap temp 3 Return Adr main Arrays and Pointers
Null Pointers Null Pointers • Sometimes we want a pointer that points to nothing. • Used for invalid pointer error returns • Used to catch errors • NULLis a predefined macro that contains a value that non-null pointer should never hold, usually NULL=0. int *p; p = NULL; /* p is a null pointer */ Arrays and Pointers
Arrays and Pointers Arrays and Pointers • An array name is essentially a pointer to the first element in an array. • Can change the value (contents) of a pointer. char word[10]; char *cptr; cptr = word; // points to word[0] Arrays and Pointers
Arrays and Pointers Arrays and Pointers • Given the previous declarations, each of the following lines are equal. char word[10]; char *cptr; cptr = word; // points to word[0] cptr word &word[0] address of word[0] (cptr + n) word + n &word[n] address of word[n] *cptr *word word[0] value of word[0] *(cptr + n) *(word + n) word[n] value of word[n] Arrays and Pointers
Arrays and Pointers Array Pointer Arithmetic • Address calculations depend on size of elements • char x[4] – add 4 to base address • int x[4] – add 8 (2*4) to base address • long x[4] – add 16 (4*4) to base address • C does size calculations behind the scenes, depending on type of pointer (size of item being pointed to) long x[10]; // allocates 40 bytes long *y = x; *(y + 3) = 13; // same as x[3] = 13 Arrays and Pointers
Arrays and Pointers Common Pitfalls with Arrays • Overrun array limits. • There is no boundary checking in C. int array[10], i; for (i = 0; i <= 10; i++) // oops array[i] = 0; • Arrays must be statically declared • Compiler flags run-time declarations void SomeFunction(int num_elements) { int temp[num_elements]; // error … } Arrays and Pointers
Arrays and Pointers Initialization of Pointer Arrays • Pointer arrays can be initialized as follows: /* month_name: return name of n-th month */ char* month_name(int n) { static char* name[ ] = { "Illegal month", "January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December" }; return ( n < 1 || n > 12 ) ? name[0] : name[n]; } Arrays and Pointers
linesptr[0] defghi linesptr[1] lmnopqrstuvwxyz linesptr[2] abc … Pointers to Pointers Pointers to Pointers • Since pointers are variables themselves, they can be stored in arrays just as other variables can. Example: char* linesptr[8]; Arrays and Pointers
linesptr[0] linesptr[1] linesptr[2] … Pointers to Pointers Pointers to Pointers • Since pointers are variables themselves, they can be stored in arrays just as other variables can. Example: char* linesptr[8]; defghi lmnopqrstuvwxyz abc Arrays and Pointers
Multi-dimensional Arrays Multi-dimensional Arrays • Multi-dimensional arrays declared with multiple indexes • daytab[i][j] /* [row][col] */ • daytab[i,j] /* WRONG! */ • Array elements are stored by rows • The rightmost subscript varies the fastest • Array name “points” to 1st element • Multi-dimensional arrays passed to a function must declare the number of elements for every subscript except the first • func(int daytab[ ][13]) {…} Arrays and Pointers
Command-line Arguments Command-line Arguments • When main is called, it is passed two arguments. • The first (conventionally called argc, for argument count) is the number of command-line arguments the program was invoked with. • The second (argv, for argument vector) is a pointer to an array of character pointers (strings) that contain the arguments, one per string. • By conventions, argv[0] points to the name by which the program was invoked. • By standards, argv[argc] is a null pointer. Arrays and Pointers
argv: echo\0 hello\0 world\0 Command-line Arguments Command-line Arguments • By standards, argv[argc] is a null pointer. /* echo command-line arguments int main(int argc, char* argv[ ]) { while (--argc > 0) printf("%s%s", *++argv, (argc > 1) ? " " : ""); printf("\n"); return 0; } Arrays and Pointers
Function Pointers Function Pointers • In C, a function is not a variable, but it is possible to define pointers to functions which can be: • assigned, • placed in arrays, • passed to functions, • returned by functions, and so on. int function1(int a, char* s) { … } int function2(int a, char* s) { … } int (*f[2])(int, char*); f[0] = function1; f[1] = function2; (*f[n])(10, "hello"); Arrays and Pointers
Function Pointers Complicated Declarations • C is sometimes castigated for the syntax of declarations, particularly ones that involve pointers to functions: int *f(); // f: function returning pointer to int int (*pf)(); // pf: pointer to function returning int • What do these do? char **argvargv: pointer to pointer to char int (*daytab)[13]daytab: pointer to array[13] of int int *daytab[13]daytab: array[13] of pointer to int char (*(*x())[])()x: function returning pointer to array[ ] of pointers to function returning char char (*(*x[3])())[5]x: array[3] of pointer to function returning pointer to array[5] of char Arrays and Pointers