File: src/dataTypeSizes.cpp
/** File: dataTypeSizes.cpp
Objective: Show C/C++ primitive data types sizes.
*/
#include <iostream>
#include <limits>
using namespace std;
int main(){
// 8 bits / 1 byte numeric types
//---------------------------------------------------
int charMin = numeric_limits<char>::min() ;
int charMax = numeric_limits<char>::max() ;
int scharMin = numeric_limits<signed char>::min() ;
int scharMax = numeric_limits<signed char>::max() ;
int ucharMin = numeric_limits<unsigned char>::min() ;
int ucharMax = numeric_limits<unsigned char>::max() ;
int int8Min = numeric_limits<int8_t>::min() ;
int int8Max = numeric_limits<int8_t>::max() ;
int uint8Min = numeric_limits<uint8_t>::min() ;
int uint8Max = numeric_limits<uint8_t>::max() ;
// 16 bits / 2 bytes Numeric types
//---------------------------------------------------
int shortMin = numeric_limits<short>::min() ;
int shortMax = numeric_limits<short>::max() ;
int ushortMin = numeric_limits<unsigned short>::min() ;
int ushortMax = numeric_limits<unsigned short>::max() ;
int int16Min = numeric_limits<int16_t>::min() ;
int int16Max = numeric_limits<int16_t>::max() ;
int uint16Min = numeric_limits<uint16_t>::min() ;
int uint16Max = numeric_limits<uint16_t>::max() ;
// 32 bits / 4 bytes Numeric types
//---------------------------------------------------
int intMin = numeric_limits<int>::min() ;
int intMax = numeric_limits<int>::max() ;
cout << "C/C++ Data type sizes in number of bytes (1 byte = 8 bits)" << endl;
cout << "\n1 byte / 8 bits Data types" << endl;
cout << "------------------------------------" << endl;
cout << "sizeof(char) = " << sizeof(char) << " min = " << charMin << " max = " << charMax << endl;
cout << "sizeof(signed char) = " << sizeof(signed char) << " min = " << scharMin << " max = " << scharMax << endl;
cout << "sizeof(unsigned char) = " << sizeof(unsigned char) << " min = " << ucharMin << " max = " << ucharMax << endl;
cout << "sizeof(int8_t) = " << sizeof(int8_t) << " min = " << int8Min << " max = " << int8Max << endl;
cout << "sizeof(uint8_t) = " << sizeof(uint8_t) << " min = " << uint8Min << " max = " << uint8Max << endl;
cout << "\n2 bytes / 16 bits Data types" << endl;
cout << "------------------------------------" << endl;
cout << "sizeof(short) = " << sizeof(short) << " min = " << shortMin << " max = " << shortMax << endl;
cout << "sizeof(usigned short) = " << sizeof(unsigned short) << " min = " << ushortMin << " max = " << ushortMax << endl;
cout << "sizeof(int16_t) = " << sizeof(int16_t) << " min = " << int16Min << " max = " << int16Max << endl;
cout << "sizeof(uint16_t) = " << sizeof(uint16_t) << " min = " << uint16Min << " max = " << uint16Max << endl;
cout << "\n4 bytes / 32 bits Data types" << endl;
cout << "------------------------------------" << endl;
cout << "sizeof(int) = " << sizeof(int) << " min = " << intMin << " max = " << intMax << endl;
cout << "sizeof(int32_t) = " << sizeof(int32_t) << endl;
cout << "sizeof(int64_t) = " << sizeof(int64_t) << endl;
cout << "sizeof(float) = " << sizeof(float) << endl;
cout << "\n8 bytes / 64 bits Data types" << endl;
cout << "------------------------------------" << endl;
cout << "sizeof(long) = " << sizeof(long) << endl;
cout << "sizeof(long long) = " << sizeof(long long) << endl;
cout << "sizeof(double) = " << sizeof(double) << endl;
return 0;
}
Running:
$ g++ dataTypeSizes.cpp -o dataTypeSizes.bin && ./dataTypeSizes.bin
C/C++ Data type sizes in number of bytes (1 byte = 8 bits)
1 byte / 8 bits Data types
------------------------------------
sizeof(char) = 1 min = -128 max = 127
sizeof(signed char) = 1 min = -128 max = 127
sizeof(unsigned char) = 1 min = 0 max = 255
sizeof(int8_t) = 1 min = -128 max = 127
sizeof(uint8_t) = 1 min = 0 max = 255
2 bytes / 16 bits Data types
------------------------------------
sizeof(short) = 2 min = -32768 max = 32767
sizeof(usigned short) = 2 min = 0 max = 65535
sizeof(int16_t) = 2 min = -32768 max = 32767
sizeof(uint16_t) = 2 min = 0 max = 65535
4 bytes / 32 bits Data types
------------------------------------
sizeof(int) = 4 min = -2147483648 max = 2147483647
sizeof(int32_t) = 4
sizeof(int64_t) = 8
sizeof(float) = 4
8 bytes / 64 bits Data types
------------------------------------
sizeof(long) = 8
sizeof(long long) = 8
sizeof(double) = 8
- file:src/testing1.cpp - Unit test example cpp files - Automated Unit Testing for CPP
#include <cassert>
int sum(int min, int max){
return min + max;
}
int main()
{
assert(sum(0, 2) == 3);
assert(sum(-2, 2) == 0);
assert(sum(3, 7) == 25);
return 0;
}
$ ./testing.bin
testing.bin: testing1.cpp:9: int main(): Assertion `sum(0, 2) == 3' failed.
Aborted
File: file:src/assert.cpp
// Description: Assertion demonstration in C++.
// Author: Caio Rodrigues
// File: assert.cpp
// Compile: g++ assert.cpp -o assert.bin
//
#include <cassert> // Assertion
#include <iostream> // Standard library
int main (int argc, char * argv[]) {
// Check argc and exit if not enough arguments are provided to avoid segmentation fault.
//
if (argc != 2){
std::cout << "Usage: ./" << argv[0] << "[n]" << std::endl;
std::cout << "where [n] is a number > 0. If n * n != 25 the assertion fails." << std::endl;
exit(0); // exit(1) - Return status code 1 - Indicating failure.
}
int i = atoi(argv[1]);
int j = i * i ;
assert (j == 25);
std::cout << "continuing" << std::endl;
exit(0); // exit(0) - Return status code 0 - Indicating success.
}
This file demonstrate assertion in C++. If the square of input argument is not 25 it throws an assertion error.
Compile:
$ g++ assert.cpp -o assert.bin
Running:
No arguments - print help
./assert.bin
Usage: ././assert.bin[n]
where [n] is a number > 0. If n * n != 25 the assertion fails.
Passing 4 as argument.
./assert.bin 4
assert.bin: assert.cpp:24: int main(int, char**): Assertion `j == 25' failed.
Passing 10 as argument
./assert.bin 10
assert.bin: assert.cpp:24: int main(int, char**): Assertion `j == 25' failed.
Passing 5 as argument. 5 * 5 == 25. Ok. The assertion doesn’t fail.
./assert.bin 5
continuing
Shows how to parse number with atoi, atof and so on.
File: file:src/numberParse.cpp
// Description: atoi, atof, strtol demonstration.
// Note: Convert string to integer, double and long integer.
// Tags: atoi, atof, strtol
//
#include <cassert>
#include <iostream>
using namespace std;
int main (){
cout << "\nAtoi - parse int 32 bits" << endl;
cout << "atoi(\"2342\") = " << atoi("2342") << endl;
cout << "atoi(\"-2323\") = " << atoi("-2323") << endl;
cout << "atoi(\"failed\") = " << atoi("failed") << endl;
cout << "atoi(\"12xy346\") = " << atoi("12xy346") << endl;
cout << "\nAtof - parse float/double" << endl;
cout << "atof(\"100.23\") = " << atof("100.23") << endl;
cout << "atof(\"-20.015e3\") = " << atof("-20.015e3") << endl;
cout << "atof(\"100.134354blablah\") = " << atof("100.134354blablah") << endl;
cout << "atof(\"failed0.3123garbage\") = " << atof("failed0.3123garbage") << endl;
return 0;
}
Running:
./g++ numberParse.cpp -o numberParse.bin && ./numberParse.bin
Atoi - parse int 32 bits
atoi("2342") = 2342
atoi("-2323") = -2323
atoi("failed") = 0
atoi("12xy346") = 12
Atof - parse float/double
atof("100.23") = 100.23
atof("-20.015e3") = -20015
atof("100.134354blablah") = 100.134
atof("failed0.3123garbage") = 0
#include <iostream> // Basic IO functions
#include <cmath> // C-math functions such as sqrt, pow ...
#include <cassert> // Assertions
using namespace std;
// Function prototypes
//---------------------------------//
double scalarProduct (double [], double [], int);
double vectorSum (double [], int);
double vectorNorm (double [], int);
void printVectorVert (double xs[], int size);
// Main function
//-------------------------------
int main()
{
int size = 4 ;
double v1[] = {1.0, 2.0, 3.0, 4.0} ;
double v2[] = {3.0, 4.0, 5.0, 6.0} ;
cout << "\n\nVector v1 = " << endl ;
printVectorVert(v1, size);
cout << "\n\nVector v2 = " << endl ;
printVectorVert(v2, size);
cout << "\n\nScalar product is = " << scalarProduct(v1, v2, size) << endl;
cout << "Vector v1 sum is = " << vectorSum(v1, size) << endl;
cout << "Vector v2 Norm is = " << vectorNorm(v1, size) << endl;
assert(scalarProduct(v1, v2, size) == 50.0);
return 0 ; // Return 0 as status code.
}
// Functions Implementations
// -------------------------------- //
double scalarProduct(double xs[], double ys[], int size){
double sum = 0.0;
for (int i = 0; i <= size -1; i++){
sum = sum + xs[i] * ys[i];
}
return sum;
}
double vectorSum(double xs[], int size){
double sum = 0.0 ;
for (int i = 0; i <= size - 1; i++){
sum = sum + xs[i];
}
return sum;
}
double vectorNorm(double xs[], int size){
double sum = 0.0 ;
for (int i = 0; i <= size - 1; i++){
sum = sum + xs[i] * xs[i];
}
return sqrt(sum);
}
void printVectorVert(double xs[], int size){
for (int i = 0; i <= size -1; i++){
cout << "v[" << i << "] = " << xs[i] << endl ;
}
}
Program output:
g++ arraysFun.cpp -o arraysFun.bin && ./arraysFun.bin
Vector v1 =
v[0] = 1
v[1] = 2
v[2] = 3
v[3] = 4
Vector v2 =
v[0] = 3
v[1] = 4
v[2] = 5
v[3] = 6
Scalar product is = 50
Vector v1 sum is = 10
Vector v2 Norm is = 5.47723
- File: src/cppVector2D.cpp
#include <iostream>
#include <cmath>
using namespace std;
class vector2D
{
private:
// Private members
double x;
double y;
public:
// Class constructors
vector2D();
vector2D(double vX, double vY);
// Getters
double getX() const;
double getY() const;
void print() const;
void move(double dx, double dy);
void setPos(double vX, double vY);
//-- Operators (Binary Functions/ Class members) -- //
vector2D operator+ (vector2D B);
vector2D operator- (vector2D B);
vector2D operator* (double factor);
vector2D operator/ (double factor);
};
vector2D::vector2D() {
x = 0.0;
y = 0.0;
}
vector2D::vector2D(double vX, double vY){
x = vX;
y = vY;
}
double vector2D::getX() const{
return x;
}
double vector2D::getY() const{
return y;
}
void vector2D::move(double dx, double dy){
x = x + dx;
y = y + dy;
}
void vector2D::setPos(double vX, double vY)
{
x = vX;
y = vY;
}
void vector2D::print() const
{
cout << "Vector2D (X = " << x << ", Y = " << y << ")" << endl;
}
vector2D vector2D::operator + (vector2D B){
vector2D res;
res.x = x + B.x;
res.y = y + B.y;
return res;
}
vector2D vector2D::operator - (vector2D B){
vector2D res;
res.x = x - B.x;
res.y = y - B.y;
return res;
}
vector2D vector2D::operator * (double factor){
vector2D res;
res.x = x * factor;
res.y = y * factor;
return res;
}
vector2D vector2D::operator / (double factor){
vector2D res;
res.x = x / factor;
res.y = y / factor;
return res;
}
int main(){
vector2D vA = vector2D();
vector2D vB = vector2D(10.23, -8.63);
vA.print();
vA.move(2.0, 3.0);
vA.print();
vB.print();
vB.move(2.0, 3.0);
vB.print();
cout << "\n(1) Vc = vA + vB = " << endl;
vector2D vC = vA + vB;
vC.print();
cout << "\n(2) Vc = vA + vB = " << endl;
(vA + vB).print();
cout << "\n(3) vB * 3.0 = " << endl;
(vB * 3.0).print();
cout << "\n(4) (vA + vB) / 2.0 = " << endl;
vector2D vD = (vB + vB) / 2.0 ;
vD.print();
// ----------- Pointer Tests ------------------ //
vector2D * vp ;
vp = & vB ; // Assign pointer to address of vector vB.
cout << "\n\nPointer address = " << vp << endl ;
cout << "\nvp->print() = " << endl;
vp->print();
cout << "\n(*vp).print() = " << endl;
(*vp).print();
cout << "\nvector2D m = *vp; m.print(); = " << endl;
vector2D m = *vp;
m.print();
return 0;
}
Running:
$ g++ cppVector2D.cpp -o cppVector2D.bin && ./cppVector2D.bin
Vector2D (X = 0, Y = 0)
Vector2D (X = 2, Y = 3)
Vector2D (X = 10.23, Y = -8.63)
Vector2D (X = 12.23, Y = -5.63)
(1) Vc = vA + vB =
Vector2D (X = 14.23, Y = -2.63)
(2) Vc = vA + vB =
Vector2D (X = 14.23, Y = -2.63)
(3) vB * 3.0 =
Vector2D (X = 36.69, Y = -16.89)
(4) (vA + vB) / 2.0 =
Vector2D (X = 12.23, Y = -5.63)
Pointer address = 0x7fffa50cb390
vp->print() =
Vector2D (X = 12.23, Y = -5.63)
(*vp).print() =
Vector2D (X = 12.23, Y = -5.63)
vector2D m = *vp; m.print(); =
Vector2D (X = 12.23, Y = -5.63)
C++ Arrays Drawbacks
- The size of array is fixed or constant.
- Passing an array as parameter is cumbersome since the array and its size must be passed.
- There is no way to insert elements at the beggining or at the end.
- It is not possible to return an array from a function.
- It requires manual memory management and allocation what is error prone.
Vectors
- C++ Vectors are a class in C++.
- Size of vectors can grow or shrink during execution.
- A vector stores its size, therefore a it doesn’t need to be passed as function argument.
- It provides random access. Vector elements can accessed by its indexes like C/C++ arrays.
- Vectors can be returned from functions.
Vectors X Arrays Declaration
C/C++ Arrays
const int VECTOR_SIZE = 10;
double xs[VECTOR_SIZE];
C/C++ STL Vector
const int VECTOR_SIZE = 10
vector<double> xs;
Import vector class
Add at the top of file. - #include <vector>
#include <iostream>
#include <vector>
using namespace std;
... .... ... ... ...
File: src/cppStlVector.cpp
#include <iostream>
#include <vector>
#include <cmath>
#include <string>
using namespace std;
/// Pass the vectors by value. It copies the vectors, so passing by
// reference does not copies the vectors and it is more efficient.
//
vector<double> sumVectors1(vector<double> xs, vector<double> ys){
vector<double> zs(xs.size());
for (int i = 0; i < xs.size(); i++){
zs.at(i) = xs.at(i) + ys.at(i);
}
return zs;
}
vector<double> sumVectors2(vector<double> &xs, vector<double> &ys){
vector<double> zs(xs.size());
for (int i = 0; i < xs.size(); i++){
zs.at(i) = xs.at(i) + ys.at(i);
}
return zs;
}
void printVector1(string name, vector<double> xs){
cout << name << " = [ ";
for (int i = 0; i < xs.size(); i++){
cout << xs.at(i) << " " ;
}
cout << "]" << endl;
}
void printVector2(string name, vector<double> &xs){
cout << name << " = [ ";
for (int i = 0; i < xs.size(); i++){
cout << xs.at(i) << " " ;
}
cout << "]" << endl;
}
void printVectorWithIterator(string name, vector<double> &xs){
cout << name << " = [ ";
for (vector<double>::iterator i = xs.begin(); i != xs.end(); ++i){
cout << *i << " " ;
}
cout << "]" << endl;
}
// Returns the sum of all vector elements.
double vectorSum(vector<double> &xs){
double sum = 0;
for (int i = 0; i < xs.size(); i++){
sum = sum + xs.at(i);
}
return sum;
}
// Returns the product of all vectors elements.
double vectorProd(vector<double> &xs){
double prod = 1.0;
for (int i = 0; i < xs.size(); i++){
prod = prod + xs.at(i);
}
return prod;
}
double vectorNorm(vector<double> &xs){
double sum = 1.0;
double x = 0.0;
for (int i = 0; i < xs.size(); i++){
x = xs.at(i);
sum = sum + x * x;
}
return sqrt(sum);
}
double vectorAverage(vector<double> &xs){
double sum = 1.0;
for (int i = 0; i < xs.size(); i++){
sum = sum + xs.at(i);
}
return sum / xs.size();
}
void vectorAnalytics(string name, vector<double> &xs){
cout << "\n\nAnalytic for vector " << name << endl;
cout << "----------------------------------- " << endl;
printVector2(name, xs);
cout << "size = " << xs.size() << endl;
cout << "average = " << vectorAverage(xs) << endl;
cout << "sum = " << vectorSum(xs) << endl;
cout << "product = " << vectorProd(xs) << endl;
cout << "norm = " << vectorNorm(xs) << endl;
}
int main(){
int size = 6;
// Vector initialized from a double array.
vector<double> xs({1, 2, 3, 5.5, 10.8, 4.5});
// Vector initialized with all elements set to 0.0
vector<double> ys(6);
// Vector intialized with all elements set to 4.0
vector<double> zs(6, 4.0);
// Vector with 0 elements.
vector<double> ks;
printVector1("xs", xs);
printVector1("ys", ys);
printVector2("zs", zs);
printVectorWithIterator("Print Vector with iteractor - xs", xs);
cout << "xs.size() = " << xs.size() << endl ;
cout << "xs.at(3) = " << xs.at(3) << endl ;
cout << "xs.at(0) = " << xs.at(0) << endl ;
cout << "xs.at(5) = " << xs.at(5) << endl ;
cout << "vectorSum(xs) = " << vectorSum(xs) << endl;
cout << "vectorNorm(xs) = " << vectorNorm(xs) << endl;
printVector1("sumVectors1(xs, zs) = xs + zs", sumVectors1(xs, zs));
printVector1("sumVectors2(xs, zs) = xs + zs", sumVectors2(xs, zs));
cout << "Clear vector xs -> " ;
xs.clear();
printVector2("xs", xs);
ks.push_back(4.0);
ks.push_back(5.0);
ks.push_back(3.0);
ks.push_back(6.0);
ks.push_back(7.0);
ks.push_back(9.3);
printVector2("ks", ks);
vectorAnalytics("ks", ks);
return 0;
}
Running:
$ g++ cppStlVector.cpp -o cppStlVector.bin && ./cppStlVector.bin
xs = [ 1 2 3 5.5 10.8 4.5 ]
ys = [ 0 0 0 0 0 0 ]
zs = [ 4 4 4 4 4 4 ]
Print Vector with iteractor - xs = [ 1 2 3 5.5 10.8 4.5 ]
xs.size() = 6
xs.at(3) = 5.5
xs.at(0) = 1
xs.at(5) = 4.5
vectorSum(xs) = 26.8
vectorNorm(xs) = 13.4959
sumVectors1(xs, zs) = xs + zs = [ 5 6 7 9.5 14.8 8.5 ]
sumVectors2(xs, zs) = xs + zs = [ 5 6 7 9.5 14.8 8.5 ]
Clear vector xs -> xs = [ ]
ks = [ 4 5 3 6 7 9.3 ]
Analytic for vector ks
-----------------------------------
ks = [ 4 5 3 6 7 9.3 ]
size = 6
average = 5.88333
sum = 34.3
product = 35.3
norm = 14.9161
- file:src/glibc-version.c
Source:
/*
Description: Show glibc Version.
OS: Linux only
Compile with:
$ gcc glibc-version.c -o glibc-version.bin && ./glibc-version.bin
glibc version: 2.24
*/
#include <stdio.h>
#include <stdlib.h>
#include <gnu/libc-version.h>
int main(int argc, char *argv[]) {
printf("glibc version: %s\n", gnu_get_libc_version());
}
Compile:
gcc glibc-version.c -o glibc-version.bin
Run:
$ ./src/glibc-version.bin
glibc version: 2.24