4: data abstractionpds15.egloos.com/pds/200911/25/21/chapter_4_2.pdf · thinking in c++ page 6...

24
4: Data Abstraction 4: Data Abstraction 김동원 김동원 김동원 김동원 2003.02.12

Upload: others

Post on 07-Jul-2020

3 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

4: Data Abstraction4: Data Abstraction

김동원김동원김동원김동원

2003.02.12

Page 2: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 1

Overview

• Abstract data typing

• Object details

• Header file etiquette

• Nested structures

• Global scope resolution

Page 3: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 2

Abstract data typing

• The ability to package data with functions

– Allows you to create a new data type

– Called encapsulation

• abstract data type

– Even though it acts like a real, built-in data type, we refer to it

– It allows us to abstract a concept from the problem spaceinto the solution space

• object.memberFunction(arglist)

– Calling a member function for an object

– referred to as sending a message to an object

Page 4: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 3

Object details

• The size of a struct

– The combined size of all of its members

– Sometimes when the compiler lays out a struct, it adds extra bytes

� This may increase execution efficiency

Page 5: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 4

Object details (example)

#include "CLib.h"

#include "CppLib.h"

#include <iostream>

using namespace std;

struct A

{

int i[100];

};

struct B

{

void f();

};

void B::f()

{ }

Page 6: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 5

Object details (example)

int main()

{

cout << "sizeof struct A = " << sizeof(A)

<< " bytes" << endl;

cout << "sizeof struct B = " << sizeof(B)

<< " bytes" << endl;

cout << "sizeof CStash in C = "

<< sizeof(CStash) << " bytes" << endl;

cout << "sizeof Stash in C++ = "

<< sizeof(Stash) << " bytes" << endl;

}

Page 7: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 6

Header file etiquette

• Importance of header files

• The multiple-declaration problem

• The preprocessor directives #define, #ifdef, and #endif

• A standard for header files

• Namespaces in headers

• Using headers in projects

Page 8: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 7

Header file etiquette

• The header file

– tells the compiler what is available in your library

– has the interface specification

• You can use the library even if you only possess the header file along with the object file or library file

– Don’t need the source code for the cpp file

Page 9: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 8

Importance of header files

• In the past

– People would sometimes do this to speed up the compiler just a bit by avoiding the task of opening and including the file

• In the C language

– Allows you the option of ignoring the header file and simply declaring the function by hand

• In the C++ language

– must include the header file everywhere a struct is used and where struct member functions are defined

– The compiler will give an error message if you try to call a regular function, or to call or define a member function, without declaring it first

– By enforcing the proper use of header files, the language ensures consistency in libraries, and reduces bugs by forcing the same interface to be used everywhere

Page 10: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 9

Certain issues when the using header file

• First issue

– concerns what you can put into header files

– The basic rule is only declarations

� Only information to the compiler but nothing that allocates storage by generating code or creating variables

� Why

• The header file will typically be included in several translation units in a project

• If storage for one identifier is allocated in more than one place, the linker will come up with a multiple definition error

Page 11: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 10

Certain issues when the using header file (The multiple-declaration problem)

• The second issue

– When you put a struct declaration in a header file, it is possible for the file to be included more than once in a complicated program

– To prevent this error when multiple header files are included

� You need to build some intelligence into your header files using the preprocessor

– Both C and C++

� Allow you to redeclare a function, as long as the two declarations match

� Will not allow the redeclaration of a structure

Page 12: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 11

The preprocessor directives#define, #ifdef, and #endif

• The preprocessor directive #define can be used to create compile time flags

#define FLAG

or you can give it a value

#define PI 3.14159

• The label can now be tested by the preprocessor to see if it has been defined

#ifdef FLAG

• This inclusion stops when the preprocessor encounters the statement

#endif // FLAG

Page 13: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 12

A standard for header files

• In each header file

– You should first check to see if this header has already been included in this particular cpp file

#ifndef HEADER_FLAG

#define HEADER_FLAG

// Type declaration here...

#endif // HEADER_FLAG

Page 14: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 13

A standard for header files (example)

#ifndef SIMPLE_H

#define SIMPLE_H

struct Simple {

int i,j,k;

initialize() { i = j = k = 0; }

};

#endif // SIMPLE_H ///:~

Page 15: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 14

Namespaces in headers

• using namespace std;

– allows the names in the Standard C++ library to be used without qualification

• The using directive

– eliminates the protection of that particular namespace

– The effect lasts until the end of the current compilation unit

– This loss of namespace protection

• In short: don’t put using directives in header files

Page 16: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 15

Using headers in projects

• Put the declaration for each type or group of associated types in a separate header file

• Define the functions for that type in a translation unit

• When you use that type, you must include the header file to perform the declarations

Page 17: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 16

Nested structures

• A structure within another structure

Page 18: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 17

Nested structures (example)

#ifndef STACK_H#define STACK_Hstruct Stack {

struct Link {void* data;Link* next;void initialize(void* dat, Link* nxt);

}* head;void initialize();void push(void* dat);void* peek();void* pop();void cleanup();

};#endif // STACK_H ///:~

Page 19: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 18

Nested structures (example)

#include "Stack.h"#include "../require.h"using namespace std;void Stack::Link::initialize(void* dat, Link* nxt) {

data = dat;next = nxt;

}void Stack::initialize() { head = 0; }void Stack::push(void* dat) {

Link* newLink = new Link;newLink->initialize(dat, head);head = newLink;

}

Page 20: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 19

Nested structures (example)

void* Stack::peek() {

require(head != 0, "Stack empty");return head->data;

}void* Stack::pop() {

if(head == 0) return 0;void* result = head->data;Link* oldHead = head;head = head->next;delete oldHead;return result;

}

void Stack::cleanup() {require(head == 0, "Stack not empty");

}

Page 21: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 20

Nested structures (example)

#include "Stack.h"#include "../require.h"#include <fstream>#include <iostream>#include <string>using namespace std;int main(int argc, char* argv[]) {

requireArgs(argc, 1); // File name is argumentifstream in(argv[1]);assure(in, argv[1]);Stack textlines;textlines.initialize();string line;// Read file and store lines in the Stack:while(getline(in, line))textlines.push(new string(line));// Pop the lines from the Stack and print them:

Page 22: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 21

Nested structures (example)

string* s;

while((s = (string*)textlines.pop()) != 0) {

cout << *s << endl;

delete s;

}

textlines.cleanup();

}

Page 23: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 22

Global scope resolution

• The scope resolution operator

– Gets you out of situations in which the name the compiler chooses by default (the “nearest” name) isn’t what you want

Page 24: 4: Data Abstractionpds15.egloos.com/pds/200911/25/21/Chapter_4_2.pdf · Thinking in C++ Page 6 Header file etiquette • Importance of header files • The multiple-declaration problem

Thinking in C++ Page 23

Global scope resolution (example)

int a;void f() {};struct S {

int a;void f();

};void S::f() {

::f(); // Would be recursive otherwise!::a++; // Select the global aa--; // The a at struct scope

}int main() {S s; f();

}