However, in C we can group related variables together into something called a struct.

Similar documents
For instance, we can declare an array of five ints like this: int numbers[5];

In Java we have the keyword null, which is the value of an uninitialized reference type

C Programming Basics II

CS 11 C track: lecture 5

Kurt Schmidt. October 30, 2018

Lecture 5: Outline. I. Multi- dimensional arrays II. Multi- level arrays III. Structures IV. Data alignment V. Linked Lists

The combination of pointers, structs, and dynamic memory allocation allow for creation of data structures

CS61C Midterm Review on C & Memory Management

CS 31: Intro to Systems Pointers and Memory. Martin Gagne Swarthmore College February 16, 2016

+ Abstract Data Types

Heap Arrays and Linked Lists. Steven R. Bagley

Pointers, Dynamic Data, and Reference Types

Variables, Memory and Pointers

printf( Please enter another number: ); scanf( %d, &num2);

CS107 Handout 08 Spring 2007 April 9, 2007 The Ins and Outs of C Arrays

CP2 Revision. theme: dynamic datatypes & data structures

Dynamic Data Structures. CSCI 112: Programming in C

ECE 2400 Computer Systems Programming, Fall 2017 Prelim 1 Prep

PROGRAMMAZIONE I A.A. 2017/2018

Lab 5 - Linked Lists Git Tag: Lab5Submission

INITIALISING POINTER VARIABLES; DYNAMIC VARIABLES; OPERATIONS ON POINTERS

ECE 15B COMPUTER ORGANIZATION

Two approaches. array lists linked lists. There are two approaches that you can take:

Java and C CSE 351 Spring

Introduction to Linked Lists

Class Information ANNOUCEMENTS

CS 11 Haskell track: lecture 1

CS 31: Intro to Systems Pointers and Memory. Kevin Webb Swarthmore College October 2, 2018

Dynamic memory. EECS 211 Winter 2019

Heap Arrays. Steven R. Bagley

Lecture Notes on Memory Layout

Administrivia. Introduction to Computer Systems. Pointers, cont. Pointer example, again POINTERS. Project 2 posted, due October 6

BBM 201 DATA STRUCTURES

Memory and Addresses. Pointers in C. Memory is just a sequence of byte-sized storage devices.

Introduction to Programming Using Java (98-388)

Programs in memory. The layout of memory is roughly:

This exam is worth 24 points, or 24% of your total course grade. The exam contains six

MM1_ doc Page E-1 of 12 Rüdiger Siol :21

Data Structure Series

Homework 3 CS161 Computer Security, Fall 2008 Assigned 10/07/08 Due 10/13/08

Supporting Class / C++ Lecture Notes

CSCI-243 Exam 1 Review February 22, 2015 Presented by the RIT Computer Science Community

CSE 374 Programming Concepts & Tools. Hal Perkins Spring 2010

Lab 4 - Linked Lists

Lecture Notes on Generic Data Structures

Lecture 8 Dynamic Memory Allocation

CS61C : Machine Structures

A function is a named piece of code that performs a specific task. Sometimes functions are called methods, procedures, or subroutines (like in LC-3).

Functions in C C Programming and Software Tools

Dynamic Memory Allocation

Lectures 5-6: Introduction to C

ECE 220 Final Exam. Joseph Ravichandran, Kanad Sarkar, Srijan Chakraborty

Lists (Section 5) Lists, linked lists Implementation of lists in C Other list structures List implementation of stacks, queues, priority queues

malloc(), calloc(), realloc(), and free()

CS113: Lecture 9. Topics: Dynamic Allocation. Dynamic Data Structures

Memory Allocation in C C Programming and Software Tools. N.C. State Department of Computer Science

Outline. Briefly review the last class Pointers and Structs Memory allocation Linked lists

Java and C I. CSE 351 Spring Instructor: Ruth Anderson

CS11001/CS11002 Programming and Data Structures (PDS) (Theory: 3-1-0) Allocating Space

Data Structures and Algorithms for Engineers

CS61C Machine Structures. Lecture 4 C Structs & Memory Management. 9/5/2007 John Wawrzynek. www-inst.eecs.berkeley.edu/~cs61c/

Darshan Institute of Engineering & Technology for Diploma studies Unit 4

Chapter 1 Getting Started

Lecture Notes on Memory Management

Here's how you declare a function that returns a pointer to a character:

Announcements. assign0 due tonight. Labs start this week. No late submissions. Very helpful for assign1

CS61, Fall 2012 Section 2 Notes

Memory Management. CS31 Pascal Van Hentenryck CS031. Lecture 19 1

CS107, Lecture 9 C Generics Function Pointers

Lecture Notes on Queues

Run-time Environments - 3

Linked List. April 2, 2007 Programming and Data Structure 1

Chapter 19 Data Structures -struct -dynamic memory allocation

D Programming Language

EL2310 Scientific Programming

Introduction to Programming in C Department of Computer Science and Engineering

SYSC 2006 C Winter String Processing in C. D.L. Bailey, Systems and Computer Engineering, Carleton University

Writing Functions in C

Chapter 19 Data Structures

Introduction to Programming in C Department of Computer Science and Engineering. Lecture No. #34. Function with pointer Argument

Linked Lists in C and C++

CE221 Programming in C++ Part 2 References and Pointers, Arrays and Strings

DAY 3. CS3600, Northeastern University. Alan Mislove

Lecture 14 Notes. Brent Edmunds

COMP 250: Java Programming I. Carlos G. Oliver, Jérôme Waldispühl January 17-18, 2018 Slides adapted from M. Blanchette

Programming refresher and intro to C programming

COMP 524 Spring 2018 Midterm Thursday, March 1

Lectures 13 & 14. memory management

Lecture 14. No in-class files today. Homework 7 (due on Wednesday) and Project 3 (due in 10 days) posted. Questions?

Lectures 5-6: Introduction to C

Pointers. A pointer is simply a reference to a variable/object. Compilers automatically generate code to store/retrieve variables from memory

CS61C Machine Structures. Lecture 5 C Structs & Memory Mangement. 1/27/2006 John Wawrzynek. www-inst.eecs.berkeley.edu/~cs61c/

An Introduction to Data Structures

1 Dynamic Memory continued: Memory Leaks

C for C++ Programmers

Types II. Hwansoo Han

CS 11 C track: lecture 6

Linked List in Data Structure. By Prof. B J Gorad, BECSE, M.Tech CST, PHD(CSE)* Assistant Professor, CSE, SITCOE, Ichalkaranji,Kolhapur, Maharashtra

The C++ Object Lifecycle. EECS 211 Winter 2019

ch = argv[i][++j]; /* why does ++j but j++ does not? */

Transcription:

CIT 593: Intro to Computer Systems Lecture #21 (11/27/12) Structs Unlike Java, C++, and to some extent Python, C is not traditionally considered an objectoriented language. That is, there is no concept of an object that has a set of attributes and its own methods, and certainly nothing like inheritance, polymorphism, etc. However, in C we can group related variables together into something called a struct. For instance, here is how we would define a struct called flight_info that contains information about a single flight. struct flight_info { char *origin; char *destination; char *airline; double price; ; Now if we want to create an instance of this struct, we can simply declare one (it can be global, local, whatever) and then start using it: struct flight_info flight1; flight1.origin = PHL ; flight1.destination = ORD ; flight1.airline = United ; flight1.price = 500.0; The first line creates a variable called flight1 ; its type is struct flight_info. What does this look like in memory? Recall that the strings PHL, ORD, and United are immutable and are stored in the program text area of memory. But if flight1 is a local variable, then the three char pointers and the double (for price ) are all stored on the stack. Address Value Comment x1234 x1235 address of first char in PHL address of first char in ORD flight1.origin stored here flight1.destination stored here

x1236 address of first char in United flight1.airline stored here x1237 500.0 flight1.price stored here Note that there is no spot on the stack for the variable flight1 itself. In a way, flight1 is an array: its value is the address of the first element (specifically, the char pointer origin) and that value only exists as an offset in the symbol table. To get to individual elements of the struct, the compiler uses the offset based on the struct's definition. However, you cannot access something like flight1[2]; you must use the element's name. It can get a bit tiresome having to write struct flight_info over and over again. C allows you to create your own types using the typedef directive. This allows you to give a new name to an existing type. For instance, to create a type called flight, which is the same thing as struct flight_info, you could do this: typedef struct flight_info flight; This means create a new type called flight that is the same as what's called struct flight_info. Now you don't have to keep using struct flight_info everywhere: flight flight2; flight2.destination = LHR ; flight2.airline = flight1.airline; Pointers to Structs One other key difference between a struct and an array is that you can have pointers to structs: flight *p = &flight2; Note that the variable p would, in fact, hold the address of the first element of flight2. To use the pointer, you would first have to dereference it: (*p).price = 200;

