Structures Etter Chapter 7

62
1 Structures Etter Chapter 7 In engineering, we need to process or visualize data Some of you have done Matlab simulations and visualizations Sometimes we work with a single piece of data E.g. the temperature reading at this point in time. But usually we’d work with a large set of data. E.g. the temperature reading every minute for the last 8 hours. This works out to 480 pieces of data.

description

Structures Etter Chapter 7. In engineering, we need to process or visualize data Some of you have done Matlab simulations and visualizations Sometimes we work with a single piece of data E.g. the temperature reading at this point in time. But usually we’d work with a large set of data. - PowerPoint PPT Presentation

Transcript of Structures Etter Chapter 7

Page 1: Structures Etter Chapter 7

1

StructuresEtter Chapter 7

• In engineering, we need to process or visualize data– Some of you have done Matlab simulations and

visualizations

• Sometimes we work with a single piece of data– E.g. the temperature reading at this point in time.

• But usually we’d work with a large set of data.– E.g. the temperature reading every minute for the last 8

hours.– This works out to 480 pieces of data.

Page 2: Structures Etter Chapter 7

2

StructuresPages 327 to 332

• In Lecture 8, we solved this problem by using arrays.

• BUT arrays can only store data of a single type!– E.g. you can’t store strings in this array:

double mydata[1024];

Page 3: Structures Etter Chapter 7

3

Structures

• Fortunately C gives us a way of representing related information of different types, in a “structure.”

• E.g. hurricanes have names, intensities and categories.– Name: This is a string.– Intensity: Integer.– Category: Intger.

Page 4: Structures Etter Chapter 7

4

Structures

struct hurricane{

char name[10];int year, category;

};

• “name”, “year” and “category” are called “members” of the structure “hurricane”

• This statement declares a new type!– IT DOES NOT DECLARE A NEW VARIABLE!

This “;” is very important and often forgotten!

Page 5: Structures Etter Chapter 7

5

Self Help Questions

1. What are the differences between a “variable” and a “type”?

Page 6: Structures Etter Chapter 7

6

Answer

1. A “type” tells C what the variable is. E.g. “int” is a type. “double” is a type. After declaring our structure “hurricane”, “struct hurricane” is also a type! Types do not occupy memory and cannot store values.To declare a variable, we always use “type varname;”. So to declare an integer variable, we use “int xl;”. This tells C that “x1” is a variable of type “int”. Variables occupy memory and can be assigned values.

Page 7: Structures Etter Chapter 7

7

Structure Variables

• To declare a new variable of the “hurricane” type, we do:

struct hurricane h1;

?

?

?

h1name

year

category

Page 8: Structures Etter Chapter 7

8

Structure Variables

• You can declare multiple variables of this type:

struct hurricane h1, my_hurricane;

?

?

?

h1name

year

category

?

?

?

my_hurricane

name

year

category

Page 9: Structures Etter Chapter 7

9

Structure Variables

• You can also initialize the members of a structure variable.

struct hurricane h1 = {“Camille”, 1969, 5};

Camille

1969

5

h1name

year

category

Page 10: Structures Etter Chapter 7

10

Structure Variables

• Alternatively you can initialize the members using C statements:struct hurricane h1;

h1.name = “Camille”;

h1.year = 1969;

h1.category = 5;

• Notice how we used the “.” operator to access members of a structure variable!

Page 11: Structures Etter Chapter 7

11

Structure Example

• We can use scanf or fscanf statements to write to structure variable members.

• We can use printf or fprintf to read them.

• We will now write a program that reads hurricane information from a file, and prints them out.

Page 12: Structures Etter Chapter 7

12

Structure Example

#include <stdio.h>

#define FILENAME "storms2.txt"

struct hurricane

{

char name[10];

int year, category;

};

Page 13: Structures Etter Chapter 7

13

Structure Example

int main(void)

{

/* Declare variables */

struct hurricane h1;

FILE *storms;

storms = fopen(FILENAME, "r");

if(storms == NULL)

printf("Error opening data file.\n");

Page 14: Structures Etter Chapter 7

14

Structure Example

else{

while(fscanf(storms, "%s %d %d", h1.name, &h1.year, &h1.category) == 3)

{printf("Hurricane: %s\n", h1.name);printf("Year: %d, Category: %d\n",

h1.year, h1.category);}fclose(storms);

} /* else */return 0;

}

Page 15: Structures Etter Chapter 7

15

Self Help Questions

1. In the fscanf statement:fscanf(storms, "%s %d %d", h1.name,

&h1.year, &h1.category)

