AA 2004/2005¶
Course of Scientific Programming in C++¶
Suggested lectures¶
-
Bruce Eckel’s Free Electronic Books:
-
C++ Annotations
Lessons¶
Lesson of 16/5/2005¶
File: 1.cpp
1/*
2 A multi line comment
3 start with a slash + star
4 end with a star + slash
5 */
6
7// single line comment
8
9// include
10#include <iostream>
11
12/*
13 A program consist in a procedure named "main"
14 with o without arguments
15 */
16
17int // means integer is the
18 // return type of the routine main
19main () // main is the name "fixed" of the program
20 // () contains eventual arguments
21{ // open brace is the beginning of the body of the program
22
23 // cout = character out is the object for the output
24 // cout write to the standard output
25 std::cout << "hello world!\n" ;
26 // << is an operator, that in the case of the object cout means
27 // that the thing on the right is put in the standard output.
28 // the character \n is the newline. There are others special character
29 // \r = is the return character
30 // \t = is the tabulation character
31 // \g = the bell sound
32
33 // first possibility to avoid the use of std::
34 using std::cout ;
35 cout << "cout without std::\r"
36 << "XYZ\n" ;
37
38 // use of endl
39 using namespace std ;
40 cout << "ABC" << endl ; // endl = "\n"
41 // but endl also empty the buffer
42 // endl is equivalent to the compose command
43 cout << "a string" << endl ;
44 cout << "a string" << "\n" << flush ;
45
46 return 0 ;
47} // closing brace is the end of the program
File: 2.cpp
1#include <iostream>
2
3using namespace std ;
4
5int
6main () {
7 int a, b ; // define the integer a and b
8
9 /*
10
11 Other numerical type
12
13 char = character (typically 8 bits)
14 int = integer of the size of the word of the machine
15 (typically 32 bits, 4 byte)
16 float = floting point number (normally 32, bits 4byte)
17 double = double precision floating point number
18 (typically 64 bits, 8 bytes).
19
20 Modificator
21
22 usigned
23 signed
24
25 [ unsigned int usigned char
26 signed int signed char ]
27
28 short
29 long
30
31 short int = small integer (typically 16 bits )
32 long int = large integer (typically 64 bits )
33
34 "short" is a synonimous of "short int"
35 "long" is a synonimous of "long int"
36
37 long double = quadruple precision floating point number
38 (hardware dependent)
39
40 The only sure thing anbout the size
41
42 short <= int <= long <= long long
43 float <= double<= long double
44
45 */
46
47 cout << "Given me a and b " ;
48 // cin is the object dedicated to the input
49 cin >> a >> b ;
50
51 int c = a + b ;
52
53 cout << a << " + " << b << " = " << c << "\n" ;
54
55 return 0 ;
56}
File: 3.cpp
1#include <iostream>
2// I/O standard definitions
3
4#include <iomanip>
5// I/O manipulators
6
7using namespace std ; // load the namespace std to ::
8
9int
10main () {
11 double a, b ; // define the integer a and b
12
13 cout << "Given me a and b " ;
14 // cin is the object dedicated to the input
15 cin >> a >> b ;
16
17 double c = a + b ;
18
19 // set(int n) = reserve n character for the next output
20 cout << setw(20) << a << " + " << b << " = " << c << "\n" ;
21
22 // other manipulators
23 /*
24 setprecision( int ) = set precision in printing number
25 setbase( int ) = set base to print integer 10, 8, 16
26 setfill( char ) = set the filling character
27 dec = print decimal
28 hex = print hexadecimal
29 oct = print octal
30
31 flush = flush buffer
32
33 setw(int) = reserve spaces for next output
34
35 left = align left
36 right = align right
37
38 scientific = print number scientific e.g. 1.234E23
39 floatfield = print number e.g. 123.343
40
41 */
42
43 cout << setw(20) << setfill('*') << a << " + " << b << " = " << c << "\n" ;
44 cout << setprecision(10) << a << " + " << b << " = " << c << "\n" ;
45 cout << a << " + " << b << " = " << c << "\n" ;
46
47 cout << setbase(10) << 123 << " " << setbase(8) << 123 << "\n" ;
48 cout << setbase(10) << 123 << " " << setbase(16) << 123 << "\n" ;
49
50 cout << dec << 123 << " " << oct << 123 << "\n" ;
51 cout << dec << 123 << " " << hex << 123 << "\n" ;
52
53 return 0 ;
54}
File: 4.cpp
1#include <iostream>
2
3using namespace std ;
4
5/*
6 Conditional and loop
7 */
8
9int
10main () {
11 /*
12 if ( condition ) statement ;
13
14 if ( condition ) statement ;
15 else statement ;
16
17 */
18 int a = 1 ;
19 int b = 2 ;
20 if ( a < b ) cout << "a < b is true \n" ;
21 else cout << "a < b is true \n" ;
22
23 if ( a < b ) {
24 int c = a+b ;
25 cout << "a < b is true \n" ;
26 }
27 else {
28 cout << "a < b is true \n" ;
29 }
30
31 /*
32 while ( condition ) statement ;
33 */
34
35 int i = 0 ;
36 while ( ++i < 100 ) cout << i << endl ;
37
38 /* ++i means i = i+1 ;
39 there is also --i that means i = i-1
40 ++i and i++ are different in the sense that
41 int j = i++ ; means that j = i next i = i+1 ;
42 int j = ++i ; means that i = i+1 next j = i ;
43 */
44
45 /*
46 do {
47 instructions ;
48 } while ( condition ) ;
49 */
50
51 i = 0 ;
52 do {
53 i++ ;
54 cout << i << ", " ;
55 } while ( i < 50 ) ;
56 cout << endl ;
57
58 /*
59 for ( init ; condition ; next ) statement ;
60
61 init = is a statement executed ONE time at the beginning
62 condition = is tested at EACH iteration
63 next = is a statement executed at the end of EACH iteration
64 */
65 // int i = 1 ; is an error
66 int sum = 0 ;
67 for ( int i = 1 ; // init
68 i < 100 ;
69 i++ ) {
70 sum += i ; // sum = sum + i ;
71 }
72 cout << "sum = " << sum << endl ;
73 /*
74 short cut form of =
75
76 a OP= b ; means a = a OP b ;
77
78 for example
79
80 a /= b ; ==> a = a / b ;
81 a *= b ; ==> a = a * b ;
82 a |= b ; ==> a = a | b ;
83
84 */
85
86 /*
87 The switch statement
88
89 switch ( int ) {
90 case number:
91
92 break ; // interrupt the switch,
93 // if not present continue to the next case.
94 case number:
95
96 case number:
97
98 default:
99 }
100 */
101
102 int j = -1 ;
103 switch (j) {
104 case 7: cout << "j = 7" << endl ;
105 case -1: cout << "j = -1" << endl ;
106 case 0: cout << "j = 0" << endl ;
107 case 3: cout << "j = 3" << endl ;
108 break ;
109 default: cout << "j = none" << endl ;
110 }
111 return 0 ;
112
113 /*
114 break instruction
115 continue instruction
116
117 for ( ) {
118 ...
119 ...
120 if ( cond ) break ; // interrupt the loop
121 ..
122 ..
123 if ( cond ) continue ; // skip to the next iteration
124 ..
125 ..
126 }
127
128 */
129}
Lesson of 17/5/2005¶
File: 5.cpp
1#include <iostream>
2
3using namespace std ;
4
5int
6main()
7{
8 // comparison operator
9
10 double a = 1 ;
11 double b = 2 ;
12
13 // equality
14 if ( a == b ) { // = is the assign not the comparison sign
15 cout << "a is equal to b\n" ;
16 } else {
17 cout << "a is NOT equal to b\n" ;
18 }
19
20 // not equal
21 if ( a != b ) {
22 cout << "a is NOT equal to b\n" ;
23 } else {
24 cout << "a is equal to b\n" ;
25 }
26
27 // greater
28 if ( a > b ) {
29 cout << "a is greater than b\n" ;
30 } else {
31 cout << "a is NOT greater than b\n" ;
32 }
33
34 // lesser
35 if ( a < b ) {
36 cout << "a is less than b\n" ;
37 } else {
38 cout << "a is NOT less than b\n" ;
39 }
40
41 // greater or equal
42 if ( a >= b ) { // => is not a comparison operator
43 cout << "a is greater or equal than b\n" ;
44 } else {
45 cout << "a is NOT greater or equal than b\n" ;
46 }
47
48 // lesser or equal
49 if ( a <= b ) { // =< is not a comparison operator
50 cout << "a is less or equal than b\n" ;
51 } else {
52 cout << "a is NOT less or equal than b\n" ;
53 }
54
55 // BOOLEAN
56 double c = 3 ;
57 if ( a == b || b == c ) ; // || is the OR operator
58 if ( a == b && b == c ) ; // && is the AND operator
59
60 // using boolean type
61 bool eq = a == b ; // eq takes the values "true" or "false"
62 bool neq = b != c ;
63 if ( eq || neq ) ;
64
65 bool bc = true ;
66 bool ac = false ;
67
68 // loop with the use of boolean
69 bool cont = true ;
70 int i = 1 ;
71 while ( cont ) {
72 cout << i << endl ;
73 cont = i < 100 ;
74 ++i ;
75 }
76
77 // boolean arithmetic
78 {
79 bool a, b, c, d, e ;
80 a = true ;
81 b = true ;
82 c = false ;
83 d = false ;
84 e = false ;
85
86 a = (b && c) || e ; // (b AND c) OR e
87 b = ! c ; // negation
88 }
89
90 return 0 ;
91}
File: 6.cpp
1#include <iostream>
2#include <cmath>
3
4/*
5 most important include
6
7 iostream
8 fstream
9 iomanip
10 cmath
11 cstblib
12
13 from standard template library
14
15 string
16 vector
17
18*/
19
20using namespace std ;
21
22typedef long double value_type ;
23// make value_type an alias of long double
24
25typedef int index_type ;
26// make index_type an alias of int
27
28int
29main()
30{
31 // example the use the trapezoidal rule to
32 // compute the integral of f(x)=1+sin(x)
33 // using 100 intervals
34
35 value_type a = 1 ;
36 value_type b = 10 ;
37 index_type n = 100 ;
38
39 value_type fa = (1+sin(a)) ;
40 value_type fb = (1+sin(b)) ;
41 value_type h = (b-a) / n ;
42
43 value_type res = (fa+fb)*h/2 ;
44 for ( index_type i = 1 ; i < n ; ++i ) {
45 value_type xi = a + i*h ;
46 value_type fi = (1+sin(xi)) ;
47 res += h * fi ;
48 }
49
50 cout << "The approximate integral is = " << res << "\n" ;
51 return 0 ;
52}
File: 7.cpp
1#include <iostream>
2#include <cmath>
3
4using namespace std ;
5
6typedef long double value_type ;
7// make value_type an alias of long double
8
9typedef int index_type ;
10// make index_type an alias of int
11
12// declaration of fun
13value_type fun( value_type x ) ;
14
15int
16main()
17{
18 // example the use the trapezoidal rule to
19 // compute the integral of f(x)=1+sin(x)
20 // using 100 intervals
21
22 value_type a = 1 ;
23 value_type b = 10 ;
24 index_type n = 100 ;
25
26 value_type fa = fun(a) ;
27 value_type fb = fun(b) ;
28 value_type h = (b-a) / n ;
29
30 value_type res = (fa+fb)*h/2 ;
31 for ( index_type i = 1 ; i < n ; ++i ) {
32 value_type xi = a + i*h ;
33 value_type fi = fun(xi) ;
34 res += h * fi ;
35 }
36
37 cout << "The approximate integral is = " << res << "\n" ;
38 return 0 ;
39}
40
41// definition of fun
42value_type // return value of the function
43fun( value_type x ) { // fun is the name of the function
44 return 1+sin(x); // x is one argument
45}
File: 8.1.cpp
1#include <iostream>
2#include <cmath>
3
4using namespace std ;
5
6typedef long double value_type ;
7// make value_type an alias of long double
8
9typedef int index_type ;
10// make index_type an alias of int
11
12// declaration of fun
13value_type fun( value_type x ) ;
14
15int
16main()
17{
18 // example the use the trapezoidal rule to
19 // compute the integral of f(x)=1+sin(x)
20 // using 100 intervals
21
22 value_type a = 1 ;
23 value_type b = 10 ;
24 index_type n = 100 ;
25
26 value_type fa = fun(a) ;
27 value_type fb = fun(b) ;
28 value_type h = (b-a) / n ;
29
30 value_type res = (fa+fb)*h/2 ;
31 for ( index_type i = 1 ; i < n ; ++i ) {
32 value_type xi = a + i*h ;
33 value_type fi = fun(xi) ;
34 res += h * fi ;
35 }
36
37 cout << "The approximate integral is = " << res << "\n" ;
38 return 0 ;
39}
File: 8.2.cpp
1#include <iostream>
2#include <cmath>
3
4using namespace std ;
5
6typedef long double value_type ;
7// make value_type an alias of long double
8
9typedef int index_type ;
10// make index_type an alias of int
11
12// declaration of fun
13value_type fun( value_type x ) ;
14
15// definition of fun
16value_type // return value of the function
17fun( value_type x ) { // fun is the name of the function
18 return 2+sin(x); // x is one argument
19}
File: 9.1.cpp
1#include "9.h"
2
3int
4main()
5{
6 // example the use the trapezoidal rule to
7 // compute the integral of f(x)=1+sin(x)
8 // using 100 intervals
9
10 value_type a = 1 ;
11 value_type b = 10 ;
12 index_type n = 100 ;
13
14 value_type fa = fun(a) ;
15 value_type fb = fun(b) ;
16 value_type h = (b-a) / n ;
17
18 value_type res = (fa+fb)*h/2 ;
19 for ( index_type i = 1 ; i < n ; ++i ) {
20 value_type xi = a + i*h ;
21 value_type fi = fun(xi) ;
22 res += h * fi ;
23 }
24
25 cout << "The approximate integral is = " << res << "\n" ;
26 return 0 ;
27}
File: 9.2.cpp
1#include "9.h"
2
3// definition of fun
4value_type // return value of the function
5fun( value_type x ) { // fun is the name of the function
6 return 2+sin(x); // x is one argument
7}
File: 9.h
1#include <iostream>
2#include <cmath>
3
4using namespace std ;
5
6typedef double value_type ;
7// make value_type an alias of double
8
9typedef int index_type ;
10// make index_type an alias of int
11
12// declaration of fun
13value_type fun( value_type x ) ;
File: 10.1.cpp
1#include "10.h"
2#include <iomanip>
3
4value_type valabs( value_type x ) ;
5
6int
7main() {
8 // solving f(x) = 0 by Newton method
9 value_type x = 0 ;
10 value_type epsilon = 1E-6 ;
11 for ( index_type i = 1 ; i < 100 ; ++i ) {
12 value_type f = fun(x) ;
13 if ( valabs(f) < epsilon ) break ; // interrupt the loop
14 value_type f_1 = fun_1(x) ;
15 x = x - f/f_1 ;
16 cout << "iter = " << setw(2) << i
17 << " x = " << setw(10) << x
18 << " residual = " << f << "\n" ;
19 }
20 cout << "result x = " << x << "\n" ;
21}
22
23value_type
24valabs( value_type x ) {
25 return x > 0 ? x : -x ;
26}
File: 10.2.cpp
1#include "10.h"
2
3value_type
4fun(value_type x) {
5 return pow(x-1,2) ; // (x-1)*(x-1)
6}
7
8value_type
9fun_1(value_type x) {
10 return 2*(x-1) ;
11}
File: 10.h
1#include <iostream>
2#include <cmath>
3
4using namespace std ;
5
6typedef double value_type ;
7// make value_type an alias of double
8
9typedef int index_type ;
10// make index_type an alias of int
11
12// declaration of fun
13value_type fun( value_type x ) ;
14
15// declaration of fun_1
16value_type fun_1( value_type x ) ;
File: 11.cpp
1#include "11.h"
2#include <iomanip>
3
4// include again 11.h
5#include "11.h"
6
7value_type valabs( value_type x ) ;
8
9int
10main () {
11 // solving f(x) = 0 by newton method
12 value_type x = 0 ;
13 value_type epsilon = 1E-6 ;
14 for ( index_type i = 1 ; i < 100 ; ++i ) {
15 value_type f = fun(x) ;
16 if ( valabs( f ) < epsilon ) break ;
17 value_type f_1 = fun_1(x) ;
18 x = x - f/f_1 ;
19 cout << "iter = " << setw(2) << i
20 << " x = " << setw(10) << x
21 << " residual = " << f << "\n" ;
22 }
23 cout << " result x = " << x << "\n" ;
24}
File: 11.h
1#ifndef ELEVEN_H
2#define ELEVEN_H
3
4#include <iostream>
5#include <cmath>
6
7using namespace std ;
8
9typedef double value_type ;
10// make value_type an alias of double
11
12typedef int index_type ;
13// make index_type an alias of int
14
15inline
16value_type
17fun(value_type x) {
18 return pow(x-1,2) ; // (x-1)*(x-1)
19}
20
21inline
22value_type
23fun_1(value_type x) {
24 return 2*(x-1) ;
25}
26
27inline
28value_type
29valabs( value_type x ) {
30 return x > 0 ? x : -x ;
31}
32
33#endif
File: 12.cpp
1#include <iomanip>
2#include <string>
3
4using namespace std ;
5
6/*
7 Introduction to struct
8
9 want to collect
10
11 first name
12 second name
13 age
14 nationality
15 weight
16 hair
17 driving licence
18
19*/
20
21typedef double value_type ;
22typedef int index_type ;
23
24struct record {
25 string first_name ;
26 string second_name ;
27 index_type age ;
28 string nationality ;
29 value_type weight ;
30 string hair_color ;
31 bool have_a_driving_licence ;
32} ;
33
34int
35main () {
36 struct record a ;
37
38 a . first_name = "Pippo" ;
39 a . second_name = "Pluto" ;
40 a . age = 1204 ;
41 a . have_a_driving_licence = true ;
42
43 // Define and initialize
44 struct record b = {
45 "Pluto",
46 "Dog",
47 1204,
48 "Topolinia",
49 256,
50 "Red",
51 true
52 } ;
53
54 typedef struct record Record ;
55
56 Record c ;
57
58}
Lesson of 18/5/2005¶
File: 13.cpp
1#include <iostream>
2#include <iomanip>
3
4using namespace std ;
5
6typedef double value_type ;
7typedef int index_type ;
8
9// vec is a pointer to memory allocated
10// with 100 value_type
11
12value_type vec[100] ;
13
14int
15main() {
16 /*
17 to access the elements of vec we use
18 the operator [ ], and the index run
19 from 0 to dim-1 (here dim = 100)
20 */
21
22 vec[1] ; // is the second element
23 vec[99] ; // is the last element
24
25 for ( index_type i = 0 ; i < 100 ; ++i )
26 vec[i] = i * i ;
27
28 value_type * p_vec ; // is a pointer to value_type things
29 p_vec = vec ; // p_vec point to the first value of
30 // the vector vec
31
32 // NO vec = p_vec ; vec is not assignable
33
34 p_vec = & vec[0] ; // is equivalent to p_vec = vec
35
36 cout << "& vec[0] = " << &vec[0] << " ==> "
37 << (long)&vec[0]<< "\n"
38 << " p_vec = " << p_vec << " ==> "
39 << (long)p_vec << "\n" ;
40
41 // (long) is a "casting" operator, reinterprets
42 // p_vec (address) as a long integer.
43
44 cout << "vec[0] = " << vec[0] << "\n"
45 << "*p_vec = " << *p_vec << "\n" ;
46 // * is the deference operator:
47 // p_vec contains the address of a value_type value
48 // *p_vec is the value_type value at the address p_vec
49
50
51 /*
52 pointer ca be assigned, incremented,
53 subtracted, ...
54 some example
55 */
56
57 p_vec = & vec[11] ; // & estract the address from an lvalue
58
59 cout << "vec[11] = " << vec[11] << "\n"
60 << "*p_vec = " << *p_vec << "\n" ;
61
62 cout << "& vec[11] = " << &vec[11] << "\n"
63 << " p_vec = " << p_vec << "\n" ;
64
65 /*
66 Equivalent access with the * operator
67 */
68
69 // vec[13] is equalent to *(vec+13)
70 cout << "vec[13] = " << vec[13]
71 << " *(vec+13) = " << *(vec+13) << "\n" ;
72
73 //the address vec+13 is:
74 // the address of vec + 13 * sizeof(value_type) bytes
75
76 // assign a pointer to a translated value
77 p_vec = vec + 14 ;
78 cout << "vec[14] = " << vec[14]
79 << " *p_vec = " << *p_vec << "\n" ;
80
81 /*
82 Operation with pointers
83 */
84
85 // loop with pointers
86
87 // old loop
88 //for ( index_type i = 0 ; i < 100 ; ++i )
89 // vec[i] = 0 ;
90 for ( p_vec = vec ; p_vec < vec + 100 ; ++p_vec )
91 *p_vec = 0 ;
92
93 // another way
94 for ( p_vec = vec ; p_vec < vec + 100 ; )
95 *p_vec++ = 0 ;
96
97 // another way again
98 p_vec = vec ;
99 while ( p_vec < vec + 100 ) *p_vec++ = 0 ;
100
101 // distance between pointer
102 p_vec = &vec[11] ;
103 cout << "p_vec - vec = " << p_vec - vec << "\n" ;
104 cout << "(short*) p_vec - (short*) vec = "
105 << (short*) p_vec - (short*) vec << "\n" ;
106
107 // the sizeof
108 cout << "sizeof(value_type) = " << sizeof(value_type) << "\n"
109 << "sizeof(short) = " << sizeof(short) << "\n" ;
110}
File: 14.cpp
1#include <iostream>
2#include <iomanip>
3
4using namespace std ;
5
6typedef double value_type ;
7typedef int index_type ;
8
9// vec is a pointer to memory allocated
10// with 100 value_type
11
12// declare and initialize
13value_type avec[10] = { 1,2,3,4,5,6,7,8,9,10 } ;
14
15// declare and initialize, infer the size by the
16// initalization list
17value_type bvec[] = { 1,2,3,4,5,6,7,8,9,10 } ;
18
19struct point {
20 value_type x ;
21 value_type y ;
22 value_type z ;
23} ;
24
25typedef struct point Point ;
26
27// collapsing the previous two definition as
28
29typedef struct {
30 value_type x ;
31 value_type y ;
32 value_type z ;
33} point3d ;
34
35int
36main() {
37 value_type * cvec ;
38
39 // use dynamic allocation
40 cvec = new value_type [10] ;
41 // new is the allocator operator
42 // value_type is the type I am allocating
43 // [10] is the number of cell allocated by new
44
45 // YES cvec = bvec + 100 ;
46 // NO bvec = cvec + 100 ;
47
48 struct point * old_pnts ;
49 point3d * pnts ;
50
51 old_pnts = new struct point [100] ;
52 old_pnts = new Point [100] ;
53 pnts = new point3d [100] ;
54
55 // access to the x of the second element:
56 pnts[1] . x ; // first get the first element then
57 // access by . operator
58 (*(pnts+1)) . x ;
59 (pnts+1) -> x ;
60
61 for ( index_type i = 0 ; i < 100 ; ++i ) {
62 pnts[i] . x = 1 ;
63 pnts[i] . y = i ;
64 pnts[i] . z = -3 ;
65 // another equivalent possibility
66 point3d * p = pnts + i ;
67 p -> x = 1 ;
68 p -> y = i ;
69 p -> z = -3 ;
70 }
71
72 for ( index_type i = 0 ; i < 10 ; ++i )
73 cvec[i] = avec[i] + bvec[i] ;
74
75 // freeing memory operator is delete:
76 delete [] cvec ;
77 // delete is the deletion operator
78 // [] mean that I am deallocating a vector
79 // cvec is the idetifier of the pointer allocated
80}
File: 15.cpp
1#include <iostream>
2#include <iomanip>
3#include <cmath>
4
5using namespace std ;
6
7typedef double value_type ;
8typedef int index_type ;
9
10typedef struct {
11 value_type x, y, z ;
12} point3d ;
13
14value_type
15norm( point3d const p ) { // p is passed by VALUE!
16 return sqrt( p.x*p.x +
17 p.y*p.y +
18 p.z*p.z ) ;
19}
20
21value_type
22norm_addr( point3d const * p_addr ) { // p is passed by ADDRESS!
23 p_addr = p_addr + 1 ;
24 p_addr = p_addr - 1 ;
25 return sqrt( p_addr -> x * p_addr -> x +
26 p_addr -> y * p_addr -> y +
27 p_addr -> z * p_addr -> z ) ;
28}
29
30value_type
31norm_addr_1( point3d const * const p_addr ) { // p is passed by ADDRESS!
32 // NO p_addr = p_addr + 1 ; pointer cannot be modified
33 // NO p_addr = p_addr - 1 ;
34 return sqrt( p_addr -> x * p_addr -> x +
35 p_addr -> y * p_addr -> y +
36 p_addr -> z * p_addr -> z ) ;
37}
38
39value_type
40norm_addr_2( point3d * const p_addr ) { // p is passed by ADDRESS!
41 // NO p_addr = p_addr + 1 ; pointer cannot be modified
42 // NO p_addr = p_addr - 1 ;
43 // YES p_addr -> x = 2 ; thing pointed can be modified
44 return sqrt( p_addr -> x * p_addr -> x +
45 p_addr -> y * p_addr -> y +
46 p_addr -> z * p_addr -> z ) ;
47}
48
49value_type
50norm_ref( point3d const & p_ref ) { // p is passed by REFERENCE!
51 return sqrt( p_ref . x * p_ref . x +
52 p_ref . y * p_ref . y +
53 p_ref . z * p_ref . z ) ;
54}
55
56// modification of p_ref
57value_type
58norm_ref_modify( point3d & p_ref ) { // p is passed by REFERENCE!
59 value_type res = sqrt( p_ref . x * p_ref . x +
60 p_ref . y * p_ref . y +
61 p_ref . z * p_ref . z ) ;
62 p_ref . z = 0 ;
63 return res ;
64}
65
66
67int
68main() {
69 point3d pt ;
70
71 pt . x = 1 ;
72 pt . y = 2 ;
73 pt . z = 3 ;
74
75 cout << " norm_ref_modify = " << norm_ref_modify( pt ) << "\n" ;
76 cout << " norm = " << norm( pt ) << "\n" ;
77 cout << " norm_addr = " << norm_addr( & pt ) << "\n" ;
78 cout << " norm_ref = " << norm_ref( pt ) << "\n" ;
79
80 point3d volatile * p_pt = & pt ;
81 // some operation
82 // you cannot assume that pt is unchanged
83
84}
Lesson of 23/5/2005¶
File: 16.1.cpp
1#include "16.h"
2
3namespace newton_solver_2d {
4
5 // F(x) = / x0 - x1 \
6 // | |
7 // \ x0**2 + x1**3 - 2 /
8 void
9 F( vec2 const & x, vec2 & Fx ) {
10 Fx[0] = x[0] - x[1] ;
11 Fx[1] = x[0]*x[0] - x[1]*x[1]*x[1] - 2 ;
12 // Fx[1] = pow(x[0],2) - pow(x[1],3) -2 ;
13 }
14
15 // JFx[row][column]
16 void JF( vec2 const & x, mat2 & JFx ) {
17 JFx[0][0] = 1 ; // DF[0]/Dx[0]
18 JFx[0][1] = -1 ; // DF[0]/Dx[1]
19 JFx[1][0] = 2*x[0] ; // DF[1]/Dx[0]
20 JFx[1][1] = -3*x[1]*x[1] ; // DF[1]/Dx[1]
21 }
22
23 /*
24 Small 2x2 linear solver
25 */
26
27 bool
28 linear_solver( mat2 const & A, // coefficients matrix
29 vec2 const & b, // r.h.s
30 vec2 & x // the solution of the linear system
31 ) {
32 // Using Cramer rule
33
34 value_type det = A[0][0] * A[1][1] - A[1][0] * A[0][1] ;
35 if ( det == 0 ) return false ;
36
37 x[0] = ( b[0] * A[1][1] - b[1] * A[0][1] ) / det ;
38 x[1] = ( A[0][0] * b[1] - A[1][0] * b[0] ) / det ;
39
40 return true ;
41 }
42
43 /*
44 Newton scheme
45 -1
46 x = x - JF(x ) F(x )
47 n+1 n n n
48
49 the implementation:
50
51 SOLVE: JF(x ) h = F(x )
52 n n
53
54 UPDATE: x = x + h
55 n+1 n
56 */
57 bool
58 solver( vec2 const & x0,
59 F_type * pF,
60 JF_type * pJF,
61 index_type const n,
62 value_type const & tol,
63 vec2 & x
64 ) {
65
66 // set x to the initial value
67 x[0] = x0[0] ;
68 x[1] = x0[1] ;
69
70 for ( index_type i = 0 ; i < n ; ++i ) {
71 vec2 f, h ;
72 mat2 jf ;
73 // perform a Newton step
74 // substep 1: compute F(x)
75 (*pF)(x,f) ; // shortcut borrowed for C syntax ==> pF(x,f) ;
76 // substep 2: compute JF(x)
77 (*pJF)(x,jf) ; // shortcut borrowed for C syntax ==> pJF(x,jf) ;
78 // substep 3: compute the correction h = JF(x)^(-1)F(x)
79 bool ok = linear_solver(jf, f, h) ;
80 if ( !ok ) return false ;
81 // substep 4: update x
82 x[0] -= h[0] ;
83 x[1] -= h[1] ;
84 // check for the stopping criteria
85 value_type res = sqrt( h[0]*h[0]+h[1]*h[1] ) ;
86 if ( res <= tol ) return true ;
87 }
88 return false ;
89 }
90}
File: 16.2.cpp
1#include "16.h"
2
3int
4main() {
5 using newton_solver_2d::vec2 ;
6 using newton_solver_2d::F ;
7 using newton_solver_2d::JF ;
8 using newton_solver_2d::solver ;
9 using namespace std ;
10
11 vec2 x0, x ;
12
13 x0[0] = 1 ;
14 x0[1] = 1 ;
15 solver( x0, F, JF, 100, 1E-6, x ) ;
16
17 cout << "The solution is x = [ "
18 << x[0] << ", " << x[1] << "]\n" ;
19}
File: 16.h
1// standard trick for only one time inclusion
2#ifndef SIXTEEN_H
3#define SIXTEEN_H
4
5#include <iostream>
6#include <iomanip>
7#include <cmath>
8
9namespace newton_solver_2d {
10 using namespace std ;
11
12 // set the value_type to double,
13 // value_type is the generic name for "number"
14 // (non integer)type
15 typedef double value_type ;
16
17 // set the index_type to int,
18 // index_type is the generic name for "integer" type
19 typedef int index_type ;
20
21 // define vec2 as a name for the vector with 2 components
22 typedef value_type vec2[2] ; // value_type a[2] ; ==> vec2 a ;
23
24 // define mat2 as a name for the matrix 2x2
25 typedef value_type mat2[2][2] ; // value_type a[2][2] ; ==> mat2 a ;
26
27 // an equivalent definition
28 // typedef vec2 mat2[2] ;
29
30 /*
31 now we set the definition (prototipe)
32 of the functions
33 */
34
35 /*
36 This methos is not correct:
37 vec2
38 fun( vec2 x ) {
39 vec2 res ;
40 res[0] = .... ;
41 res[1] = .... ;
42 return res ;
43 }
44
45 return res ; // return the pointer to a temporary
46 */
47
48 // prototype of the non-linear system
49 extern void F( vec2 const & x, vec2 & Fx ) ;
50
51 // prototype of the Jacobian of the non-linear system
52 extern void JF( vec2 const & x, mat2 & JFx ) ;
53
54 /*
55 extern = means that the bodies of the functions
56 are somewhere else.
57 */
58
59 // prototype for the solver
60
61 extern
62 bool // return true = if the solution was found
63 solver( vec2 const & x0,
64 // the starting point of the Newton scheme
65 void (*pF) ( vec2 const & x, vec2 & Fx ),
66 // pF is a pointer to the function
67 void (*pJF) ( vec2 const & x, mat2 & JFx ),
68 // pF is a pointer to the jacobian function
69 index_type const n,
70 // n is the maximum number of iteration allowed
71 value_type const & tol,
72 // tolerance for the stopping critertia
73 vec2 & x
74 // x contains the computed solution
75 ) ;
76
77 /*
78 A less difficult to read definition can be
79 obtained by splitting the prototype definition
80 as follows
81 */
82
83 typedef void F_type ( vec2 const &, vec2 &) ;
84 typedef void JF_type ( vec2 const &, mat2 &) ;
85
86 extern
87 bool
88 solver( vec2 const & x0,
89 F_type * pF,
90 JF_type * pJF,
91 index_type const n,
92 value_type const & tol,
93 vec2 & x
94 ) ;
95}
96
97#endif
File: 17.1.cpp
1#include "17.h"
2
3namespace newton_solver_2d {
4
5 // F(x) = / x0 - x1 \
6 // | |
7 // \ x0**2 + x1**3 - 2 /
8 vec2
9 F( vec2 const & in ) {
10 vec2 Fx ;
11 Fx.c1 = in.c1 - in.c2 ;
12 Fx.c2 = in.c1*in.c1 - in.c2*in.c2*in.c2 - 2 ;
13 return Fx ;
14 }
15
16 //
17 mat2x2
18 JF( vec2 const & in ) {
19 mat2x2 JFx ;
20 JFx.A11 = 1 ; // DF[0]/Dx[0]
21 JFx.A12 = -1 ; // DF[0]/Dx[1]
22 JFx.A21 = 2*in.c1 ; // DF[1]/Dx[0]
23 JFx.A22 = -3*in.c2*in.c2 ; // DF[1]/Dx[1]
24 return JFx ;
25 }
26
27 /*
28 Small 2x2 linear solver
29 */
30
31 bool
32 linear_solver( mat2x2 const & A, // coefficients matrix
33 vec2 const & b, // r.h.s
34 vec2 & x // the solution of the linear system
35 ) {
36 // Using Cramer rule
37
38 value_type det = A.A11 * A.A22 - A.A21 * A.A12 ;
39 if ( det == 0 ) return false ;
40
41 x.c1 = ( b.c1 * A.A22 - b.c2 * A.A12 ) / det ;
42 x.c2 = ( A.A11 * b.c2 - A.A21 * b.c1 ) / det ;
43
44 return true ;
45 }
46
47 /*
48 Newton scheme
49 -1
50 x = x - JF(x ) F(x )
51 n+1 n n n
52
53 the implementation:
54
55 SOLVE: JF(x ) h = F(x )
56 n n
57
58 UPDATE: x = x + h
59 n+1 n
60 */
61 bool
62 solver( vec2 const & x0,
63 F_type * pF,
64 JF_type * pJF,
65 index_type const n,
66 value_type const & tol,
67 vec2 & x
68 ) {
69
70 // set x to the initial value
71 x = x0 ; // not reccomended
72
73 for ( index_type i = 0 ; i < n ; ++i ) {
74 vec2 f, h ;
75 mat2x2 jf ;
76 // perform a Newton step
77 // substep 1: compute F(x)
78 f = (*pF)(x) ; // shortcut borrowed for C syntax ==> pF(x) ;
79 // substep 2: compute JF(x)
80 jf = (*pJF)(x) ; // shortcut borrowed for C syntax ==> pJF(x) ;
81 // substep 3: compute the correction h = JF(x)^(-1)F(x)
82 bool ok = linear_solver(jf, f, h) ;
83 if ( !ok ) return false ;
84 // substep 4: update x
85 x.c1 -= h.c1 ;
86 x.c2 -= h.c2 ;
87 // check for the stopping criteria
88 value_type res = sqrt( h.c1*h.c1+h.c2*h.c2 ) ;
89 if ( res <= tol ) return true ;
90 }
91 return false ;
92 }
93}
File: 17.2.cpp
1#include "17.h"
2
3int
4main() {
5 using newton_solver_2d::vec2 ;
6 using newton_solver_2d::F ;
7 using newton_solver_2d::JF ;
8 using newton_solver_2d::solver ;
9 using namespace std ;
10
11 vec2 x0, x ;
12
13 x0.c1 = 1 ;
14 x0.c2 = 1 ;
15 solver( x0, F, JF, 100, 1E-6, x ) ;
16
17 cout << "The solution is x = [ "
18 << x.c1 << ", " << x.c2 << "]\n" ;
19}
File: 17.h
1// standard trick for only one time inclusion
2#ifndef SEVENTEEN_H
3#define SEVENTEEN_H
4
5#include <iostream>
6#include <iomanip>
7#include <cmath>
8
9namespace newton_solver_2d {
10 using namespace std ;
11
12 // set the value_type to double,
13 // value_type is the generic name for "number"
14 // (non integer)type
15 typedef double value_type ;
16
17 // set the index_type to int,
18 // index_type is the generic name for "integer" type
19 typedef int index_type ;
20
21 typedef struct {
22 value_type c1 ; // component one
23 value_type c2 ; // component two
24 } vec2 ;
25
26 typedef struct {
27 value_type A11 ;
28 value_type A12 ;
29 value_type A21 ;
30 value_type A22 ;
31 } mat2x2 ;
32
33 // an equivalent definition
34 // typedef vec2 mat2[2] ;
35
36 /*
37 now we set the definition (prototipe)
38 of the functions
39 */
40
41 // prototype of the non-linear system
42 extern vec2 F( vec2 const & in ) ;
43
44 // prototype of the Jacobian of the non-linear system
45 extern mat2x2 JF( vec2 const & in ) ;
46
47 // prototype for the solver
48
49 extern
50 bool // return true = if the solution was found
51 solver( vec2 const & x0,
52 // the starting point of the Newton scheme
53 vec2 (*pF) ( vec2 const & x ),
54 // pF is a pointer to the function
55 mat2x2 (*pJF) ( vec2 const & x ),
56 // pF is a pointer to the jacobian function
57 index_type const n,
58 // n is the maximum number of iteration allowed
59 value_type const & tol,
60 // tolerance for the stopping critertia
61 vec2 & x
62 // x contains the computed solution
63 ) ;
64
65 /*
66 A less difficult to read definition can be
67 obtained by splitting the prototype definition
68 as follows
69 */
70
71 typedef vec2 F_type ( vec2 const & ) ;
72 typedef mat2x2 JF_type ( vec2 const & ) ;
73
74 extern
75 bool
76 solver( vec2 const & x0,
77 F_type * pF,
78 JF_type * pJF,
79 index_type const n,
80 value_type const & tol,
81 vec2 & x
82 ) ;
83}
84
85#endif
Lesson of 24/5/2005¶
File: 18.1.cpp
1#include "18.h"
2
3namespace newton_solver {
4
5 /*
6 Small 2x2 linear solver
7 */
8
9 bool
10 linear_solver( mat const & A, // coefficients matrix
11 vec const & b, // r.h.s
12 vec & x // the solution of the linear system
13 ) {
14 // Using Cramer rule
15 value_type det = A.values[0][0] * A.values[1][1]
16 - A.values[1][0] * A.values[0][1] ;
17 if ( det == 0 ) return false ;
18
19 x.values[0] = ( b.values[0] * A.values[1][1]
20 - b.values[1] * A.values[0][1] ) / det ;
21 x.values[1] = ( A.values[0][0] * b.values[1]
22 - A.values[1][0] * b.values[0] ) / det ;
23
24 return true ;
25 }
26
27 /*
28 Newton scheme
29 -1
30 x = x - JF(x ) F(x )
31 n+1 n n n
32
33 the implementation:
34
35 SOLVE: JF(x ) h = F(x )
36 n n
37
38 UPDATE: x = x + h
39 n+1 n
40 */
41 bool
42 solver( vec const & x0,
43 F_type * pF,
44 JF_type * pJF,
45 index_type const n,
46 value_type const & tol,
47 vec & x
48 ) {
49
50 // set x to the initial value
51 x = x0 ; // not reccomended
52
53 for ( index_type i = 0 ; i < n ; ++i ) {
54 vec f, h ;
55 mat jf ;
56 // perform a Newton step
57 // substep 1: compute F(x)
58 f = pF(x) ;
59 // substep 2: compute JF(x)
60 jf = pJF(x) ;
61 // substep 3: compute the correction h = JF(x)^(-1)F(x)
62 bool ok = linear_solver(jf, f, h) ;
63 if ( !ok ) return false ;
64 // substep 4: update x
65 for ( index_type i = 0 ; i < dim ; ++i )
66 x.values[i] -= h.values[i] ;
67 // check for the stopping criteria
68 value_type res = 0 ;
69 for ( index_type i = 0 ; i < dim ; ++i )
70 res += h.values[i]*h.values[i] ;
71 res = sqrt(res) ;
72 if ( res <= tol ) return true ;
73 }
74 return false ;
75 }
76}
File: 18.2.cpp
1#include "18.h"
2
3namespace newton_solver {
4 // F(x) = / x0 - x1 \
5 // | |
6 // \ x0**2 + x1**3 - 2 /
7 vec
8 F( vec const & in ) {
9 vec Fx ;
10 value_type const * x = in . values ;
11 Fx.values[0] = x[0] - x[1] ; // in . values[0] - in . values[1]
12 Fx.values[1] = x[0]*x[0] - x[1]*x[1]*x[1] - 2 ;
13 return Fx ;
14 }
15
16 //
17 mat
18 JF( vec const & in ) {
19 mat JFx ;
20 value_type const * x = in . values ;
21 JFx.values[0][0] = 1 ; // DF[0]/Dx[0]
22 JFx.values[0][1] = -1 ; // DF[0]/Dx[1]
23 JFx.values[1][0] = 2*x[0] ; // DF[1]/Dx[0]
24 JFx.values[1][1] = -3*x[1]*x[1] ; // DF[1]/Dx[1]
25 return JFx ;
26 }
27}
28
29int
30main() {
31 using newton_solver::vec ;
32 using newton_solver::F ;
33 using newton_solver::JF ;
34 using newton_solver::solver ;
35 using namespace std ;
36
37 vec x0, x ;
38
39 x0.values[0] = 1 ;
40 x0.values[1] = 1 ;
41 solver( x0, F, JF, 100, 1E-6, x ) ;
42
43 cout << "The solution is x = [ "
44 << x.values[0] << ", "
45 << x.values[1] << "]\n" ;
46}
File: 18.h
1// standard trick for only one time inclusion
2#ifndef EIGHTEEN_H
3#define EIGHTEEN_H
4
5#include <iostream>
6#include <iomanip>
7#include <cmath>
8
9namespace newton_solver {
10 using namespace std ;
11
12 // set the value_type to double,
13 // value_type is the generic name for "number"
14 // (non integer)type
15 typedef double value_type ;
16
17 // set the index_type to int,
18 // index_type is the generic name for "integer" type
19 typedef int index_type ;
20
21 index_type const dim = 2 ;
22
23 typedef struct {
24 value_type values[dim] ;
25 } vec ;
26
27 typedef struct {
28 value_type values[dim][dim];
29 } mat ;
30
31 /*
32 now we set the definition (prototipe)
33 of the functions
34 */
35
36 // prototype of the non-linear system
37 extern vec F( vec const & in ) ;
38
39 // prototype of the Jacobian of the non-linear system
40 extern mat JF( vec const & in ) ;
41
42 // prototype for the solver
43
44 typedef vec F_type ( vec const & ) ;
45 typedef mat JF_type ( vec const & ) ;
46
47 extern
48 bool
49 solver( vec const & x0,
50 F_type * pF,
51 JF_type * pJF,
52 index_type const n,
53 value_type const & tol,
54 vec & x
55 ) ;
56}
57
58#endif
File: 19.1.cpp
1#include "19.h"
2
3namespace newton_solver {
4
5 /*
6 Small 2x2 linear solver
7 */
8
9 bool
10 linear_solver( mat const & A, // coefficients matrix
11 vec const & b, // r.h.s
12 vec & x // the solution of the linear system
13 ) {
14 // Using Cramer rule
15 value_type det = A(0,0) * A(1,1) - A(1,0) * A(0,1) ;
16 if ( det == 0 ) return false ;
17
18 x[0] = ( b[0] * A(1,1) - b[1] * A(0,1) ) / det ;
19 x[1] = ( A(0,0) * b[1] - A(1,0) * b[0] ) / det ;
20
21 return true ;
22 }
23
24 /*
25 Newton scheme
26 -1
27 x = x - JF(x ) F(x )
28 n+1 n n n
29
30 the implementation:
31
32 SOLVE: JF(x ) h = F(x )
33 n n
34
35 UPDATE: x = x + h
36 n+1 n
37 */
38 bool
39 solver( vec const & x0,
40 F_type * pF,
41 JF_type * pJF,
42 index_type const n,
43 value_type const & tol,
44 vec & x
45 ) {
46
47 // set x to the initial value
48 x = x0 ; // not reccomended
49
50 for ( index_type i = 0 ; i < n ; ++i ) {
51 vec f, h ;
52 mat jf ;
53 // perform a Newton step
54 // substep 1: compute F(x)
55 f = pF(x) ;
56 // substep 2: compute JF(x)
57 jf = pJF(x) ;
58 // substep 3: compute the correction h = JF(x)^(-1)F(x)
59 bool ok = linear_solver(jf, f, h) ;
60 if ( !ok ) return false ;
61 // substep 4: update x
62 for ( index_type i = 0 ; i < dim ; ++i )
63 x[i] -= h[i] ;
64 // check for the stopping criteria
65 value_type res = 0 ;
66 for ( index_type i = 0 ; i < dim ; ++i )
67 res += h[i]*h[i] ;
68 res = sqrt(res) ;
69 if ( res <= tol ) return true ;
70 }
71 return false ;
72 }
73}
File: 19.2.cpp
1#include "19.h"
2
3namespace newton_solver {
4 // F(x) = / x0 - x1 \
5 // | |
6 // \ x0**2 + x1**3 - 2 /
7 vec
8 F( vec const & x ) {
9 vec Fx ;
10 Fx[0] = x[0] - x[1] ; // in . values[0] - in . values[1]
11 Fx[1] = x[0]*x[0] - x[1]*x[1]*x[1] - 2 ;
12 return Fx ;
13 }
14
15 //
16 mat
17 JF( vec const & in ) {
18 mat JFx ;
19 value_type const * x = in . values ;
20 JFx(0,0) = 1 ; // DF[0]/Dx[0]
21 JFx(0,1) = -1 ; // DF[0]/Dx[1]
22 JFx(1,0) = 2*x[0] ; // DF[1]/Dx[0]
23 JFx(1,1) = -3*x[1]*x[1] ; // DF[1]/Dx[1]
24 return JFx ;
25 }
26}
27
28int
29main() {
30 using newton_solver::vec ;
31 using newton_solver::F ;
32 using newton_solver::JF ;
33 using newton_solver::solver ;
34 using namespace std ;
35
36 vec x0, x ;
37
38 x0.values[0] = 1 ;
39 x0.values[1] = 1 ;
40 solver( x0, F, JF, 100, 1E-6, x ) ;
41
42 cout << "The solution is x = [ "
43 << x.values[0] << ", "
44 << x.values[1] << "]\n" ;
45}
File: 19.h
1// standard trick for only one time inclusion
2#ifndef NINETEEN_H
3#define NINETEEN_H
4
5#include <iostream>
6#include <iomanip>
7#include <cmath>
8
9namespace newton_solver {
10 using namespace std ;
11
12 // set the value_type to double,
13 // value_type is the generic name for "number"
14 // (non integer)type
15 typedef double value_type ;
16
17 // set the index_type to int,
18 // index_type is the generic name for "integer" type
19 typedef int index_type ;
20
21 index_type const dim = 2 ;
22
23 typedef struct {
24 value_type values[dim] ;
25
26 // declare the operator []
27 value_type & operator [] ( index_type i )
28 { return this -> values[i] ; }
29
30 value_type const & operator [] ( index_type i )
31 const // this const means that this method do not
32 // modify the contents of the struct
33 { return this -> values[i] ; }
34
35 } vec ;
36
37 typedef struct {
38 value_type values[dim][dim];
39
40 // declare the operator ()
41 value_type & operator () ( index_type i, index_type j)
42 { return this -> values[i][j] ; }
43
44 value_type const & operator () ( index_type i, index_type j)
45 const // this const means that this method do not
46 // modify the contents of the struct
47 { return this -> values[i][j] ; }
48 } mat ;
49
50 /*
51 now we set the definition (prototipe)
52 of the functions
53 */
54
55 // prototype of the non-linear system
56 extern vec F( vec const & in ) ;
57
58 // prototype of the Jacobian of the non-linear system
59 extern mat JF( vec const & in ) ;
60
61 // prototype for the solver
62
63 typedef vec F_type ( vec const & ) ;
64 typedef mat JF_type ( vec const & ) ;
65
66 extern
67 bool
68 solver( vec const & x0,
69 F_type * pF,
70 JF_type * pJF,
71 index_type const n,
72 value_type const & tol,
73 vec & x
74 ) ;
75}
76
77#endif
File: 20.1.cpp
1#include "20.h"
2
3namespace newton_solver {
4
5 /*
6 Small 2x2 linear solver
7 */
8
9 bool
10 linear_solver( mat const & A, // coefficients matrix
11 vec const & b, // r.h.s
12 vec & x // the solution of the linear system
13 ) {
14 // Using Cramer rule
15 value_type det = A(0,0) * A(1,1) - A(1,0) * A(0,1) ;
16 if ( det == 0 ) return false ;
17
18 x[0] = ( b[0] * A(1,1) - b[1] * A(0,1) ) / det ;
19 x[1] = ( A(0,0) * b[1] - A(1,0) * b[0] ) / det ;
20
21 // b[0] is the same as:
22 // b . operator [] (0)
23 return true ;
24 }
25
26 /*
27 Newton scheme
28 -1
29 x = x - JF(x ) F(x )
30 n+1 n n n
31
32 the implementation:
33
34 SOLVE: JF(x ) h = F(x )
35 n n
36
37 UPDATE: x = x + h
38 n+1 n
39 */
40 bool
41 solver( vec const & x0,
42 F_type * pF,
43 JF_type * pJF,
44 index_type const n,
45 value_type const & tol,
46 vec & x
47 ) {
48
49 // set x to the initial value
50 x = x0 ; // not reccomended
51
52 for ( index_type i = 0 ; i < n ; ++i ) {
53 vec f, h ;
54 mat jf ;
55 // perform a Newton step
56 // substep 1: compute F(x)
57 f = pF(x) ;
58 // substep 2: compute JF(x)
59 jf = pJF(x) ;
60 // substep 3: compute the correction h = JF(x)^(-1)F(x)
61 bool ok = linear_solver(jf, f, h) ;
62 if ( !ok ) return false ;
63 // substep 4: update x
64 // x = x - h ;
65 x -= h ;
66 // check for the stopping criteria
67 value_type res = h . norm2() ;
68 if ( res <= tol ) return true ;
69 }
70 return false ;
71 }
72}
File: 20.2.cpp
1#include "20.h"
2
3namespace newton_solver {
4 // F(x) = / x0 - x1 \
5 // | |
6 // \ x0**2 + x1**3 - 2 /
7 vec
8 F( vec const & x ) {
9 vec Fx ;
10 Fx[0] = x[0] - x[1] ; // in . values[0] - in . values[1]
11 Fx[1] = x[0]*x[0] - x[1]*x[1]*x[1] - 2 ;
12 return Fx ;
13 }
14
15 //
16 mat
17 JF( vec const & in ) {
18 mat JFx ;
19 value_type const * x = in . values ;
20 JFx(0,0) = 1 ; // DF[0]/Dx[0]
21 JFx(0,1) = -1 ; // DF[0]/Dx[1]
22 JFx(1,0) = 2*x[0] ; // DF[1]/Dx[0]
23 JFx(1,1) = -3*x[1]*x[1] ; // DF[1]/Dx[1]
24 return JFx ;
25 }
26}
27
28int
29main() {
30 using newton_solver::vec ;
31 using newton_solver::F ;
32 using newton_solver::JF ;
33 using newton_solver::solver ;
34 using namespace std ;
35
36 vec x0, x ;
37
38 x0.values[0] = 1 ;
39 x0.values[1] = 1 ;
40 solver( x0, F, JF, 100, 1E-6, x ) ;
41
42 cout << "The solution is x = [ "
43 << x.values[0] << ", "
44 << x.values[1] << "]\n" ;
45}
File: 20.h
1// standard trick for only one time inclusion
2#ifndef TWENTIETH_H
3#define TWENTIETH_H
4
5#include <iostream>
6#include <iomanip>
7#include <cmath>
8
9namespace newton_solver {
10 using namespace std ;
11
12 // set the value_type to double,
13 // value_type is the generic name for "number"
14 // (non integer)type
15 typedef double value_type ;
16
17 // set the index_type to int,
18 // index_type is the generic name for "integer" type
19 typedef int index_type ;
20
21 index_type const dim = 2 ;
22
23 typedef struct vec {
24 value_type values[dim] ;
25
26 // declare the operator []
27 value_type & operator [] ( index_type i )
28 { return this -> values[i] ; }
29
30 value_type const & operator [] ( index_type i )
31 const // this const means that this method do not
32 // modify the contents of the struct
33 { return this -> values[i] ; }
34
35 vec const &
36 operator -= ( vec const & a ) {
37 for ( index_type i = 0 ; i < dim ; ++i )
38 values[i] -= a[i] ;
39 return * this ;
40 }
41
42 vec const &
43 operator += ( vec const & a ) {
44 for ( index_type i = 0 ; i < dim ; ++i )
45 values[i] += a[i] ;
46 return * this ;
47 }
48
49 // compute the 2 norm of the vector
50 value_type norm2() const {
51 value_type res = 0 ;
52 for ( index_type i = 0 ; i < dim ; ++i )
53 res += values[i] * values[i] ;
54 return sqrt(res) ;
55 }
56
57 } vec ;
58
59 // external operator
60
61 // add two vector
62 inline
63 vec
64 operator + ( vec const & a, vec const & b ) {
65 vec c ;
66 for ( index_type i = 0 ; i < dim ; ++i )
67 c[i] = a[i] + b[i] ;
68 }
69
70 // subtract two vector (definition only)
71 vec
72 operator - ( vec const & a, vec const & b ) ;
73
74 typedef struct {
75 value_type values[dim][dim];
76
77 // declare the operator ()
78 value_type & operator () ( index_type i, index_type j)
79 { return this -> values[i][j] ; }
80
81 value_type const & operator () ( index_type i, index_type j)
82 const // this const means that this method do not
83 // modify the contents of the struct
84 { return this -> values[i][j] ; }
85 } mat ;
86
87 /*
88 now we set the definition (prototipe)
89 of the functions
90 */
91
92 // prototype of the non-linear system
93 extern vec F( vec const & in ) ;
94
95 // prototype of the Jacobian of the non-linear system
96 extern mat JF( vec const & in ) ;
97
98 // prototype for the solver
99
100 typedef vec F_type ( vec const & ) ;
101 typedef mat JF_type ( vec const & ) ;
102
103 extern
104 bool
105 solver( vec const & x0,
106 F_type * pF,
107 JF_type * pJF,
108 index_type const n,
109 value_type const & tol,
110 vec & x
111 ) ;
112}
113
114#endif
File: 21.1.cpp
1#include "21.1.h"
2
3namespace vector_matrix {
4
5 value_type & // return value
6 vec::operator [] // the operator [] is defined here
7 ( index_type i ) // the argument of []
8 { return this -> values[i] ; }
9
10 value_type const &
11 vec::operator [] ( index_type i ) const
12 { return this -> values[i] ; }
13
14 vec const &
15 vec::operator -= ( vec const & a ) {
16 for ( index_type i = 0 ; i < dim ; ++i )
17 values[i] -= a[i] ;
18 return * this ;
19 }
20
21 vec const &
22 vec::operator += ( vec const & a ) {
23 for ( index_type i = 0 ; i < dim ; ++i )
24 values[i] += a[i] ;
25 return * this ;
26 }
27
28 // compute the 2 norm of the vector
29 value_type vec::norm2() const {
30 value_type res = 0 ;
31 for ( index_type i = 0 ; i < dim ; ++i )
32 res += values[i] * values[i] ;
33 return sqrt(res) ;
34 }
35
36 // external operator
37
38 // add two vector
39 vec
40 operator + ( vec const & a, vec const & b ) {
41 vec c ;
42 for ( index_type i = 0 ; i < dim ; ++i )
43 c[i] = a[i] + b[i] ;
44 return c ;
45 }
46
47 // subtract two vector (definition only)
48 vec
49 operator - ( vec const & a, vec const & b ) {
50 vec c ;
51 for ( index_type i = 0 ; i < dim ; ++i )
52 c[i] = a[i] - b[i] ;
53 return c ;
54 }
55
56 // declare the operator ()
57 value_type &
58 mat::operator () ( index_type i, index_type j)
59 { return this -> values[i][j] ; }
60
61 value_type const &
62 mat::operator () ( index_type i, index_type j) const
63 { return this -> values[i][j] ; }
64
65
66 /*
67 Small 2x2 linear solver
68 */
69
70 vec
71 operator / ( vec const & b, mat const & A) {
72 vec x ;
73 // Using Cramer rule
74 value_type det = A(0,0) * A(1,1) - A(1,0) * A(0,1) ;
75
76 x[0] = ( b[0] * A(1,1) - b[1] * A(0,1) ) / det ;
77 x[1] = ( A(0,0) * b[1] - A(1,0) * b[0] ) / det ;
78
79 return x ;
80 }
81
82}
File: 21.2.cpp
1#include "21.2.h"
2
3namespace newton_solver {
4 /*
5 Newton scheme
6 -1
7 x = x - JF(x ) F(x )
8 n+1 n n n
9
10 the implementation:
11
12 SOLVE: JF(x ) h = F(x )
13 n n
14
15 UPDATE: x = x + h
16 n+1 n
17 */
18 bool
19 solver( vec const & x0,
20 F_type * pF,
21 JF_type * pJF,
22 index_type const n,
23 value_type const & tol,
24 vec & x
25 ) {
26
27 // set x to the initial value
28 x = x0 ; // not reccomended
29
30 for ( index_type i = 0 ; i < n ; ++i ) {
31 vec f, h ;
32 mat jf ;
33 // perform a Newton step
34 // substep 1: compute F(x)
35 f = pF(x) ;
36 // substep 2: compute JF(x)
37 jf = pJF(x) ;
38 // substep 3: compute the correction h = JF(x)^(-1)F(x)
39 h = f / jf ;
40 //bool ok = linear_solver(jf, f, h) ;
41 //if ( !ok ) return false ;
42 // substep 4: update x
43 // x = x - h ;
44 x -= h ;
45 // check for the stopping criteria
46 value_type res = h . norm2() ;
47 if ( res <= tol ) return true ;
48 }
49 return false ;
50 }
51}
File: 21.3.cpp
1#include "21.2.h"
2
3namespace newton_solver {
4 // F(x) = / x0 - x1 \
5 // | |
6 // \ x0**2 + x1**3 - 2 /
7 vec
8 F( vec const & x ) {
9 vec Fx ;
10 Fx[0] = x[0] - x[1] ; // in . values[0] - in . values[1]
11 Fx[1] = x[0]*x[0] - x[1]*x[1]*x[1] - 2 ;
12 return Fx ;
13 }
14
15 //
16 mat
17 JF( vec const & x ) {
18 mat JFx ;
19 JFx(0,0) = 1 ; // DF[0]/Dx[0]
20 JFx(0,1) = -1 ; // DF[0]/Dx[1]
21 JFx(1,0) = 2*x[0] ; // DF[1]/Dx[0]
22 JFx(1,1) = -3*x[1]*x[1] ; // DF[1]/Dx[1]
23 return JFx ;
24 }
25}
26
27int
28main() {
29 using newton_solver::vec ;
30 using newton_solver::F ;
31 using newton_solver::JF ;
32 using newton_solver::solver ;
33 using namespace std ;
34
35 vec x0, x ;
36
37 x0[0] = 1 ;
38 x0[1] = 1 ;
39 solver( x0, F, JF, 100, 1E-6, x ) ;
40
41 cout << "The solution is x = [ "
42 << x[0] << ", "
43 << x[1] << "]\n" ;
44}
File: 21.1.h
1// standard trick for only one time inclusion
2#ifndef TWENTIONE_ONE_H
3#define TWENTIONE_ONE_H
4
5#include <iostream>
6#include <iomanip>
7#include <cmath>
8
9namespace vector_matrix {
10 using namespace std ;
11
12 // set the value_type to double,
13 // value_type is the generic name for "number"
14 // (non integer)type
15 typedef double value_type ;
16
17 // set the index_type to int,
18 // index_type is the generic name for "integer" type
19 typedef int index_type ;
20
21 index_type const dim = 2 ;
22
23 class mat ; // forward declaration
24
25 class vec {
26 // private member of the class
27 value_type values[dim] ;
28
29 public: // from now the public interface
30 // declare the operator []
31 value_type & operator [] ( index_type i ) ;
32 value_type const & operator [] ( index_type i ) const ;
33
34 vec const & operator -= ( vec const & a );
35 vec const & operator += ( vec const & a );
36
37 // compute the 2 norm of the vector
38 value_type norm2() const ;
39
40 } ;
41
42 // external operator
43
44 // add two vector
45 vec operator + ( vec const & a, vec const & b ) ;
46
47 // subtract two vector (definition only)
48 vec operator - ( vec const & a, vec const & b ) ;
49
50 vec operator / ( vec const & b, mat const & A ) ;
51
52 class mat {
53 value_type values[dim][dim];
54
55 public:
56 // declare the operator ()
57 value_type & operator () ( index_type i, index_type j) ;
58 value_type const & operator () ( index_type i, index_type j) const ;
59 } ;
60
61
62}
63
64#endif
File: 21.2.h
1// standard trick for only one time inclusion
2#ifndef TWENTIONE_TWO_H
3#define TWENTIONE_TWO_H
4
5#include <iostream>
6#include <iomanip>
7#include <cmath>
8
9#include "21.1.h"
10
11namespace newton_solver {
12 using namespace std ;
13 using namespace vector_matrix ;
14
15 /*
16 now we set the definition (prototipe)
17 of the functions
18 */
19
20 // prototype of the non-linear system
21 extern vec F( vec const & in ) ;
22
23 // prototype of the Jacobian of the non-linear system
24 extern mat JF( vec const & in ) ;
25
26 // prototype for the solver
27
28 typedef vec F_type ( vec const & ) ;
29 typedef mat JF_type ( vec const & ) ;
30
31 extern
32 bool
33 solver( vec const & x0,
34 F_type * pF,
35 JF_type * pJF,
36 index_type const n,
37 value_type const & tol,
38 vec & x
39 ) ;
40}
41
42#endif
File: 22.1.cpp
1#include "22.1.h"
2
3namespace vector_matrix {
4
5 // the constructor
6 vec::vec( index_type dim ) {
7 this -> dim = dim ;
8 // new allocate dynamicaly the memory
9 // new TYPE [ SIZE ]
10 values = new value_type [ dim ] ;
11 }
12
13 // the destructor
14 vec::~vec() {
15 delete [] values ;
16 }
17
18 vec const & vec::operator = ( vec const & a ) {
19 for ( index_type i = 0 ; i < dim ; ++i )
20 values[i] = a[i] ;
21 return *this ;
22 }
23
24 value_type & // return value
25 vec::operator [] // the operator [] is defined here
26 ( index_type i ) // the argument of []
27 { return this -> values[i] ; }
28
29 value_type const &
30 vec::operator [] ( index_type i ) const
31 { return this -> values[i] ; }
32
33 vec const &
34 vec::operator -= ( vec const & a ) {
35 for ( index_type i = 0 ; i < dim ; ++i )
36 values[i] -= a[i] ;
37 return * this ;
38 }
39
40 vec const &
41 vec::operator += ( vec const & a ) {
42 for ( index_type i = 0 ; i < dim ; ++i )
43 values[i] += a[i] ;
44 return * this ;
45 }
46
47 // compute the 2 norm of the vector
48 value_type vec::norm2() const {
49 value_type res = 0 ;
50 for ( index_type i = 0 ; i < dim ; ++i )
51 res += values[i] * values[i] ;
52 return sqrt(res) ;
53 }
54
55 // external operator
56
57 // add two vector
58 vec
59 operator + ( vec const & a, vec const & b ) {
60 index_type dim = a.get_dim() ;
61 vec c(dim) ;
62 for ( index_type i = 0 ; i < dim ; ++i )
63 c[i] = a[i] + b[i] ;
64 return c ;
65 }
66
67 // subtract two vector (definition only)
68 vec
69 operator - ( vec const & a, vec const & b ) {
70 index_type dim = a.get_dim() ;
71 vec c(dim) ;
72 for ( index_type i = 0 ; i < dim ; ++i )
73 c[i] = a[i] - b[i] ;
74 return c ;
75 }
76
77 // the constructor
78 mat::mat( index_type dim ) {
79 this -> dim = dim ;
80 // new allocate dynamicaly the memory
81 // new TYPE [ SIZE ]
82 values = new value_type [ dim * dim ] ;
83 }
84
85 // the destructor
86 mat::~mat() {
87 delete [] values ;
88 }
89
90 // the copy contructor
91 mat const & mat::operator = ( mat const & a ) {
92 for ( index_type i = 0 ; i < dim*dim ; ++i )
93 values[i] = a . values[i] ;
94 return *this ;
95 }
96
97 // declare the operator ()
98 value_type &
99 mat::operator () ( index_type i, index_type j)
100 { return this -> values[i+j*dim] ; }
101
102 value_type const &
103 mat::operator () ( index_type i, index_type j) const
104 { return this -> values[i+j*dim] ; }
105
106
107 /*
108 Small 2x2 linear solver
109 */
110
111 vec
112 operator / ( vec const & b, mat const & A) {
113 vec x(2) ;
114 // Using Cramer rule
115 value_type det = A(0,0) * A(1,1) - A(1,0) * A(0,1) ;
116
117 x[0] = ( b[0] * A(1,1) - b[1] * A(0,1) ) / det ;
118 x[1] = ( A(0,0) * b[1] - A(1,0) * b[0] ) / det ;
119
120 return x ;
121 }
122
123}
File: 22.2.cpp
1#include "22.2.h"
2
3namespace newton_solver {
4 /*
5 Newton scheme
6 -1
7 x = x - JF(x ) F(x )
8 n+1 n n n
9
10 the implementation:
11
12 SOLVE: JF(x ) h = F(x )
13 n n
14
15 UPDATE: x = x + h
16 n+1 n
17 */
18 bool
19 solver( vec const & x0,
20 F_type * pF,
21 JF_type * pJF,
22 index_type const n,
23 value_type const & tol,
24 vec & x
25 ) {
26
27 index_type dim = x0 . get_dim();
28
29 // set x to the initial value
30 x = x0 ; // not reccomended
31
32 for ( index_type i = 0 ; i < n ; ++i ) {
33 vec f(dim), h(dim) ;
34 mat jf(dim) ;
35 // perform a Newton step
36 // substep 1: compute F(x)
37 f = pF(x) ;
38 // substep 2: compute JF(x)
39 jf = pJF(x) ;
40 // substep 3: compute the correction h = JF(x)^(-1)F(x)
41 h = f / jf ;
42 //bool ok = linear_solver(jf, f, h) ;
43 //if ( !ok ) return false ;
44 // substep 4: update x
45 // x = x - h ;
46 x -= h ;
47 // check for the stopping criteria
48 value_type res = h . norm2() ;
49 if ( res <= tol ) return true ;
50 }
51 return false ;
52 }
53}
File: 22.3.cpp
1#include "22.2.h"
2
3namespace newton_solver {
4 // F(x) = / x0 - x1 \
5 // | |
6 // \ x0**2 + x1**3 - 2 /
7 vec
8 F( vec const & x ) {
9 vec Fx(2) ;
10 Fx[0] = x[0] - x[1] ; // in . values[0] - in . values[1]
11 Fx[1] = x[0]*x[0] - x[1]*x[1]*x[1] - 2 ;
12 return Fx ;
13 }
14
15 //
16 mat
17 JF( vec const & x ) {
18 mat JFx(2) ;
19 JFx(0,0) = 1 ; // DF[0]/Dx[0]
20 JFx(0,1) = -1 ; // DF[0]/Dx[1]
21 JFx(1,0) = 2*x[0] ; // DF[1]/Dx[0]
22 JFx(1,1) = -3*x[1]*x[1] ; // DF[1]/Dx[1]
23 return JFx ;
24 }
25}
26
27int
28main() {
29 using newton_solver::vec ;
30 using newton_solver::F ;
31 using newton_solver::JF ;
32 using newton_solver::solver ;
33 using namespace std ;
34
35 vec x0(2), x(2) ;
36
37 x0[0] = 1 ;
38 x0[1] = 1 ;
39 solver( x0, F, JF, 100, 1E-6, x ) ;
40
41 cout << "The solution is x = [ "
42 << x[0] << ", "
43 << x[1] << "]\n" ;
44}
File: 22.1.h
1// standard trick for only one time inclusion
2#ifndef TWENTITWO_ONE_H
3#define TWENTITWO_ONE_H
4
5#include <iostream>
6#include <iomanip>
7#include <cmath>
8
9namespace vector_matrix {
10 using namespace std ;
11
12 // set the value_type to double,
13 // value_type is the generic name for "number"
14 // (non integer)type
15 typedef double value_type ;
16
17 // set the index_type to int,
18 // index_type is the generic name for "integer" type
19 typedef int index_type ;
20
21 class mat ; // forward declaration
22
23 class vec {
24
25 index_type dim ;
26
27 // private member of the class
28 value_type * values ;
29
30 vec() ;
31
32 public: // from now the public interface
33
34 // the constructor
35 vec( index_type dim ) ;
36
37 // the destructor
38 ~vec() ;
39
40 index_type const & get_dim() const { return dim ; }
41
42 // the copy constructor
43 vec const & operator = (vec const & ) ;
44
45 // declare the operator []
46 value_type & operator [] ( index_type i ) ;
47 value_type const & operator [] ( index_type i ) const ;
48
49 vec const & operator -= ( vec const & a );
50 vec const & operator += ( vec const & a );
51
52 // compute the 2 norm of the vector
53 value_type norm2() const ;
54
55 } ;
56
57 // external operator
58
59 // add two vector
60 vec operator + ( vec const & a, vec const & b ) ;
61
62 // subtract two vector (definition only)
63 vec operator - ( vec const & a, vec const & b ) ;
64
65 vec operator / ( vec const & b, mat const & A ) ;
66
67 class mat {
68
69 index_type dim ;
70
71 // private member of the class
72 value_type * values ;
73
74 mat() ;
75
76 public: // from now the public interface
77
78 // the constructor
79 mat( index_type dim ) ;
80
81 // the destructor
82 ~mat() ;
83
84 // the copy constructor
85 mat const & operator = (mat const & ) ;
86
87 // declare the operator ()
88 value_type & operator () ( index_type i, index_type j) ;
89 value_type const & operator () ( index_type i, index_type j) const ;
90 } ;
91
92
93}
94
95#endif
File: 22.2.h
1// standard trick for only one time inclusion
2#ifndef TWENTITWO_TWO_H
3#define TWENTITWO_TWO_H
4
5#include <iostream>
6#include <iomanip>
7#include <cmath>
8
9#include "22.1.h"
10
11namespace newton_solver {
12 using namespace std ;
13 using namespace vector_matrix ;
14
15 /*
16 now we set the definition (prototipe)
17 of the functions
18 */
19
20 // prototype of the non-linear system
21 extern vec F( vec const & in ) ;
22
23 // prototype of the Jacobian of the non-linear system
24 extern mat JF( vec const & in ) ;
25
26 // prototype for the solver
27
28 typedef vec F_type ( vec const & ) ;
29 typedef mat JF_type ( vec const & ) ;
30
31 extern
32 bool
33 solver( vec const & x0,
34 F_type * pF,
35 JF_type * pJF,
36 index_type const n,
37 value_type const & tol,
38 vec & x
39 ) ;
40}
41
42#endif
Lesson of 25/5/2005¶
File: 24.cpp
1#include <iostream>
2
3/*
4 Overloading and templates
5
6 */
7
8/*
9 compute the maximum of two numbers
10 */
11
12/* function max for double precision numbers */
13// first definition
14
15double max( double const & a, double const & b ) {
16 if ( a > b ) return a ;
17 else return b ;
18}
19
20/* function max for single precision numbers */
21// second definition
22
23float max( float const & a, float const & b ) {
24 if ( a > b ) return a ;
25 else return b ;
26}
27
28/* overloading means the same name for differents functions */
29
30/*
31 The template mechanism can produce skeleton
32 of code that can be expanded when is needed
33 */
34
35template <typename T>
36T max( T const & a, T const & b ) {
37 if ( a > b ) return a ;
38 else return b ;
39}
40
41
42template <typename Ta, typename Tb>
43Ta max( Ta const & a, Tb const & b ) {
44 if ( a > b ) return a ;
45 else return b ;
46}
47
48
49int
50main() {
51 {
52 double a = 1 ;
53 double b = 2 ;
54 double c = max(a,b) ;// use first definition
55 }
56 {
57 float a = 1 ;
58 float b = 2 ;
59 float c = max(a,b) ;// use second definition
60 }
61 {
62 int a = 1 ;
63 int b = 2 ;
64 int c = max(a,b) ; // use the template with T=int
65 }
66 {
67 int a = 1 ;
68 long b = 2 ;
69 int c = max(a,b) ; // use the template with T=int
70 }
71}
Lesson of 30/5/2005¶
File: 25.cpp
1#include <iostream>
2
3using namespace std ;
4/*
5 Overloading and templates
6 */
7
8/*
9 The template mechanism can produce skeleton
10 of code that can be expanded when is needed
11 */
12
13template <typename T, int N>
14T sum( T const v[] ) {
15 T res = 0 ;
16 for ( int i = 0 ; i < N ; ++i )
17 res += v[i] ;
18 return res ;
19}
20
21extern double b[] ; // extern double b[] ;
22 // somewhere there is double b[12] ;
23
24int
25main() {
26 double a[] = {1,2,3,4,5,6,7,8,9} ;
27 int const n = sizeof(a)/sizeof(a[0]); //sizeof(a)/sizeof(double) ;
28 cout << n << endl ;
29 double res = sum<double,5>(a) ;
30 cout << res << endl ;
31 res = sum<double,n>(a) ;
32 cout << res << endl ;
33 res = sum<double,n+10000>(a) ;
34 cout << res << endl ;
35}
File: 26.cpp
1#include <iostream>
2#include <string>
3
4using namespace std ;
5
6/*
7 A class can be thinked as a structure
8 with all the methods and data public.
9 */
10
11// this class
12class A {
13 public:
14 int a, b ;
15} ;
16
17// is "nearly" equivalent to this struct
18
19struct {
20 int a, b ;
21} A ;
22
23/*
24 One of the important feature of a class is
25 that we can protect some information
26 */
27
28class B {
29 string name ;
30 double x, y ;
31public:
32 // constructor method
33 B(string const & _n,
34 double const & _x,
35 double const & _y)
36 : name(_n), x(_x), y(_y)
37 { cout << "passing to the FIRST constructor for " << name << "\n" ; }
38 // another constructor
39 B(string const & _n) : name(_n), x(0), y(0)
40 { cout << "passing to the SECOND constructor for " << name << "\n" ; }
41 // another constructor
42 B(string const & _n, int const _x, int const _y)
43 : name(_n), x(_x), y(_y)
44 { cout << "passing to the THIRD constructor for " << name << "\n" ; }
45
46 // the destructor
47 ~B() {
48 cout << "passing to the destructor for " << name << "\n" ;
49 }
50} ;
51
52B a("a",0,1) ; // call of the third constuctor
53
54int
55main() {
56 cout << "STARTING THE PROGRAM\n" ;
57 B b("b",0.0,1.0) ; // call of the first constuctor
58
59 B * pointer_to_d ;
60 pointer_to_d = new B("pointer",0.0,1.0) ;
61 cout << "INSIDE THE PROGRAM\n" ;
62 delete pointer_to_d ; // free memory for pointer_to_d
63
64 B c("c") ; // call of the second constuctor
65
66 cout << "ENDING THE PROGRAM\n" ;
67 return 0 ;
68}
File: 27.cpp
1#include <iostream>
2#include <string>
3
4using namespace std ;
5
6/*
7 Example of a class with many costructor
8 */
9
10template <typename T>
11class vector {
12public:
13 typedef T value_type ; // alias of T to value_type ;
14private:
15 string the_name ;
16 int the_size ;
17 value_type * the_data ;
18public:
19 // constructor method
20 vector(string const & n, int const size) : the_name(n), the_size(size) {
21 cout << "Building vector " << the_name << " size = " << the_size << "\n" ;
22 the_data = new value_type [size] ;
23 }
24
25 // the destructor
26 ~vector() {
27 cout << "passing to the destructor for " << the_name << "\n" ;
28 delete [] the_data ;
29 }
30
31 // define the [] operator
32 value_type const & operator [] ( int i ) {
33 if ( i < 0 || i >= the_size ) {
34 cerr << "bad index for " << the_name << "[" << i << "]\n" ;
35 exit(0) ; // exit from the program
36 }
37 return the_data[i] ;
38 }
39
40} ;
41
42typedef vector<double> VECTOR ;
43
44int
45main() {
46 cout << "STARTING THE PROGRAM\n" ;
47 VECTOR v("v",100) ;
48
49 for ( int i = 0 ; i < 200 ; ++i ) {
50 VECTOR::value_type a ;
51 a = v[i] ;
52 }
53 cout << "ENDING THE PROGRAM\n" ;
54 return 0 ;
55}
File: 28.cpp
1#include <iostream>
2#include <string>
3#include <sstream>
4
5using namespace std ;
6
7/*
8 Example of a class with many costructor
9 */
10
11template <typename T>
12class vector {
13public:
14 typedef T value_type ; // alias of T to value_type ;
15private:
16 string the_name ;
17 int the_size ;
18 value_type * the_data ;
19public:
20 // constructor method
21 vector(string const & n, int const size) : the_name(n), the_size(size) {
22 cout << "Building vector " << the_name << " size = " << the_size << "\n" ;
23 the_data = new value_type [size] ;
24 }
25
26 // the destructor
27 ~vector() {
28 cout << "passing to the destructor for " << the_name << "\n" ;
29 delete [] the_data ;
30 }
31
32 // define the [] operator
33 value_type const & operator [] ( int i ) {
34 if ( i < 0 || i >= the_size ) {
35 // throw 1.234 ;
36 ostringstream the_error ;
37 the_error << "bad index for " << the_name << "[" << i << "]\n" ;
38 throw the_error.str(); // throw a string object
39 }
40 return the_data[i] ;
41 }
42
43} ;
44
45typedef vector<double> VECTOR ;
46
47int
48main() {
49 cout << "STARTING THE PROGRAM\n" ;
50 VECTOR v("v",100) ;
51
52 try {
53 for ( int i = 0 ; i < 200 ; ++i ) {
54 VECTOR::value_type a ;
55 a = v[i] ;
56 }
57 }
58 catch (int err_code) {
59 cerr << "found error number " << err_code << "\n" ;
60 }
61 catch (string const & err ) {
62 cerr << "found error : " << err << "\n" ;
63 }
64 catch (...) {
65 cerr << " unknown error found\n" ;
66 }
67 cout << "ENDING THE PROGRAM\n" ;
68 return 0 ;
69}
File: 29.cpp
1#include <iostream>
2#include <string>
3#include <sstream>
4
5using namespace std ;
6
7/*
8 Example of an error class
9 */
10
11class error {
12 string the_error_message ;
13 int the_error_number ;
14public:
15 error(string const & s, int n) :
16 the_error_message(s),
17 the_error_number(n) {}
18
19 void
20 print( ostream & stream ) const {
21 stream << "ERROR: " << the_error_message
22 << "\nERROR number: " << the_error_number
23 << "\n" ;
24 }
25};
26
27/*
28 Example of a class with many costructor
29 */
30
31template <typename T>
32class vector {
33public:
34 typedef T value_type ; // alias of T to value_type ;
35private:
36 string the_name ;
37 int the_size ;
38 value_type * the_data ;
39public:
40 // constructor method
41 vector(string const & n, int const size) : the_name(n), the_size(size) {
42 cout << "Building vector " << the_name << " size = " << the_size << "\n" ;
43 the_data = new value_type [size] ;
44 }
45
46 // the destructor
47 ~vector() {
48 cout << "passing to the destructor for " << the_name << "\n" ;
49 delete [] the_data ;
50 }
51
52 // define the [] operator
53 value_type const & operator [] ( int i ) {
54 if ( i < 0 || i >= the_size ) {
55 ostringstream the_error ;
56 the_error << "bad index for " << the_name << "[" << i << "]\n" ;
57 throw error(the_error.str(),1) ; // throw a string object
58 }
59 return the_data[i] ;
60 }
61
62} ;
63
64typedef vector<double> VECTOR ;
65
66int
67main() {
68 cout << "STARTING THE PROGRAM\n" ;
69 VECTOR v("v",100) ;
70
71 try {
72 for ( int i = 0 ; i < 200 ; ++i ) {
73 VECTOR::value_type a ;
74 a = v[i] ;
75 }
76 }
77 catch (int err_code) {
78 cerr << "found error number " << err_code << "\n" ;
79 }
80 catch (string const & err ) {
81 cerr << "found error : " << err << "\n" ;
82 }
83 catch (error const & err ) {
84 err . print(cerr) ;
85 }
86 catch (...) {
87 cerr << " unknown error found\n" ;
88 }
89 cout << "ENDING THE PROGRAM\n" ;
90 return 0 ;
91}
File: 30.cpp
1#include <iostream>
2#include <string>
3
4using namespace std ;
5
6/*
7 Example of inheritance
8 */
9
10// define the base class
11
12class Base {
13 string the_name ;
14 double x, y ;
15public:
16 Base( string const & n ) : the_name(n), x(0), y(0) {}
17 Base( string const & n,
18 double const & _x,
19 double const & _y) : the_name(n), x(_x), y(_y) {}
20
21 string const & name() const { return the_name ; }
22
23 void print( ostream & stream ) const {
24 stream << "class: " << the_name << " " << x << " " << y << "\n" ;
25 }
26} ;
27
28class Derived : public Base {
29 public:
30 Derived(string const & n) : Base(n,1,1) {}
31} ;
32
33int
34main() {
35 cout << "STARTING THE PROGRAM\n" ;
36 Base a("a") ;
37 Derived b("b") ;
38 a . print(cout) ;
39 b . print(cout) ;
40 cout << "ENDING THE PROGRAM\n" ;
41 return 0 ;
42}
File: 31.cpp
1#include <iostream>
2#include <string>
3
4using namespace std ;
5
6/*
7 A classical Example of inheritance
8 */
9
10// define the base class
11
12class Object {
13 string the_name ;
14protected:
15 double cx, cy ; // center of the object
16 double area ; // area of the object
17public:
18 Object( string const & n ) : the_name(n) {}
19
20 string const & name() const { return the_name ; }
21
22 void print( ostream & stream ) const {
23 stream << "object: " << the_name
24 << "\ncenter " << cx << " " << cy
25 << "\narea " << area << "\n" ;
26 }
27} ;
28
29class Circle : public Object {
30 double ray ;
31 // here cx, cy, area are in the private part of Circle
32 double const PI ;
33public:
34 Circle(double const & _cx,
35 double const & _cy,
36 double const & _ray) :
37 Object("circle"),
38 ray(_ray),
39 PI(3.1415)
40 {
41 // You can use the scope :: operator to access
42 // inherited part of the class
43 Object::cx = _cx ;
44 Object::cy = _cy ;
45 Object::area = 0 ;
46
47 // If there is no possibility of confusion
48 // you can avoid the scope operator ::
49 cx = _cx ;
50 cy = _cy ;
51 area = ray*ray*PI ;
52 }
53
54 void print( ostream & stream ) const {
55 Object::print(stream) ;
56 stream << "perimeter: " << 2*ray*PI << "\n" ;
57 }
58
59} ;
60
61class Square : public Object {
62 double length ;
63 // here cx, cy, area are in the private part of Circle
64public:
65 Square(double const & _cx,
66 double const & _cy,
67 double const & _length) :
68 Object("square"),
69 length(_length)
70 {
71 // If there is no possibility of confusion
72 // you can avoid the scope operator ::
73 cx = _cx ;
74 cy = _cy ;
75 area = length*length ;
76 }
77} ;
78
79void
80print( Object const & o ) {
81 o . print ( cout ) ;
82}
83
84int
85main() {
86 cout << "STARTING THE PROGRAM\n" ;
87 Circle c(2,3,3) ;
88 Square q(2,3,3) ;
89 c . print(cout) ;
90 print(c) ; // loose the print of the perimeter
91 print(q) ;
92 cout << "ENDING THE PROGRAM\n" ;
93 return 0 ;
94}
File: 32.cpp
1#include <iostream>
2#include <string>
3
4using namespace std ;
5
6/*
7 A classical Example of inheritance
8 */
9
10// define the base class
11
12class Object {
13 string the_name ;
14protected:
15 double cx, cy ; // center of the object
16 double area ; // area of the object
17public:
18 Object( string const & n ) : the_name(n) {}
19
20 string const & name() const { return the_name ; }
21
22 virtual // declare the routine as virtual
23 void print( ostream & stream ) const {
24 stream << "object: " << the_name
25 << "\ncenter " << cx << " " << cy
26 << "\narea " << area << "\n" ;
27 }
28} ;
29
30class Circle : public Object {
31 double ray ;
32 // here cx, cy, area are in the private part of Circle
33 double const PI ;
34public:
35 Circle(double const & _cx,
36 double const & _cy,
37 double const & _ray) :
38 Object("circle"),
39 ray(_ray),
40 PI(3.1415)
41 {
42 // You can use the scope :: operator to access
43 // inherited part of the class
44 Object::cx = _cx ;
45 Object::cy = _cy ;
46 Object::area = 0 ;
47
48 // If there is no possibility of confusion
49 // you can avoid the scope operator ::
50 cx = _cx ;
51 cy = _cy ;
52 area = ray*ray*PI ;
53 }
54
55 void print( ostream & stream ) const {
56 Object::print(stream) ;
57 stream << "perimeter: " << 2*ray*PI << "\n" ;
58 }
59
60} ;
61
62class Square : public Object {
63 double length ;
64 // here cx, cy, area are in the private part of Circle
65public:
66 Square(double const & _cx,
67 double const & _cy,
68 double const & _length) :
69 Object("square"),
70 length(_length)
71 {
72 // If there is no possibility of confusion
73 // you can avoid the scope operator ::
74 cx = _cx ;
75 cy = _cy ;
76 area = length*length ;
77 }
78} ;
79
80void
81print( Object const & o ) {
82 o . print ( cout ) ;
83}
84
85int
86main() {
87 cout << "STARTING THE PROGRAM\n" ;
88 Circle c(2,3,3) ;
89 Square q(2,3,3) ;
90 c . print(cout) ;
91 print(c) ; // NOW do not loose the print of the perimeter
92 print(q) ;
93 cout << "ENDING THE PROGRAM\n" ;
94 return 0 ;
95}
Lesson of 30/5/2005 (pomeriggio)¶
File: 33.cpp
1#include <iostream>
2
3using namespace std ;
4
5/*
6 A classical Example of generic programming
7 */
8
9// a simple routine that sort a vector of number
10void
11sort( int v[], int const dim ) {
12 // sorting by bubble sort
13 for ( int i = 0 ; i < dim-1 ; ++i )
14 for ( int j = i+1 ; j < dim ; ++j )
15 if ( v[i] > v[j] ) {
16 // swap the values
17 int k = v[i] ;
18 v[i] = v[j] ;
19 v[j] = k ;
20 }
21}
22
23/*
24 Using template we can generalize the algorithm
25 for any data type, other than integer
26 */
27
28template <typename T>
29void
30sort( T v[], int const dim ) {
31 // sorting by bubble sort
32 for ( int i = 0 ; i < dim-1 ; ++i )
33 for ( int j = i+1 ; j < dim ; ++j )
34 if ( v[i] > v[j] ) {
35 // swap the values
36 T k = v[i] ;
37 v[i] = v[j] ;
38 v[j] = k ;
39 }
40}
41
42
43/*
44 Sorting algorithm in the spirit of
45 the Standard Template Library
46
47 */
48
49template <typename T>
50void
51sort( T * begin, // pointer to the first element of the vector
52 T * end) { // pointer to PAST to the last element of the vector
53 // sorting by bubble sort
54 for ( T * pi = begin ; pi < end-1 ; ++pi )
55 for ( T * pj = pi+1 ; pj < end ; ++pj )
56 if ( *pi > *pj ) {
57 // swap the values
58 T buff = *pi ;
59 *pi = *pj ;
60 *pj = buff ;
61 }
62}
63
64int
65main() {
66 //int v[] = {1,3,-3,2,23,123,-23,232,-3,-45,-2} ;
67 //int dim = sizeof(v)/sizeof(v[0]) ;
68 long v[] = {1,3,-3,2,23,123,-23,232,-3,-45,-2} ;
69 long dim = sizeof(v)/sizeof(v[0]) ;
70
71 sort(v,v+dim) ; // v = pointer to the first element
72 // v + dim = pointer to past to the last element
73 cout << v[0] ;
74 for ( int i = 1 ; i < dim ; ++i )
75 cout << ", " << v[i] ;
76 cout << "\n" ;
77 return 0 ;
78}
File: 34.cpp
1#include <iostream>
2
3// Standard template library for algorithm
4#include <algorithm>
5
6using namespace std ;
7
8int
9main() {
10 //int v[] = {1,3,-3,2,23,123,-23,232,-3,-45,-2} ;
11 //int dim = sizeof(v)/sizeof(v[0]) ;
12
13 long a[] = {1,3,-3,2,23,123,-23,232,-3,-45,-2} ;
14 long adim = sizeof(a)/sizeof(a[0]) ;
15
16 long b[] = {22,-34,12} ;
17 long bdim = sizeof(b)/sizeof(b[0]) ;
18
19 sort(a,a+adim) ; // a = pointer to the first element
20 // a + dim = pointer to past to the last element
21
22 sort(b,b+bdim) ; // b = pointer to the first element
23 // b + dim = pointer to past to the last element
24
25 for ( int i = 0 ; i < adim ; ++i )
26 if ( a[i] == 23 )
27 cout << "FOUND at rank " << i << endl ;
28
29 /*
30 lower_bound implements the binary search
31 in a sorted vector ( o vector like ).
32 If found return the pointer (iterator) of the found
33 thing. If not found return the pointer (iterator)
34 of past to the last element.
35 */
36 long * res = lower_bound( a, a + adim, 1111123) ;
37 if ( res == a + adim || *res != 1111123 )
38 cout << "NOT FOUND\n" ;
39 else
40 cout << " FOUND = " << *res
41 << " RANK = " << res - a
42 << endl ;
43
44 cout << a[0] ;
45 for ( int i = 1 ; i < adim ; ++i )
46 cout << ", " << a[i] ;
47 cout << "\n" ;
48
49 /*
50 merge: merge two sorted vector into a
51 big one sorted vector
52 */
53 long c[1000] ;
54 merge( a, a+adim,
55 b, b+bdim,
56 c ) ;
57
58 cout << c[0] ;
59 for ( int i = 1 ; i < adim+bdim ; ++i )
60 cout << ", " << c[i] ;
61 cout << "\n" ;
62
63 cout << "MAX a = " << * max_element( a, a + adim) << endl ;
64
65 c[0] = 1 ;
66 c[1] = 2 ;
67 c[2] = 3 ;
68 for ( int i = 0 ; i < 7 ; ++i ) {
69 cout << c[0] << " " << c[1] << " " << c[2] << endl ;
70 next_permutation( c, c+3 ) ;
71 }
72
73 return 0 ;
74}
File: 35.cpp
1#include <iostream>
2
3// Standard template library for algorithm
4#include <algorithm>
5
6// Standard template library for vector container
7#include <vector>
8
9using namespace std ;
10
11int
12main() {
13 long avec[] = {1,3,-3,2,23,123,-23,232,-3,-45,-2} ;
14 long adim = sizeof(avec)/sizeof(avec[0]) ;
15
16 vector<long> a ;
17
18 a . reserve( 10 ) ; // reserve memory
19
20 for ( int i = 0 ; i < adim ; ++i ) {
21 a . push_back(avec[i]) ;
22 cout << "insert " << avec[i]
23 << " size = " << a . size()
24 << " capacity = " << a . capacity() << endl ;
25 }
26
27 sort( a . begin(), a . end() ) ;
28
29 vector<long> b(3) ; // 3 is the size of the vector
30 b[0] = 22 ;
31 b[1] = -34 ;
32 b[2] = 12 ;
33
34 sort( b . begin(), b . end() ) ;
35
36 /*
37 lower_bound implements the binary search
38 in a sorted vector ( o vector like ).
39 If found return the pointer (iterator) of the found
40 thing. If not found return the pointer (iterator)
41 of past to the last element.
42 */
43
44 vector<long>::iterator
45 res = lower_bound( a . begin(),
46 a . end(),
47 23 ) ;
48
49 if ( res == a . end() || *res != 23 )
50 cout << "NOT FOUND\n" ;
51 else
52 cout << " FOUND = " << *res
53 << " RANK = " << res - a . begin()
54 << endl ;
55
56 cout << a . front() ; // equivalent *(a.begin())
57 for ( vector<long>::const_iterator i = a.begin()+1 ;
58 i < a . end() ; ++i )
59 cout << ", " << *i ;
60 cout << "\n" ;
61
62 /*
63 merge: merge two sorted vector into a
64 big one sorted vector
65 */
66
67 vector<long> c(a.size()+b.size()) ;
68 merge( a . begin(), a . end(),
69 b . begin(), b . end(),
70 c.begin() ) ;
71
72 cout << c . front() ;
73 for ( vector<long>::const_iterator i = c.begin()+1 ;
74 i < c . end() ; ++i )
75 cout << ", " << *i ;
76 cout << "\n" ;
77
78 cout << "MAX a = " << * max_element( a.begin(), a.end()) << endl ;
79
80 c . resize(3) ;
81 c[0] = 1 ;
82 c[1] = 2 ;
83 c[2] = 3 ;
84 for ( int i = 0 ; i < 7 ; ++i ) {
85 cout << c[0] << " " << c[1] << " " << c[2] << endl ;
86 next_permutation( c . begin(), c . end() ) ;
87 }
88
89 return 0 ;
90}