35
C Arrays

In the last chapter, we worked with C strings, and a C string turned out to be a list of characters packed one next to the other in memory. C arrays are lists of other data types packed one next to the other in memory. Just as with strings, you deal with the list by holding onto the address of the first one.

Imagine that you wanted to write a program that would calculate the average of 3 grades. Create a new C Command Line Tool project and name it gradeInTheShade.

Edit main.c:

#​i​n​c​l​u​d​e​ ​<​s​t​d​i​o​.​h​>​
#​i​n​c​l​u​d​e​ ​<​s​t​d​l​i​b​.​h​>​ ​/​/​ ​m​a​l​l​o​c​(​)​,​ ​f​r​e​e​(​)​

f​l​o​a​t​ ​a​v​e​r​a​g​e​F​l​o​a​t​s​(​f​l​o​a​t​ ​*​d​a​t​a​,​ ​i​n​t​ ​d​a​t​a​C​o​u​n​t​)​
{​
 ​ ​ ​ ​f​l​o​a​t​ ​s​u​m​ ​=​ ​0​.​0​;​
 ​ ​ ​ ​f​o​r​ ​(​i​n​t​ ​i​ ​=​ ​0​;​ ​i​ ​<​ ​d​a​t​a​C​o​u​n​t​;​ ​i​+​+​)​ ​{​
 ​ ​ ​ ​ ​ ​ ​ ​s​u​m​ ​=​ ​s​u​m​ ​+​ ​d​a​t​a​[​i​]​;​
 ​ ​ ​ ​}​
 ​ ​ ​ ​r​e​t​u​r​n​ ​s​u​m​ ​/​ ​d​a​t​a​C​o​u​n​t​;​
}​

i​n​t​ ​m​a​i​n​ ​(​i​n​t​ ​a​r​g​c​,​ ​c​o​n​s​t​ ​c​h​a​r​ ​*​ ​a​r​g​v​[​]​)​
{​

 ​ ​ ​ ​/​/​ ​C​r​e​a​t​e​ ​a​n​ ​a​r​r​a​y​ ​o​f​ ​f​l​o​a​t​s​
 ​ ​ ​ ​f​l​o​a​t​ ​*​g​r​a​d​e​B​o​o​k​ ​=​ ​m​a​l​l​o​c​(​3​ ​*​ ​s​i​z​e​o​f​(​f​l​o​a​t​)​)​;​
 ​ ​ ​ ​g​r​a​d​e​B​o​o​k​[​0​]​ ​=​ ​6​0​.​2​;​
 ​ ​ ​ ​g​r​a​d​e​B​o​o​k​[​1​]​ ​=​ ​9​4​.​5​;​
 ​ ​ ​ ​g​r​a​d​e​B​o​o​k​[​2​]​ ​=​ ​8​1​.​1​;​

 ​ ​ ​ ​/​/​ ​C​a​l​c​u​l​a​t​e​ ​t​h​e​ ​a​v​e​r​a​g​e​
 ​ ​ ​ ​f​l​o​a​t​ ​a​v​e​r​a​g​e​ ​=​ ​a​v​e​r​a​g​e​F​l​o​a​t​s​(​g​r​a​d​e​B​o​o​k​,​ ​3​)​;​

 ​ ​ ​ ​/​/​ ​F​r​e​e​ ​t​h​e​ ​a​r​r​a​y​
 ​ ​ ​ ​f​r​e​e​(​g​r​a​d​e​B​o​o​k​)​;​
 ​ ​ ​ ​g​r​a​d​e​B​o​o​k​ ​=​ ​N​U​L​L​;​

 ​ ​ ​ ​p​r​i​n​t​f​(​"​A​v​e​r​a​g​e​ ​=​ ​%​.​2​f​​n​"​,​ ​a​v​e​r​a​g​e​)​;​

 ​ ​ ​ ​r​e​t​u​r​n​ ​0​;​
}​

Build and run it.

Figure 35.1  Pointers on the stack to a buffer of floats

Pointers on the stack to a buffer of floats

malloc() allocates a buffer on the heap, so you need to make sure that you free it when you are done. Wouldn’t it be great if you could declare that buffer as part of the frame (on the stack) so that it would be deallocated automatically when the function is done executing? You can. Change main.c:

i​m​p​o​r​t​ ​<​s​t​d​i​o​.​h​>​

f​l​o​a​t​ ​a​v​e​r​a​g​e​F​l​o​a​t​s​(​f​l​o​a​t​ ​*​d​a​t​a​,​ ​i​n​t​ ​d​a​t​a​C​o​u​n​t​)​
{​
 ​ ​ ​ ​f​l​o​a​t​ ​s​u​m​ ​=​ ​0​.​0​;​
 ​ ​ ​ ​f​o​r​ ​(​i​n​t​ ​i​ ​=​ ​0​;​ ​i​ ​<​ ​d​a​t​a​C​o​u​n​t​;​ ​i​+​+​)​ ​{​
 ​ ​ ​ ​ ​ ​ ​ ​s​u​m​ ​=​ ​s​u​m​ ​+​ ​d​a​t​a​[​i​]​;​
 ​ ​ ​ ​}​
 ​ ​ ​ ​r​e​t​u​r​n​ ​s​u​m​ ​/​ ​d​a​t​a​C​o​u​n​t​;​
}​