- h1.year and h1.category are both passed to fscanf with “&”, but not h1.name. Why?

Page 16: Structures Etter Chapter 7

16

ANSWERS

• The “name” member of “hurricane” is defined as char name[10];struct hurricane

{

char name[10];

int year, category;

};

Page 17: Structures Etter Chapter 7

17

ANSWERS

• This makes “name” an array of 10 characters.• In an array:

– The name of the array is a pointer to the first item of the array.

• “fscanf” expects pointers to the variable arguments. E.g.:

fscanf(fptr, “%d”, &a);– This is so that fscanf can return the values read using

these variables.– So we use “&” to get the address of the variable.

Page 18: Structures Etter Chapter 7

18

ANSWERS

• Since “name” is already a pointer to the first item of the “name” array, there is no need to use “&”. We can just pass in “name” instead of “&name”.– Further question: What does &name give

you?

Page 19: Structures Etter Chapter 7

19

Computations with Structures

• We use the “.” operator to access individual members of a structure variable:

h1.name=“Hazel”;

• If we use the structure variable’s name without the “.” operator, then we are accessing the entire array.

Page 20: Structures Etter Chapter 7

20

Computations with Structures

• You can do assignments with structures:– Given two structures “h1” and “h2”.

• To make h2 equal to h1, just do:

h2 = h1;

Page 21: Structures Etter Chapter 7

21

Computation with Structures

• E.g.struct hurricane h1 ={“Hazel”, 1954, 4}, h2;

………

h2 = h1;

Hazel

1954

4

h1name

year

category

?

?

?

h2name

year

category

Initially:

Page 22: Structures Etter Chapter 7

22

Computation with Structures

• E.g.struct hurricane h1 ={“Hazel”, 1954, 4}, h2;

………

h2 = h1;

Hazel

1954

4

h1name

year

category

Hazel

1954

4

h2name

year

category

After h2=h1:

Page 23: Structures Etter Chapter 7

23

Computation with Structures

• Other operations like “+”, “-”, “*”, “/”, “>”, “<“, “>=“, “==“ etc. can only be performed on individual structure variable members.

E.g. h1.category += 1; /* Increment */

Page 24: Structures Etter Chapter 7

24

Computation Example

• We will modify our hurricane program to print only the Category 5 hurricanes.– Can just do this by:

if(h1.category == 5)

/* Print hurricane data */

Page 25: Structures Etter Chapter 7

25

Computation Example

#include <stdio.h>

#define FILENAME "storms2.txt"

struct hurricane

{

char name[10];

int year, category;

};

Page 26: Structures Etter Chapter 7

26

Computation Example

int main(void){struct hurricane h1;FILE *storms;

storms = fopen(FILENAME, "r");if(storms == NULL)

printf("Error opening data file.\n");

Page 27: Structures Etter Chapter 7

27

Computation Example

else{

printf("Category 5 hurricanes\n\n");while(fscanf(storms, "%s %d %d",

h1.name, &h1.year, &h1.category) == 3)if(h1.category == 5)

printf("%s\n", h1.name);fclose(storms);

} /* else */}

Page 28: Structures Etter Chapter 7

28

Passing Structures to FunctionsPages 332 to 334

• Entire structures can be passed into functions.– Structures are passed by value:

• Members of the actual arguments are copied into corresponding members of the formal parameters.

Page 29: Structures Etter Chapter 7

29

Passing Structures to Functions#include <stdio.h>

struct hurricane{

char name[10];int year, category;

};

void print_struct(struct hurricane my_h){

printf("INSIDE print_struct function\n");printf("Contents of parameter my_h: %s, %d, %d\n", my_h.name, my_h.year, my_h.category);printf("Address of parameter my_h: %u\n\n", &my_h);

}

Formal parameter declaration for a structure.

Page 30: Structures Etter Chapter 7

30

Passing Structures to Functions

int main(void)

{

struct hurricane h1 = {"Hazel", 1954, 4};

printf("\nContents of h1: %s, %d, %d\n", h1.name, h1.year, h1.category);

printf("Address of h1: %u\n", &h1);

printf("Passing h1 in as argument to print_struct\n\n");

print_struct(h1);

}

Declaration for struct variable h1.

Structure variable is passed in just like any other variable.

Page 31: Structures Etter Chapter 7

31

Passing Structures by Reference.

• Ordinarily, structures are passed by value.– This means that you cannot modify the

members of a structure from within a function.

• To be able to modify structure members, you must pass in a pointer to the argument, rather than the argument itself.

Page 32: Structures Etter Chapter 7

32

Passing Structures by Reference

Self Help Question• If:

– int *ptr declares a pointer to int.– double *ptr declares a pointer to a double.

– char *ptr declares a pointer to a char.

• How do you:– Declare a pointer to a struct hurricane?

Page 33: Structures Etter Chapter 7

33

Passing Structures by Reference

#include <stdio.h>

#include <string.h>

/* This program has a function that modifies a structure passed to it */

struct hurricane

{

char name[10];

int year, category;

};

Page 34: Structures Etter Chapter 7

34

Passing Structures by Reference

void modify_structure(struct hurricane *hur)

{

/* Modify the structure values */

strncpy(hur->name, "Grace", 10);

hur->year=1972;

hur->category = 5;

}

Pointer to a struct hurricane.

When accessing structure members from a pointer, use “->” instead of “.”.

Page 35: Structures Etter Chapter 7

35

Passing Structures by Reference

int main(void){

struct hurricane h1={"Audrey", 1957, 4};

printf("Contents of h1: %s %d %d\n", h1.name, h1.year, h1.category);printf("\nCalling modify_structure to change the contents of h1.\n\n");

modify_structure(&h1);

printf("Contents of h1: %s %d %d\n\n", h1.name, h1.year, h1.category);

}

Pass in the address of h1, instead of h1 itself.

Page 36: Structures Etter Chapter 7

36

Passing Structures by Reference

• One point to note:– When accessing members of a structure

variable, we use the “.” operator.– E.g.

struct hurricane my_hurricane;

my_hurricane.year=1852;

Page 37: Structures Etter Chapter 7

37

Passing Structures by Reference

• One point to note:– When accessing members of a pointer to a

structure variable, we use the “->” operator.– E.g.

struct hurricane *ptr = &my_hurricane;

ptr->year=1952;– “ptr->year” is a shortcut for (*ptr).year;

Page 38: Structures Etter Chapter 7

38

Returning Structures from Functions.

• A function can return whole structures.• To declare a function that returns an int, we do:

int myfun1(){

…}

• To declare a function that returns a char, we do:char myfun2(){

…}

Page 39: Structures Etter Chapter 7

39

Returning Structures from Functions.

• To call these functions:char c;

int num;

num = myfun1();

c = myfun2();

Page 40: Structures Etter Chapter 7

40

Returning Structures from Functions.

• Likewise, to declare a function that returns struct hurricane:struct hurrican myfun3(…)

{…

}

• To call myfun3:struct hurricane my_h;

my_h = myfun3();

Page 41: Structures Etter Chapter 7

41

Example

#include <stdio.h>

struct tsunami{int mo, da, yr, fatalities;double max_height;char location[20];

};

struct tsunami get_info(void);

Page 42: Structures Etter Chapter 7

42

Examplestruct tsunami get_info(void){

/* Declare variables */struct tsunami t1;

printf("Enter information for tsunami in the following order:\n");printf("Enter month, day, year, number of deaths:\n");scanf("%d %d %d %d", &t1.mo, &t1.da, &t1.yr,

&t1.fatalities);printf("Enter location (<20 characters.):\n");scanf("%s", t1.location);

return t1;}

t1 will temporarily store what the user keys in.

t1 is returned here.

Page 43: Structures Etter Chapter 7

43

Example

int main(void){

struct tsunami my_t;

my_t = get_info();

printf("\nThe information you entered:\n\n");printf("Date (day/month/year): %d/%d/%d\n",

my_t.da, my_t.mo, my_t.yr);printf("Location: %s\n", my_t.location);printf("Fatalities: %d\n\n", my_t.fatalities);

return 0;}

We declare a variable of type struct tsunami, the exact same type as the function get_info.

We call get_info just like any other function.

Page 44: Structures Etter Chapter 7

44

Arrays of Structures(Pages 334 to 336)

• Refresher:– To declare an array of 20 ints:

int my_array1[20];

– To declare an array of 20 doubles:double my_array2[20];

– To declare an array of 20 chars:char my_array3[20];

• Question: How do we declare an array of “struct hurricane”?

Page 45: Structures Etter Chapter 7

45

Array of Structures

• Assuming we have already declared “struct hurricane”, do declare an array of 20 “struct hurricane”:

struct hurricane my_array4[20];

Page 46: Structures Etter Chapter 7

46

Array of Structures

• This creates 20 “struct hurricane” variables, each with:– name– year– category

• All values are un-initialized.

? ? ?

? ? ?

? ? ?

? ? ?

… … …

? ? ?

name year category

0

1

2

3

19

Page 47: Structures Etter Chapter 7