This can get a bit wieldy, so there is a shortcut: p->price = 200; This is the same as the instruction above, but looks nicer and is much more common. Keep in mind that in order to use this notation, p would have to be a pointer to a struct, not the name of the struct itself. Linked Lists Over the course of the next few lectures, we'll start talking about various data structures and their implementations in C. The field of data structures refers to how data is stored, accessed, added, deleted, etc. Abstract data types define how the structure is used Concrete data types define how the structure is implemented We've already seen one abstract data type: a stack. You could also argue that an array is a (concrete) data type. We'll start with the simplest of data structures, which is the linked list. Linked lists are a simple datatype in which each piece of data is stored in a node, and each node contains the data and a pointer to the next node in the chain. Here is a linked list in which the data in each node is an int. The linked list has a head, which is a pointer to the first element; in the last node, the pointer to the next node is null. head 5 7 2 4 Linked lists can be doubly-linked, meaning that each node points to both next and previous, but we'll only focus on a singly-linked list for now. null

Using the example above, here is the definition of a node: typedef struct Node node; struct Node { int data; node *next; ; To refer to the linked list, all we need is a pointer to the first element (the head of the list): // pointer to head of list node *head; Note that declaring a pointer to a node does not allocate any space for a node! It just allocates space for a variable that holds a node's address. Now we'll look at some of the functions for operating on a linked list. First, let's see how we would add a new element to the list. We'll say that we're going to add it to the front (head) of the list; this makes things a little bit easier. Adding a new element to the list consists of three steps: 1. Creating a new node for that piece of data 2. Updating that node's next pointer to refer to what is currently the node at the head of the list 3. Updating the head pointer to refer to the newly created node Here's a possible implementation in which the parameter d is the value to store in the list, and head is a pointer to the first element (head will be null if the list is empty): 1 2 3 4 5 6 7 void add_to_front(int d) { node new_node; new_node.data = d; new_node.next = head; head = &new_node; This seems to make sense, right? On line 3, we create a node called new_node, and then set its data field to d (step 1, above) on line 4. On line 5, we set the value of its next pointer to that of head, so that it holds the address that head holds (step 2, above). Finally, on line 6, we update head to point to this new node.

See the problem? If not, that's okay, but when you run this and try to add a few new values to the list, you'll see something interesting: all the old values will be overwritten by new ones! Why is this happening? Because new_node is declared on the stack! On line 6, you put the address of a stack variable into head. When you overwrite that data on a subsequent function call, head still points to that same address, and now the old data is lost. In order to address this situation, we need to dynamically allocate some new memory for the node. We can't use global memory because we don't know in advance (i.e., when we write the program) how many nodes we'll have in our linked list. So we need to use the heap. The heap is an area of memory in your program that is managed by the operating system. Your program requests space on the heap from the operating system by indicating how much space it will need, and the OS returns a pointer to the space it's freed up for you. Here's the revised implementation of adding a new element to the list, using the heap instead of the stack: 1 2 3 4 5 6 7 void add_to_front(int d) { node *new_node = (node *)malloc(sizeof(node)); new_node->data = d; new_node->next = head; head = new_node; On line 3, we use the malloc function to get a pointer to some space on the heap. The argument is the amount of space (number of bytes) we need; in this case, we need enough to hold one node. The return value from malloc is a void pointer ; it's a pointer, but we don't know to what type. So we need to cast it to a node pointer before we can start using it. Now new_node holds the address of a piece of memory in the heap, which does not get overwritten by subsequent function calls, so it's safe to put the value of new_node (i.e., the address of the first element in the struct) into head. One thing we typically want to do with a data structure is determine whether it contains a specific value. For instance, in the example above, we might want to see whether it contains a certain number.

With a linked list, you typically start with the first element (referred to by the head pointer) and then look at all subsequent elements (following the next pointers) until you hit the end. This function returns 1 if k is found in the linked list, and 0 if not: int find(int k) { node *n = head; while (n!= NULL) { if (n->data == k) return 1; else n = n->next; return 0;