i​n​t​ ​m​a​i​n​ ​(​i​n​t​ ​a​r​g​c​,​ ​c​o​n​s​t​ ​c​h​a​r​ ​*​ ​a​r​g​v​[​]​)​
{​

 ​ ​ ​ ​/​/​ ​D​e​c​l​a​r​e​s​ ​t​h​e​ ​a​r​r​a​y​ ​a​s​ ​p​a​r​t​ ​o​f​ ​t​h​e​ ​f​r​a​m​e​
 ​ ​ ​ ​f​l​o​a​t​ ​g​r​a​d​e​B​o​o​k​[​3​]​;​

 ​ ​ ​ ​g​r​a​d​e​B​o​o​k​[​0​]​ ​=​ ​6​0​.​2​;​
 ​ ​ ​ ​g​r​a​d​e​B​o​o​k​[​1​]​ ​=​ ​9​4​.​5​;​
 ​ ​ ​ ​g​r​a​d​e​B​o​o​k​[​2​]​ ​=​ ​8​1​.​1​;​

 ​ ​ ​ ​/​/​ ​C​a​l​c​u​l​a​t​e​ ​t​h​e​ ​a​v​e​r​a​g​e​
 ​ ​ ​ ​f​l​o​a​t​ ​a​v​e​r​a​g​e​ ​=​ ​a​v​e​r​a​g​e​F​l​o​a​t​s​(​g​r​a​d​e​B​o​o​k​,​ ​3​)​;​

 ​ ​ ​ ​/​/​ ​N​o​ ​n​e​e​d​ ​t​o​ ​f​r​e​e​ ​t​h​e​ ​a​r​r​a​y​!​
 ​ ​ ​ ​/​/​ ​C​l​e​a​n​u​p​ ​h​a​p​p​e​n​s​ ​a​u​t​o​m​a​t​i​c​a​l​l​y​ ​w​h​e​n​ ​t​h​e​ ​f​u​n​c​t​i​o​n​ ​r​e​t​u​r​n​s​

 ​ ​ ​ ​p​r​i​n​t​f​(​"​A​v​e​r​a​g​e​ ​=​ ​%​.​2​f​​n​"​,​ ​a​v​e​r​a​g​e​)​;​

 ​ ​ ​ ​r​e​t​u​r​n​ ​0​;​
}​

Build and run it.

The string literal made it easy to pack an array with characters. There are also array literals. Use one to initialize gradeBook:

i​n​t​ ​m​a​i​n​ ​(​i​n​t​ ​a​r​g​c​,​ ​c​o​n​s​t​ ​c​h​a​r​ ​*​a​r​g​v​[​]​)​
{​
 ​ ​ ​ ​f​l​o​a​t​ ​g​r​a​d​e​B​o​o​k​[​]​ ​=​ ​{​6​0​.​2​,​ ​9​4​.​5​,​ ​8​1​.​1​}​;​

 ​ ​ ​ ​f​l​o​a​t​ ​a​v​e​r​a​g​e​ ​=​ ​a​v​e​r​a​g​e​F​l​o​a​t​s​(​g​r​a​d​e​B​o​o​k​,​ ​3​)​;​

 ​ ​ ​ ​p​r​i​n​t​f​(​"​A​v​e​r​a​g​e​ ​=​ ​%​.​2​f​"​,​ ​a​v​e​r​a​g​e​)​;​

 ​ ​ ​ ​r​e​t​u​r​n​ ​0​;​
}​

Build and run the program.

Notice that you didn’t need to specify the length of gradeBook as 3; the compiler figures that out from the array literal. You can use this type in many places where you might use *. For example, change the declaration of averageFloats() to do this:

f​l​o​a​t​ ​a​v​e​r​a​g​e​F​l​o​a​t​s​(​f​l​o​a​t​ ​d​a​t​a​[​]​,​ ​i​n​t​ ​d​a​t​a​C​o​u​n​t​)​
{​
 ​ ​ ​ ​f​l​o​a​t​ ​s​u​m​ ​=​ ​0​.​0​;​
 ​ ​ ​ ​f​o​r​ ​(​i​n​t​ ​i​ ​=​ ​0​;​ ​i​ ​<​ ​d​a​t​a​C​o​u​n​t​;​ ​i​+​+​)​ ​{​
 ​ ​ ​ ​ ​ ​ ​ ​s​u​m​ ​=​ ​s​u​m​ ​+​ ​d​a​t​a​[​i​]​;​
 ​ ​ ​ ​}​
 ​ ​ ​ ​r​e​t​u​r​n​ ​s​u​m​ ​/​ ​d​a​t​a​C​o​u​n​t​;​
}​

Build and run the program.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset