Download as pdf or txt
Download as pdf or txt
You are on page 1of 78

Data Structure

Chapter 2 Arrays

1. Abstraction Data Types & C++ Class


2. The Array as an Abstract Data Type
3. The Polynomial
4. Sparse Matrix
5. The String

J.-J. Chen, EE NTUST 2 Array-1


A class

• Four components of a class


– A class name
– Data members
– Member functions
– Levels of program access
• Public: data or functions can be accessed from anywhere
• Protected: accessed from within its class, from its sub-class, or
from a friend class
• Private: accessed from within its class or by a friend class

J.-J. Chen, EE NTUST 2 Array-2


A Rectangle Class
#ifndef RECTANGLE_H Program 2.1
#define RECTANGLE_H Definition of the C++ class Rectangle
// in the header file Rectangle.h
class Rectangle {
public: // the following members are public
// the next four members are member functions
Rectangle(); // constructor
~Rectangle(); // destructor
int GetHeight(); // returns the height of the rectangle
int GetWidth(); // returns the width of the rectangle
private:
// the following members are data members
int xLow,yLow,h,w;
// (xLow,yLow) are the coordinates of the bottom left corner of the rectangle
// w is the width of the rectangle; h is the height of the rectangle
};
#endif

J.-J. Chen, EE NTUST 2 Array-3


Data Abstraction & Encapsulation

• Data Encapsulation
– Declaring all data members of a class to be private (or
protected)
– External access→ define member functions that get and
set data members

• Data Abstraction
– Specification
• of operations of a class is separated from their implementation,
e.g., Rectangle.h →Rectangle.cpp
• Specification is contained in the public portion of a class
– Abstraction data type is implementation-independent

J.-J. Chen, EE NTUST 2 Array-4


Special Class Operations

• Constructor
– Is a member function which initializes data members of an object
– If provided, it is automatically executed when an object of that class
is created
– If not provided, data members are not properly initialized
• Destructor
– Is a member function which deletes data members immediately
before the object disappears
– Invoked automatically when a class object goes out of scope or
explicitly deleted
– Pointer data member → the object that it was pointing to is not
deleted

J.-J. Chen, EE NTUST 2 Array-5


Implementation of operations on
Rectangle

// in the source file Rectangle.C Program 2.2


#include “Rectangle.h”
// the prefix “Rectangle::” identifies GetHeight() and GetWidth()
// as member functions belonging to class Rectangle. It is required
// because the member functions are implemented outside their
// class definition

int Rectangle::GetHeight( ) { return h; }


int Rectangle::GetWidth( ) { return w; }

J.-J. Chen, EE NTUST 2 Array-6


Using Object

// in a source file main.c


#include <iostream.h>
Program 2.3
#include “Rectangle.h”
main() {
Rectangle r, s; // r and s are objects of class Rectangle
Rectangle *t=&s; // t is a pointer to class object s
.
.
// use • to access members of class objects
// use → to access members of class objects through pointers.

If( r.GetHeight() * r.GetWidth() > t → GetHeight() *t→ GetWidth() )


cout << “r”;
else cout << “s”;
cout << “has the greater area” << endl;
}

J.-J. Chen, EE NTUST 2 Array-7


Object vs. Pointer

Memory
allocation Rectangle r, s;
Rectangle *t = &s;
t: 0xaaaa 0xdddd
Pointer
to object
s: 0xdddd Rectangle

name type address


s Rectangle oxdddd
t Pointer oxaaaa

J.-J. Chen, EE NTUST 2 Array-8


Constructor Example
Rectangle:: Rectangle(int x, int y, int height, int width)
{ Program 2.4
xLow = x; yLow = y;
h = height; w = width;
}
→ a constructor must be public, and has no return type

Example: initialize Rectangle objects: Program 2.4


Rectangle r(1,3,6,6); example
Rectangle *s=new Rectangle(0,0,3,4)
Example: illegal declaration Rectangle t;
once a constructor is defined, proper input arguments for
initialization must be provided → otherwise, it is a compile-time
error
J.-J. Chen, EE NTUST 2 Array-9
Constructor Example

Rectangle::Rectangle(int x=0,int y=0; int height=0, int


width=0): xLow(x),yLow(y),h(height),w(width)
{ }
Program 2.5
Body is
empty
The data members are initialized by using a member
initialization list (i.e., colon followed by a list of data
members and the arguments to which they are to be
initialized in parentheses)
→ Directly initializes the data members in a single step

J.-J. Chen, EE NTUST 2 Array-10


Operator Overloading