47

Array of Structures

• Refresher: – To access individual ints in my_array1:

• myarray1[2] = 5;

– To access individual doubles in my_array2:• myarray2[5] = 3.1;

– To access individual chars in my_array3:• myarray3[2] = ‘c’;

• So:– How to we access individual struct variables?

Page 48: Structures Etter Chapter 7

48

Array of Structures

Answer:

my_array4[0].name = “Camille”;

my_array4[0].year = 1969;

my_array4[0].category = 5;

Page 49: Structures Etter Chapter 7

49

Example

/* Program ch7_4.c */

#include <stdio.h>#define FILENAME "storms2.txt"

struct hurricane{

char name[10];int year, category;

};

void print_hurricane(struct hurricane h);

Page 50: Structures Etter Chapter 7

50

Exampleint main(void){

int max_category=0, k=0, npts;struct hurricane h[100];

FILE *storms;

storms = fopen(FILENAME, "r");if(storms == NULL)

printf("Error opening data file.\n");else{

printf("Hurricanes with Maximum Category:\n");

Page 51: Structures Etter Chapter 7

51

Examplewhile(fscanf(storms, "%s %d %d", h[k].name,

&h[k].year, &h[k].category) == 3){

if(h[k].category > max_category)max_category = h[k].category;

k++;} /* while */npts = k;

for(k=0; k<npts; k++)if(h[k].category == max_category)

print_hurricane(h[k]);

fclose(storms);} /* else */

}

Page 52: Structures Etter Chapter 7

52

Example

void print_hurricane(struct hurricane h)

{

printf("Hurricane: %s\n", h.name);

printf("Year: %d, Category: %d\n", h.year, h.category);

}

Page 53: Structures Etter Chapter 7

53

Case Study(Pages 336 to 340)

• Tsunamis are large destructive waves:– Caused by sudden movements in the sea

floor.

• Wave speeds:– Shallow water: 125 mph.– Deep water: 400 mph.

• Heights:– 30 to 200+ feet high.

Page 54: Structures Etter Chapter 7

54

Case Study

• Problem Statement: Print a report giving:– Maximum wave height for tsunamis in a data

file.– Average wave height.– Location of all tsunamis with heights higher

than the average.

Page 55: Structures Etter Chapter 7

55

Case Study

• Analysis:– Open file “waves2.txt”

• Tell the user if the file open fails.

– Find largest maximum height.• Set max to 0 first.• Assume the tsunami array is called t:

– If t[k].max_height > max, set max = t[k].max_height.

– Find average• Add t[k] to sum.• Average = sum / # of data points

Page 56: Structures Etter Chapter 7

56

Case Study

– Print locations with wave heights larger than the average:

• if t[k].max_height > average, print t[k].location.

• Note: Height data in file is in meters. Report is in feet:– 1 m = 3.28 feet.– z m = z * 3.28 feet.

Page 57: Structures Etter Chapter 7

57

Case Study

/* ch7_5.c */

#include <stdio.h>#define FILENAME "waves1.txt"

struct tsunami{

int mo, da, yr, fatalities;double max_height;char location[20];

};

Page 58: Structures Etter Chapter 7

58

Case Study

int main(void){

/* Declare variables */int k=0, npts;double max=0, sum=0, ave;struct tsunami t[100];

FILE *waves;

waves = fopen(FILENAME, "r");if(waves == NULL)

printf("Error opening data file.\n");

Page 59: Structures Etter Chapter 7

59

Case Study

else{

while(fscanf(waves, "%d %d %d %d %lf %s", &t[k].mo, &t[k].da, &t[k].yr,&t[k].fatalities, &t[k].max_height, t[k].location) == 6)

{

sum += t[k].max_height;

if(t[k].max_height > max)max = t[k].max_height;

k++;} /* while */

Page 60: Structures Etter Chapter 7

60

Case Study

npts = k;

ave = sum/npts;

printf("Summary Information for

Tsunamis\n");

printf("Maximum wave height (in feet): %.2f\n", max * 3.28);

printf("Average wave height (in feet): %.2f\n", ave * 3.28);

Page 61: Structures Etter Chapter 7

61

Case Study

printf("Tsunamis with greater than average heights:\n\n");

for(k=0; k<npts; k++)if(t[k].max_height > ave)

printf("%s\n", t[k].location);

fclose(waves);} /* else */

}

Page 62: Structures Etter Chapter 7

62

Summary

• In this lecture we learnt:– How to aggregate data together in structures.– How to pass structures to functions.– How to return structures in functions.– How to declare arrays of structures.