• Overload operators
– for user-defined data types is allowed in C++.
– Takes the form of a class member function or an
ordinary function
1. int Rectangle:: operator==(const Rectangle &s) Program 2.6
2. {
3. if(this==&s) return (1); //check if two objects are the same
4. if( (xLow=s.x1) &&(yLow==s.y1) &&(h==s.h) (w==s.w) {
5. return (1);
6. else return (0)
7. } “this” is the pointer to the
data object upon which the
operators is performed
J.-J. Chen, EE NTUST 2 Array-11
Operator Overloading ==
#include "iostream.h"
class complex {
public:
complex(int re, int im) { real=re; imaginary=im;}
int get_real() {return(real);}
int get_imaginary() {return(imaginary);}
int operator==(complex x) {
if(real==x.get_real() && imaginary==x.get_imaginary())
return (1);
else return(0);
}
private: 1. main(){
int real; 2. int i;
int imaginary; 3. complex a(1, 2),b(3, 4);
} 4. cout << (a==b);
5. }

J.-J. Chen, EE NTUST 2 Array-12


Operator overloading <<
ostream & operator<<(ostream& os, Rectangle &r)
{
os << “Position is:” << r.xLow<<“ “;
os << r.yLow<< endl;
os << “Height is:” << r.h << endl;
os << “Width is:” << r.w << endl;
Return os;
}

Operator << access private date members of class Rectangle


→ therefore, it must be made a friend of Rectangle.
Note that: friend is an exception of data encapsulation, should be
avoided in most cases. But sometimes it is necessary as in this case.

Example: cout << r;


→ Position is: 1 3 // r.xLow r.yLow
→ Height is :6 // r.h
→ Width is: 6 // r.w
J.-J. Chen, EE NTUST 2 Array-13
The type ostream &
• The ostream & return
type means that
– this operator returns a
reference to an ostream
object.
– Example:
cout << “potluck”
returns the object
cout

J.-J. Chen, EE NTUST 2 Array-14


Operator overloading <<
#include "iostream.h"
class complex{
public:
complex(int re, int im){real=re; imaginary=im;}
Declare operator<<
int get_real() {return(real); } as a friend operator
int get_imaginary() {return(imaginary);}
friend ostream& operator << (ostream&, complex);
private:
int real; int imaginary;
};
ostream &operator <<(ostream&os, complex x){
os<<x.get_real()<<endl;
os<<x.get_imaginary()<<endl;
return(os); main(){
} int i;
complex a(1,2),b(3,4);
cout<<a<<b;
// will be illegal if the return type of “<<“ is not ostream&
} 2 Array-15
J.-J. Chen, EE NTUST
Miscellaneous Topics

• Struct
– Is idential to a class, except that the default level of access is public
– In a class, the default is private class
• Union
– A struct that reserves storage for the largest of its data members
– Useful for applications where only one of many possible data item
needs to be stored at any time
• Static class data member
– A global variable for its class class X {
public:
– A definition of the data member int normalValue = 5;
outside the class definition is required static const int i = 0;
// declaration, with initializer
};
const int X::i; // definition

J.-J. Chen, EE NTUST 2 Array-16


Example of Union
struct pair{
A pair requires 2x32 bits =
int n1; // 32 bits 64 bits
float n2; // 32 bits
}

struct exclusive_pair{
union {
int n1; // 32 bits A exclusive_pair contains only
an integer or a floating point
float n2; // 32 bits
number
} → requires only 32 bits
}

J.-J. Chen, EE NTUST 2 Array-17


Example of Union
#include “iostream.h”
typedef struct _exclusive_pair {
union {
int n1;
int n2;
}
} ex_pair

main()
{
Results: 10 10
ex_pair p;
p.n1=1; p.n2=10;
cout << p.n1 << “ “<<p.n2;
}
J.-J. Chen, EE NTUST 2 Array-18
OUTLINE

• C++ Class
• The Array as an Abstract Data Type
• The Polynomial
• Sparse Matrix
• The String

J.-J. Chen, EE NTUST 2 Array-19


ARRAY

• Traditional Array
– Is viewed as a consecutive set of memory locations
– Is a set of ordered pair, i.e., <index,value>
– Provides two standard operations
• Store a value to a given index
• Retrieve a value corresponding to a given index
– Store and retrieve are performed in a constant time
• More robust array
– To avoid out-of-bound access

J.-J. Chen, EE NTUST 2 Array-20


ADT General Array
class GeneralArray{ ADT 2.1
// object: A set of pairs <index,value> where for each value of index in indexSet there
// is a value of type float, IndexSet is a finite ordered set of one or more
// dimensionas, for example, {0, ..., n-1} for one dimension,
//{(0,0),(0,1),(0,2),(1,0),(1,1),(1,2),(2,0),(2,1),(2,2)} for two dimensions, etc.
public:
GeneralArray(int j, RangeList list, float initValue=defaultValue);
//The constructor GeneralArray creates a j dimensional array of floats; the range
// of the kth dimension is given by the kth element of list. For each index i in the
// index set, insert <i, initValue> into the array.
float Retrieve(index i);
// if (i is in the index set of the array) return the float associated with i
// in the array; else signal an error
void Store(index i, float x);
// if (i is in the index set of the array) delete any pair of the form <i, y> present
// in the array and insert the new pair <i, x>; else signal an error.
}; // end of GeneralArray

J.-J. Chen, EE NTUST 2 Array-21


Multi-dimensional Array

• A n-dimensional array
– Is usually implemented as a one-dimensional array
– A mapping mechanism is needed
– Assumption of A[u1][u2]…[un]
• First index range: [p1…q1]
• Second index range:[p2…q2]
• ….
• N-th index range:[pn…qn]
– The total number of elements in this n-dimensional
array is
 (q − p +1)
n
i =1 i i

J.-J. Chen, EE NTUST 2 Array-22


Row Major

• Row Major Order


– is also called lexicographic order
• Example
–A[4..5][2..4][1..2][3..4]
–Total # of elements: 2*3*2*2=24
–Element order
–A[4][2][1][3],A[4][2][1][4],A[4][2][2][3],A[4][2][2][4],
A[4][3][1][3],A[4][3][1][4],A[4][3][2][3],A[4][3][2][4],
A[4][4][1][3],A[4][4][1][4],A[4][4][2][3],A[4][4][2][4],
…….

J.-J. Chen, EE NTUST 2 Array-23


Row Major Array
• Demonstration
– Sequential representation of A[u1]
Array Element A[0] A[1] A[2] … A[i] … A[u1-1]
Address p p+1 p+2 p+i p+u1-1

Col 0 Col 1 Col 2 Col u2 - 1

Row 0
X X X X

Row 1 X X X X

Row u1 - 1
X X X X

u2 u2
elements elements

Row 0 Row 1 Row i Row u1 - 1


i * u2 element

J.-J. Chen, EE NTUST 2 Array-24


Address Mapping

• Formula
– Assume p is the address of A[0][0][0]
– Address for A[i][0][0] = p + i  u2u3
– Address for A[i][j][0] = p + (i  u2u3)+ j  u3
– Address for A[i][j][k] = p + (i  u2u3)+( j  u3 ) + k

A[i1][i2]…[in] p + ija j
(Row major order)
mapped to j =1

where a j = k = j +1 uk , 1  j  n
n

an = 1

J.-J. Chen, EE NTUST 2 Array-25


Address Mapping
Allocate 3d array:
http://stackoverflow.com/questions/10238699/dynamically-allocating-
3d-array

u2
u1

u3

(a) 把三維陣列A[u1][u2][u3]視為u1個二維陣列
i  u 2  u 3 個元素

 

A(0, u 2 , u 3 ) A(1, u 2 , u 3 ) A(i, u 2 , u 3 ) A(u1 − 1, u 2 , u 3 )

(b) 一個三維陣列的循序列主序表示法。每一個二維陣列都用圖2.6的方法來表示。
圖2.7:a[u1][u2][u3]的循序表示法
J.-J. Chen, EE NTUST 2 Array-26
OUTLINE

• C++ Class
• The Array as an Abstract Data Type
• The Polynomial
• Sparse Matrix
• The String

J.-J. Chen, EE NTUST 2 Array-27


ADT of Polynomial
Class Polynomial{ ADT 2.2
// object: p(x) a0 x e0 an x en ;a set of ordered pairs if ei , ai
// where ai Coefficient and ei Exponent
// we assume that Exponent consists of integers 0
public:

Polynomial();
// return the polynomial p(x)=0

Polynomial Add(polynomial poly);


// return the sum of the polynomials *this and poly

Polynomial Mult(polynomial poly);


// return the product of the polynomials *this and poly

float Eval(float f);


// Evaluate the polynomial *this at f and return the result.
}; // end of Polynomial

J.-J. Chen, EE NTUST 2 Array-28


Polynomial Representation(1)

• Fixed-size array representation


private:
int degree; // degree <=MaxDegree
float coef [MaxDegree+1]; // coeff. array

• Example
– Assume that a is a polynomial class object & n < = MaxDegree
– E.g., an xn ++ a1x1 + a0
– Then, a.degree = n and
a.coef [i ] = an −i ,  
0in
• Disadvantage
– Wasteful in its use of computer memory

J.-J. Chen, EE NTUST 2 Array-29


Polynomial Representation(2)
http://stackoverflow.com/questions/23353881/dynamic-array-c-polynomial-class

• Array with dynamic size


private:
int degree;
float *coef ;

• Constructor Polynomial::Polynomial(int d)
{
degree = d;
coef = new float [degree+1]
}
• Advantage
– The size of array can be dynamically determined,
leading to a more efficient memory usage

J.-J. Chen, EE NTUST 2 Array-30


Polynomial Representation(3)

• Sparse polynomial
– E.g., x + 1 → <coef, exp> list →
100
{<1,100>,<1,0>}
• Shared single array is used
– All polynomials, if many in the program, will be put
together as a shared single array
// private data members of Polynomial
class Polynomial; private:
static Term termArray[MaxTerms];
class Term { static int free;
friend Polynomial; int Start, Finish;
private:
float coef ; // coefficient // static data outside class declaration
int exp; // exponent Term Polynomial::termArray[MaxTerms];
} int Polynomial::free=0;
// next free location in termArray
J.-J. Chen, EE NTUST 2 Array-31
Examples: Array for Two Polynomials

• A(x)=2x100+1
– A.Start = 0; A.Finish = 1
• B(x)=x4+10x3+3x2+1
– B.Start=2; B.Finish=5

A.Start A.Finish B.Start B.Finish Free

coef 2 1 1 10 3 1
exp 100 0 4 3 2 0
index 0 1 2 3 4 5 6
A zero polynomial Z(x)=0→ Z.Finish=Z.Start - 1
J.-J. Chen, EE NTUST 2 Array-32
Polynomial Addition
1. Polynomial Polynomial::Add(Polynomial B) Program 2.8
2. //return the sum of A(x)(in *this) and B(x)
3. {
4. Polynomial C; int a=Start; int b=B.Start; C.Start=free; float c;
5. while ((a<=Finish) && (b<=B.Finish))
6. switch (compares(termArray[a].exp,termArray[b].exp)){
7. case '=':
8. c=termArray[a].coef + termArray[b].coef;
9. if(c) NewTerm(c,termArray[a].exp);
10. a++;b++;
11. break;
12. case '<';
13. NewTerm(termArray[b].coef, termArray[b].exp);
14. b++;
15. break;
16. case '>';
17. NewTerm(termArray[a].coef,termArray[a].exp);
18. a++;
19. } //end of switch & while
J.-J. Chen, EE NTUST 2 Array-33
Polynomial Addition
Program 2.8
1 Polynomial Polynomial::Add(Polynomial b)
2 { // 回傳多項式 *this與b的和
3 Polynomial c;
4 int aPos = 0, bPos = 0;
5 while ((aPos < terms) && (bPos < b.terms))
6 if (termArray [aPos].exp = = b.termArray [bPos].exp) {
7 float t = termArray [aPos].coef + b.termArray [bPos].coef;
8 If (t) c.NewTerm (t, termArray [aPos].exp);
9 aPos++; bPos++;
10 }
11 else if (termArray [aPos].exp < b.termArray [bPos].exp) {
12 c.NewTerm (b.termArray [bPos].coef, b.termArray [bPos].exp);
13 bPos++;
14 }
15 else {
16 c.NewTerm (termArray [aPos].coef,termArray [aPos].exp);
17 aPos++;
18 }
19

J.-J. Chen, EE NTUST 2 Array-34


Polynomial Addition
Program 2.8

19 // 把 *this中剩下的項給加進來
20 for ( ; aPos < terms ; aPos++)
21 c.NewTerm (termArray [aPos].coef, termArray [aPos].exp);
22 // 把 b(x) 中剩下的項給加進來
23 for ( ; bPos < b.terms ; bPos++)
24 c.NewTerm (b.termArray [bPos].coef, b.termArray [bPos].exp);
25 return c;
26 }

• When all terms are non-zero, representation 3 uses


about twice as much space as representation 2
• Unless we know that there’s few zero terms,
representation 3 is preferable

J.-J. Chen, EE NTUST 2 Array-35


Adding a new Polynomial Term

• void Polynomial::NewTerm(const float theCoeff, const int theExp)


• { // 在termArray的末端加入一個新項
Program 2.9
• if (terms = = capacity)
• { // 將termArray的容量加倍
• capacity *= 2;
• term * temp = new term[capacity]; // 新陣列
• copy(termArray, termArray + terms, temp);
• delete [ ] termArray ; // 釋放舊的記憶體
• termArray = temp;
• }
• termArray [terms].coef = theCoeff;
• termArray [terms++].exp = theExp;

• } Horner’s method to evaluate a polynomial with value x


http://math.stackexchange.com/questions/49051/using-
horners-method
J.-J. Chen, EE NTUST 2 Array-36
Disadvantage of Representing
Polynomials by Arrays
• Array is used up
– Recycle certain polynomials no longer needed
– A sophisticated compaction routine is required, involving
a lot of data movement
• Another choice
– Use a single array of terms for each polynomial
– Each array is created by using “new”
– This will requires us to know the size of the polynomial
prior to its creation
• A potential trouble to run the addition algorithm twice

J.-J. Chen, EE NTUST 2 Array-37


OUTLINE

• C++ Class
• The Array as an Abstract Data Type
• The Polynomial
• Sparse Matrix
• The String

J.-J. Chen, EE NTUST 2 Array-38


Sparse Matrices

Sparse Matrix
Is a matrix in which most elements are zero

15 0 0 22 0 − 15
− 27 3 4 0 11 3 0 0 0 
 6 82 − 2  
  0 0 0 −6 0 0 
 109 − 64 11   
  0 0 0 0 0 0 
 12 8 9 91 0 0 0 0 0 
 48 27 47   
 0 0 28 0 0 0 

J.-J. Chen, EE NTUST 2 Array-39


How to store Matrix ?

• Two dimensional array


– int A[m][n]
– Could use up huge memory space, e.g., A[5000][5000]

• Memory Space
– Use two-dimensional array for sparse matrix is a big
waste of memory space

J.-J. Chen, EE NTUST 2 Array-40


ADT of Sparse Matrix (ADT 2.3)
class SparseMatrix
{ //objects:A set of triples, <row, column, value>, where row and column are integers and
// from a unique combination; value is also an integer.
public:
SparseMatrix(int MaxRow, int MaxCol);
// the constructor function createsa SparseMatrix that can hold up to MaxItems =
// MaxRow x MaxCol and whose maximum row size is MaxRow & whose
// maximum column size is MaxCol
SparseMatrix Transpose();
// returns the SparseMatrix obtained by interchanging the row and column value of
// every triple in *this
SparseMatrix Add(SparseMatrix b);
// if the dimensionas of a (*this) and b are the same, then the matrix produced by adding
// corresponding items, namely those with identical row & column values is returned
// else error.
SparseMatrix Multiply(SparseMatrix b);
// if number of columns in a (*this) equals number of rows in b then the matrix d
// produced by multiplying a by b according to the formula d[i][j]=
// sum(a[i][k]. b[k][j], where d[i][j] is the (i,j)th element, is returned. k ranges from 0
// to the number of columns in a-1
// else error
};
ADT 2.3 2 Array-41
J.-J. Chen, EE NTUST
Sparse Matrix Representation

• Representation
– Use triple <row, column, value>
– Store triples row by row
– For all triples within a row, their column indices are in ascending
order.
– Must know the number of rows and columns and the number of
nonzero elements
15 0 0 22 0 − 15
0 11 3 0 0 0 

0 0 0 −6 0 0 
 
0 0 0 0 0 0 
91 0 0 0 0 0 
 
 0 0 28 0 0 0 

J.-J. Chen, EE NTUST 2 Array-42


Sparse Matrix Representation
class SparseMatrix; // forward declaration

class MatrixTerm { SparseMatrix


friend class SparseMatrix
private: MatrixTerm
int row, col, value;
MatrixTerm
};
.
class SparseMatrix{
.
public: //member functions
private:
.
int Rows, Cols, Terms; MatrixTerm
MatrixTerm smArray[Max#Terms];
}
SparseMatrix is modeled as
a Linear Array
J.-J. Chen, EE NTUST 2 Array-43
15 0 0 22 0 −15  15 0 0 0 91 0 
0  0 0 0 0 0
11 3 0 0 0  
11

 
0

0 0 −6 0 0 

Sparse Matrix & Its Transpose  0

 22
3
0
0 0 0 28
−6 0 0 0 

0 0 0 0 0 0 
 0 0 0 0 0
91

0
0
0
0 0 0 0 
28 0 0 0 
 A B=AT 
 − 15
0
0 0 0 0 0

The sparse matrix is row-major → ordered by rows,


and, by columns within rows

Original Row Col Value Transposed Row Col Value


smArray[0] 0 0 15 smArray[0] 0 0 15
[1] 0 3 22 [1] 0 4 91
[2] 0 5 -15 [2] 1 1 11
[3] 1 1 11 [3] 2 1 3
[4] 1 2 3 [4] 2 5 28
[5] 2 3 -6 [5] 3 0 22
[6] 4 0 91 [6] 3 2 -6
[7] 5 2 28 [7] 5 0 -15

(0, 3, 22) → (3, 0, 22) after being transposed


J.-J. Chen, EE NTUST 2 Array-44
Transpose a Matrix b=AT
1 SparseMatrix SparseMatrix::Transpose( )
2 { // 回傳*this的轉置矩陣 Program 2.10
3 SparseMatrix b(cols , rows , terms); // b.smArray的容量為 terms
4 if (terms > 0)
5 { // 非零的矩陣
6 int currentB = 0;
7 for (int c = 0 ; c < cols ; c++) // 根據行來轉置
8 for (int i = 0 ; i < terms ; i++)
9 // 尋找並移動在第c行的項
10 if (smArray[i].col = = c)
11 {
12 b.smArray[currentB].row = c;
13 b.smArray[currentB].col = smArray[i].row;
14 b.smArray[currentB++].value = smArray[i].value;
15 }
16 } // if (terms > 0) 結束
17 return b; Time Complexity = O(Cols · Terms)
18 } 2 Array-45
J.-J. Chen, EE NTUST
Transpose a Matrix Faster

• O(terms*columns) time => O(rows*columns2)


– when terms is the order of rows*columns

• A better transpose function (Program 2.11)


1. It first computes how many terms in each columns of matrix A
before transposing to matrix B
2. Then it determines where is the starting point of each row for
matrix B
3. Finally it moves each term from A to B.

J.-J. Chen, EE NTUST 2 Array-46


Transpose a Matrix Faster (1)
1 SparseMatrix SparseMatrix::FastTranspose( ) Program 2.11(a)
2 { // 在O(terms + cols)的時間內回傳 *this的轉置矩陣
3 SparseMatrix b(cols , rows , terms);
4 if (terms > 0)
5 { // 非零的矩陣
6 int *rowSize = new int[cols];
7 int *rowStart = new int[cols];
8 // 計算rowSize[i] = b的第i列之項數
9 fill(rowSize, rowSize + cols, 0); // 初始化 O(columns)
10 for (int i = 0 ; i < terms ; i ++) rowSize[smArray[i].col]++; O(terms)
11 // rowStart[i] = b的第i列之起始位置
12 rowStart[0] = 0;
13 for (int i = 1 ; i < cols ; i++) rowStart[i] = rowStart[i-1] + rowSize[i-1];
O(columns-1)

14

J.-J. Chen, EE NTUST 2 Array-47


Transpose a Matrix Faster (2)
Program 2.11(b)
O(terms) 14 for (int i = 0 ; i < terms ; i++)
15 { // 從 *this 複製到 b
16 int j = rowStart[smArray[i].col];
17 b.smArray[j].row= smArray[i].col;
18 b.smArray[j].col = smArray[i].row;
19 b.smArray[j].value = smArray[i].value;
20 rowStart[smArray[i].col]++;
21 } // end of for
22 delete [ ] rowSize;
23 delete [ ] rowStart;
24 } // end of if
25 return b;
26 }

Time complexity = O(Terms + Columns) ~ O(Terms)


J.-J. Chen, EE NTUST 2 Array-48
Examples of Matrix Transpose (1)

• Step 1:
– Scan Matrix A to construct the RowSize array of AT
1 0 2 3 1 0 0 0
0 0 1 2 0 0 0 4
A=  
Matrix A RowSize array of AT A =
T 
0 0 1 0 2 1 1 0
   
0 4 0 0 3 2 0 0
(row,col,value) 0 1 2 3
0 0 1 → 1 0 0 0
Row0 0 2 2 → 1 0 1 0
0 3 3 → 1 0 1 1
Row1 1 2 1 → 1 0 2 1
1 3 2 → 1 0 2 2
Row2 2 2 1 → 1 0 3 2
Row3 3 1 4 → 1 1 3 2

J.-J. Chen, EE NTUST 2 Array-49


Examples of Matrix Transpose (2)
• Step 2:
– Scan RowSize Array to construct the RowStart array of AT
1 0 0 0
0 0 0 4
RowSize of AT  
2 1 1 0
0 1 2 3  
3 2 0 0
1 1 3 2 AT
0 Row0
1 Row1
RowStart[0]=0;
RowStart[i]=RowStart[i-1]+RowSize[i-1] 2
3 Row2
RowStart of AT 4
0 1 2 3 5 Row3
0 1 2 5 6
J.-J. Chen, EE NTUST 2 Array-50
Examples of Matrix Transpose (3)
1 0 0 0
• Step 3: 0

0 0 4

2 1 1 0
– Move each element of Matrix A to Matrix AT 
3

2 0 0
1 0 2 3 RowStart of AT
0 0 1 2 Matrix A
  Matrix AT 0 1 2 3
0 0 1 0 (row, col, value)
  (row, col, value) 1 1 2 5
0 4 0 0
0 0 1 0 0 1 0 1
1 1 3 5
Row0 0 2 2 1 3 4 1 7
1 1 3 6
0 3 3 2 0 2 2 2
Row1 1 2 1 2 1 1 3 4 1 1 4 6

1 3 2 2 2 1 4 6
1 1 4 7
Row2 2 2 1 3 0 3 5 3
1 1 5 7
Row3 3 1 4 3 1 2 6 5
1 2 5 7
index Fill-in order
J.-J. Chen, EE NTUST 2 Array-51
Principles in Fast Transpose

• Look before you leap

• A stitch (針) beforehand saves nine


及時一針勝過事後九針

• Quick pre-computation of certain


information pay back often

J.-J. Chen, EE NTUST 2 Array-52


Matrix Multiplication(1)

Cij = ( A  B)ij = k Aik  Bkj


Take the transpose of B before multiplication
1 0 2 3 0 1 2 0
0 0 1 2
0

0 1 2
 Matrix A Matrix B 
1

0 0 0 Matrix BT
0 0 1 0  
  0 4 0 0
0 4 0 0
0 0 1 Row0 0 1 1 0 2 1 B.col0
Row0 0 2 2 0 2 2 1 0 1 B.col1
0 3 3 Row1 1 2 1 1 3 4
1 2 1 1 3 2 2 0 2 B.col2
Row1 transpose
1 3 2 Row2 2 0 1 2 1 1
Row2 2 2 1 Row3 3 1 4 3 1 2 B.col3
Row3 3 1 4

J.-J. Chen, EE NTUST 2 Array-53


Matrix Multiplication(2)
0 0 1 0
Computing C00 Matrix BT
1

0 0 4

2 1 0 0
 
Matrix A 1 0 2 3 0
0
1 2 0
(row, col, value)
0 2 0 0
0 0 1 2 0 1 2
(row, col, value) 
0

0 1 0
B 
1

0 0 0 p2 → 0 2 1 B.col0
0 0 1  p1 
0

4 0 0

0

4 0 0
Row0 0 2 2 1 0 1 B.col1

Row1
0 3 3
1 2 1
1 0 2 3  0
0 =2
1 3 4
2 0 2 B.col2
1 3 2 1 2 1 1
Row2 2 2 1
0 3 1 2 B.col3
Row3 3 1 4

while(p1 or p2 not null yet) {


switch(compare(A[p1].col, BT[p2].col) ) {
case ‘<‘: p1++; break;
case ‘=‘: result +=A[p1].value*BT[p2].value;
p1++; p2++; break;
case ‘>’: p2++; break;
}
J.-J. Chen, EE NTUST 2 Array-54
Matrix Multiplication(3)

• Notation
Ann  Bnn
– Ai: the number of non-zero elements in i-th row of A
– Bj: the number of non-zero elements in j-th col. of B (j-th row of BT)

• Complexity Upper Bound


n n n
= O( ( Ai + B j )) = O( n  Ai + Terms _ of _ B)
i =0 j =0 i =0
= O(n • Terms_of_A + n • Terms_of_B)

= O(n • max(Terms_of_A, Terms_of_B) )

J.-J. Chen, EE NTUST 2 Array-55


Disadvantages of representing
Sparse Matrix by Arrays

• Number of terms in a sparse matrix is


variable
– Represent all sparse matrices in one array for efficient
utilization of spaces, rather than using a separate array
for each matrix

J.-J. Chen, EE NTUST 2 Array-56


OUTLINE

• C++ Class
• The Array as an Abstract Data Type
• The Polynomial
• Sparse Matrix
• The String

J.-J. Chen, EE NTUST 2 Array-57


String

• Usually string is represented as a character array.


• General string operations include
– comparison,
– string concatenation,
– copy, insertion,
– string matching,
– printing, etc.

H e l l o W o r l d \0

J.-J. Chen, EE NTUST 2 Array-58


ADT of the String
class string
{ // object: A finite ordered set of zero or more characters
public:
string(char *init, int m);
// constructor that initializes *this to string init of length m
int operator==(String t);
// if(the string represented by *this equals t) return 1 (TRUE)
// else return 0 (FALSE)
int operator!();
// if *this is empty then rturn 1 (TRUE); else return 0 (FALSE)
int Length();
// return the number of characters in *this
string Concate(String t);
// return the string whose elements are those of *this at position i,i+1,...,i+j-1
// if thses are valid positions of *this; otherwise, return the empty string.
string Substr(int i, int j);
// return a string containing j characters of *this at positions i, i+1,…,i+j-1
/ if these are valid positions of *this; otherwise, return the empty string
int Find(String pat);
// return an index i such that pat matches the substring of *this that begins at position i.
// Return -1 if pat is either empty or not a substring of *this
};
J.-J. Chen, EE NTUST 2 Array-59
String Pattern Matching

• Problem
– Finding if a pattern is contained in another string

• Example
– Pattern: “data structure”
– String: “The course identifier of data structure is EE34..”
– Result = 26
– If pattern does not exist in the string, return -1

J.-J. Chen, EE NTUST 2 Array-60


Simple String Pattern Matching (1)
Pattern: data structure (14 characters)
String: data encapsulation is an important concept in data structure
A sliding window

• Comparing the sub-string within the window with the pattern


→ a mismatch at the sixth character
• Slide the window forward by one step

Pattern: data structure (14 characters)


String: data encapsulation is an important concept in data structure

•A mismatch again! Slide the window forward


J.-J. Chen, EE NTUST 2 Array-61
Simple String Pattern Matching (2)
Pattern: data structure (14 characters)
String: data encapsulation is an important concept in data structure
A sliding window

• A match
• Return the starting index of the sliding window = 47

▪Time Complexity
−the worst-case complexity of this algorithm = O (mn)
where m is the length of the pattern
n is the length of the string
▪The window matching is performed for n times and each of them
may take m steps to complete in the worst case

J.-J. Chen, EE NTUST 2 Array-62


Algorithm – Simple Matching
int String:: Find(String pat)
// i is set to -1 if pat does not occur in s (*this)
// otherwise i is set to point to the first position in *this, where pat begins.
{
char *p=pat.str, *s=str;
int i=0; // i is the starting point i is the starting index of the
if (*p && *s) window being compared
while(i <= Length() - pat.Length() )
if(*p++==*s++) { // characters match, get next char in pat & s
if(!*p) return i; // match found End of “pattern” reached
}
else {
i++; s=str+i; p=pat.str; Move window forward by 1
}
return -1; // pat is empty or does not occur in s
} // end of Find

J.-J. Chen, EE NTUST 2 Array-63


Optimal Pattern Matching
Knuth-Morris-Pratt Algorithm
• The problem of simple algorithm
– The sliding window moves forward one step at a time
• Idea
– Can we move the window several steps forward when a
partial match occurs in a window matching ?
Pattern: data structure
String: data encapsulation is an important concept in data structure

failed at 6th characters, a partial match

Can the window leap forward by 6 ?


Pattern: data structure
String: data encapsulation is an important concept in data structure

J.-J. Chen, EE NTUST 2 Array-64


String Pattern Matching

si..si+2 Mismatch occur since si+2 c


s =‘ – a b ? ? ? . . . . ?’ → compare p0 with si+1 ? NO !!
pat = ‘a b c a e c a c a b
We know that si+1=b a, there’s no
Si+4 need to compare p0 with si+1
s =‘ – a b c a ? ? . . . ?’ ➔ Compare p0=a with si+2
pat = ‘a b c a e c a c a b
The search for a match can proceed
p1 by comparing si+4 and the p1

We can determine where in the pat to continue the


search for a match without moving backward in s
J.-J. Chen, EE NTUST 2 Array-65
Failure Function(1)

• Definition
– If p = p0p1….pn-1 is a pattern, then its failure function, f,
is defined as: f(j)=
(1) largest k<j such that p0p1….pk = pj-kpj-k+1….pj
if such a k0 exist
(2) otherwise f(j)= -1;
• Example
a b c a b c a c a b

Target Pattern a b c a b c a c a b
j 0 1 2 3 4 5 6 7 8 9
F(j) -1 -1 -1 0 1 2 3 -1 0 1

J.-J. Chen, EE NTUST 2 Array-66


Failure Function(2)

• Usage
– It decides the leap size after a partial match
• Rule of pattern matching
– If a partial match is found such that
( si-j…si-1 ) = ( p0p1…pj-1) and si  pj,
then matching may be resumed by comparing:
(1) si and pf(j-1)+1 if j0
(2) si+1 and p0 if j=0;
si si does not go backward after a partial mismatch
String: data encapsulation is an important concept in data structure
Pattern: data structure (14 characters)
pj
f(5)=-1 → next character in pattern to be checked
2 Array-67
is p0 &
J.-J.sChen, EE NTUST
i
Example of
using Failure Function

s5

String a b c a b c a b y a c a b
Target pattern a b c a b y a c a b

New p
+1 p5

j 0 1 2 3 4 5 6 7 8 9

f(j) -1 -1 -1 0 1 -1 0 -1 0 1

Next step: comparing s5 with p2,


now the window of string being compared starts from s3

J.-J. Chen, EE NTUST 2 Array-68


Example of using Failure Function

S3
s5

String a b c a b c a b y a c a b
Target pattern a b c a b y a c a b

p2

j 0 1 2 3 4 5 6 7 8 9

f(j) -1 -1 -1 0 1 -1 0 -1 0 1

Next step: comparing s5 with p2,


now the window of string being compared starts from s3
J.-J. Chen, EE NTUST 2 Array-69
Algorithm of FastFind
1. int String::FastFind(string pat) PosS
2. {
abcabcabyacab
3. // Determine if pat is a substring of s
abcabyacab
4. int PosP=0; PosS=0;
5. int LengthP = pat.Length(), LengthS = Length(); PosP
6. while( PosP < LengthP ) && (PosS < LengthS) {
7. if (pat.str[PosP] == s.str[PosS]) { // matched a character
8. PosP++; PosS++;
9. }
10. else // no match
11. if (PosP ==0) PosS++; (1) si and pf(j-1)+1 if j0
12. else PosP = pat.f [ PosP – 1 ] + 1; } (2) si+1 and p0 if j=0;
13. If ( PosP < LengthP ) return(-1);
14. else return (PosS – LengthP); Time = O(LengthS)
15. }

J.-J. Chen, EE NTUST 2 Array-70


Analysis of FastFind

• Time complexity analysis


– Lines 8 & 11 can be executed for a total of at most
LengthS times
– In each iteration, PosS is incremented by 1 & is never
decreased …→.

…→

– As a result, PosP can move right at most LengthS times


– The else clause in line 12 can be executed at most
LengthS times or PosP will become less than 0
– Consequently, the maximum # of iterations of the
while loop is LengthS
➔ the computing time of FastFind is O(lengthS)

J.-J. Chen, EE NTUST 2 Array-71


Computing Failure Function
• BenchMark
– If the failure function can be computed in O(LengthP)
→ then the FastFind has an optimal complexity of
O( LengthP + LengthS )

• Rule f(j)=
 −1 if j = 0
 m
 f ( j − 1) + 1 where m is the least integer k for which p f k (j-1 )+1 = p j

 −1 if there is no k satisfying the above

note that f 1(j) = f(j) and f m(j) = f(f m-1(j)))

J.-J. Chen, EE NTUST 2 Array-72


Examples of Failure Function
Target pattern a b c a b a b c a b c c

j 0 1 2 3 4 5 6 7 8 9 10 11

f(j) -1 -1 -1 0 1 0 1 2 3 4 2 -1

• f(9)=? → fm(8)+1,( p(fm(8)+1)=p(4)=b) = (p(j)=p(9)=b)


found ! → fm(8) + 1 = 4
• f(10)=? → fm(9)+1,( p( fm(9) +1)=p(5)=a)  (p(j)=p(10)=c)
fm(9) = f(fm-1(9)) = f(4), p((f(4)+1)) =p(2)= c =(p(j)= c)
found ! → f(fm-1(9)) + 1 = f(4)+1 =2
• f(11) = ? → fm(10)+1,( p(fm(10)+1)=p(3)=a)  (p(j)=p(11)=c)
fm(10) = f(fm-1(10)) = f(2), p((f(2)+1)) =p(0)= a  c
→ not found, f(11) = -1

J.-J. Chen, EE NTUST 2 Array-73


Algorithm of Failure Function
1. void String::FailureFunction()
2. { // compute the failure function for the pattern p (*this)
3. int LengthP=Length();
4. f[0]= -1;
5. for (int j=1; j<LengthP; j++) // compute f[j]
6. {
p(j) p(fm[j-1]+1) fm[j-1]= f[fm-1(j-1)]
7. int i=f[j-1];
8. while ((*(str+j) != *(str+i+1)) && (i>=0)) i=f[i];
9. if(*(str+j)==*(str+i+1))
10. f[j]=i+1;  −1 if j = 0
 m
11. else f[j]= -1;  f ( j − 1) + 1 where m is the least integer k for which p f (j-1 )+1 = p j
k


12. }  −1 if there is no k satisfying the above

13. } // end of fail


J.-J. Chen, EE NTUST 2 Array-74
Analysis of fail

• Time complexity analysis


– The variable i is either reset to –1 (previous iteration went
through line 11) or reset to a value 1 greater than its terminal
value on the previous iteration (line 10)
– Only LengthP – 1 executions of line 7 are made, value of i
therefore has a total increment of at most LengthP - 1
– It cannot decrease more than LengthP – 1 times
→ the while loop is iterated at most LengthP – 1 times over the
whole algorithm
➔ The computing time of fail is O(LengthP)
Target pattern a b c a b a b c a b c c

j 0 1 2 3 4 5 6 7 8 9 10 11

f(j) -1 -1 -1 0 1 0 1 2 3 4 2 -1

J.-J. Chen, EE NTUST 2 Array-75


Homework #3

• Find the failure function of string:


s1= “ababcdaba”

• Utilize the fastfind procedure to search s1 from


s2 = “abaecabafdababcdabababada”
• Deadline:
Oct. 20, 2017

An interesting demo site:


http://www.enseignement.polytechnique.fr/profs/informatique/Jea
n-Jacques.Levy/00/pc4/strmatch/e.html

J.-J. Chen, EE NTUST 2 Array-76


The End of Chapter 2: Array

The Coming Chapter:

Stacks & Queues

J.-J. Chen, EE NTUST 2 Array-77


Example: Polynomial Evaluation

• Consider the polynomial


P(x) = 4x4 + 7x3 – 2x2 + 3x1 + 6
Suppose that exponentiation is carried out
using multiplications.
• Two ways to evaluate this polynomial are:
Brute force method:
P(x) = 4*x*x*x*x + 7*x*x*x – 2*x*x + 3*x + 6

Horner’s method:
P(x) = (((4*x + 7) * x – 2) * x + 3) * x + 6

J.-J. Chen, EE NTUST 2 Array-78

You might also like