Thursday, May 10, 2018

Vector of Smart Pointers with Template


#include <iostream>
#include <vector>
#include <memory>
#include <sstream>
#include <string>
#include <typeinfo>


// Require C++ version 14 to compile!

class Base
{
public:
    Base(Base & other);
    Base(Base *);
    Base(char const * const tag, char const * const desc) : m_tag(tag), m_desc(desc) {}
    //Base(std::string const & tag, std::string const & desc) : m_tag(tag), m_desc(desc) {}
    ~Base() = default;

    void print();
    virtual void Process(); 

public:
    std::string m_tag = "";
    std::string m_desc = "";
};



Base::Base(Base & rhs)
{
    m_tag = rhs.m_tag;
    m_desc = rhs.m_desc;
}


Base::Base(Base *pOther)
{
    m_tag = pOther->m_tag;
    m_desc = pOther->m_desc;
}


void Base::print()
{
    std::cout << __FUNCTION__ << "(" << this << "): Base::m_tag = " << m_tag << std::endl 
              << "                  Base::m_desc = " << m_desc << std::endl;
}


void Base::Process()
{
    std::cout << __PRETTY_FUNCTION__ << std::endl;
}



template <class CNAME>
Base* createClass(char const *const tag, char const * const desc)
{
    CNAME * pObj  = new CNAME(tag,desc);

    std::cout << "Inside " << __FUNCTION__  << "(): ";
    pObj->Process();
    return dynamic_cast<Base*>(pObj);
}


template <class CNAME>
std::unique_ptr<Base> createUniqueClass(char const *const tag, char const *const desc)
{
    std::unique_ptr<Base> obj(createClass<CNAME>(tag, desc));
    return obj;
}



class KelasA : public Base
{
public:
    KelasA(char const * const tag, char const * const desc) : Base(tag, desc) {}
 static std::string const DefaultKelasName;

    void Process() override;
private:
 std::string m_name = DefaultKelasName;
};

std::string const KelasA::DefaultKelasName = "A";




void KelasA::Process()
{
    std::cout << __PRETTY_FUNCTION__ << std::endl;
}


class KelasB : public Base
{
public:
    KelasB(char const * const tag, char const * const desc) : Base(tag, desc) {}
 static std::string const DefaultKelasName;
    void Process() override;
private:
 std::string m_name = DefaultKelasName;
};


std::string const KelasB::DefaultKelasName = "B";


void KelasB::Process()
{
    std::cout << __PRETTY_FUNCTION__ << std::endl;
}


class Container
{
public:
 template <class CNAME>
 void Add(std::string tag = "")
 {
  std::ostringstream sout;
  sout << __FUNCTION__ << ":Entry=" << m_bin.size();
  #define ANAM(x) #x
  m_bin.push_back(createUniqueClass<CNAME>(tag.c_str(), const_cast<char const *>(sout.str().c_str())));
 }

 void Process();


private:
    std::vector<std::unique_ptr<Base>> m_bin;
};



void Container::Process()
{
 for(auto & v : m_bin)
    {
        v->Process();
        v->print();
    }
}


int main()
{
 Container c;

 for(auto i = 0; i<10; ++i)
 {
  c.Add<KelasA>("A");
  c.Add<KelasB>("B");
 }

 c.Process();
 
    return 0;
}

Vector of Smart Pointers (revised)

The previous example doesn't really show the polymorphism. This example shows the coolness of C++ (version 14):





#include <iostream>
#include <vector>
#include <memory>


// Require C++ version 14 to compile!

class Base
{
public:
    Base(Base & other);
    Base(Base *);
    Base(char const * const tag, char const * const desc) : m_tag(tag), m_desc(desc) {}
    ~Base() = default;

    void print();
    virtual void Process(); 

public:
    std::string m_tag = "";
    std::string m_desc = "";
};



Base::Base(Base & rhs)
{
    m_tag = rhs.m_tag;
    m_desc = rhs.m_desc;
}


Base::Base(Base *pOther)
{
    m_tag = pOther->m_tag;
    m_desc = pOther->m_desc;
}


void Base::print()
{
    std::cout << __FUNCTION__ << "(" << this << "): Base::m_tag = " << m_tag << std::endl 
              << "                  Base::m_desc = " << m_desc << std::endl;
}


void Base::Process()
{
    std::cout << __PRETTY_FUNCTION__ << std::endl;
}



template <class CNAME>
Base* createClass(char const *const tag, char const * const desc)
{
    CNAME * pObj  = new CNAME(tag,desc);

    std::cout << "Inside " << __FUNCTION__  << "(): ";
    pObj->Process();
    return dynamic_cast<Base*>(pObj);
}


template <class CNAME>
std::unique_ptr<Base> createUniqueClass(char const *const tag, char const *const desc)
{
    std::unique_ptr<Base> obj(createClass<CNAME>(tag, desc));
    return obj;
}



class KelasA : public Base
{
public:

    KelasA(char const * const tag, char const * const desc) : Base(tag, desc) {}
    void Process() override;
};


void KelasA::Process()
{
    std::cout << __PRETTY_FUNCTION__ << std::endl;
}


class KelasB : public Base
{
public:
    KelasB(char const * const tag, char const * const desc) : Base("B", desc) {}
    void Process() override;
};



void KelasB::Process()
{
    std::cout << __PRETTY_FUNCTION__ << std::endl;
}




int main()
{
    std::vector<std::unique_ptr<Base>> vb;

    vb.push_back(createUniqueClass<KelasA>("A", "Kelase A-1"));

    vb.push_back(createUniqueClass<KelasB>("B", "Kelase B-1"));

    //for(auto v = vb.begin(); v != vb.end(); v++)a
    for(auto & v : vb)
    {
        v->Process();
        v->print();
    }

    return 0;
}

Wednesday, May 9, 2018

Vector of Smart Pointers

#include <iostream>
#include <vector>
#include <memory>


// Require C++ version 14 to compile!

class Base
{
public:
    Base(Base & other);
    Base(Base *);
    Base(char const * const tag, char const * const desc) : m_tag(tag), m_desc(desc) {}

    void print();

public:
    std::string m_tag = "";
    std::string m_desc = "";
};



Base::Base(Base & rhs)
{
    m_tag = rhs.m_tag;
    m_desc = rhs.m_desc;
}


Base::Base(Base *pOther)
{
    m_tag = pOther->m_tag;
    m_desc = pOther->m_desc;
}


void Base::print()
{
    std::cout << __FUNCTION__ << "(" << this << "): Base::m_tag = " << m_tag << std::endl 
              << "                  Base::m_desc = " << m_desc << std::endl;
}


template <class CNAME>
Base * createClass(char const *const tag, char const * const desc)
{
    CNAME *pObj = new CNAME(tag,desc);

    Base *pBase = dynamic_cast<Base*>(pObj);

    return pBase;
}




class KelasA : public Base
{
public:

    KelasA(char const * const tag, char const * const desc) : Base(tag, desc) {}
    void FuncA() {}
};

class KelasB : public Base
{
public:
    KelasB(char const * const tag, char const * const desc) : Base("B", desc) {}
    void FuncA() {}
};


int main()
{
    std::vector<std::unique_ptr<Base>> vb;

    std::unique_ptr<Base> p;
    p = std::make_unique<Base>((createClass<KelasA>("A", "Kelas A-1")));
    vb.push_back(std::move(p));
    p = std::make_unique<Base>((createClass<KelasB>("B", "Kelas B-1")));
    vb.push_back(std::move(p));

    for(auto v = vb.begin(); v != vb.end(); v++)
    {
        (*v)->print();
    }

    return 0;
}

Sunday, April 8, 2018

Stream of Prime Numbers

Create an endless stream of prime numbers - a bit like IntStream.of(2,3,5,7,11,13,17), but infinite. The stream must be able to produce a million primes in a few seconds.

Tuesday, October 3, 2017

ESP8266 vs ESP32

SpecificationsESP8266ESP32
MCUXtensa Single-core 32-bit L106Xtensa Dual-Core 32-bit LX6 with 600 DMIPS
802.11 b/g/n Wi-FiYes, HT20Yes, HT40
WiFi Security?WEP, WPA/WPA2 PSK/Enterprise
Hardware Accelerated Encryption?AES/SHA2/Elliptical Curve Cryptography/RSA-4096
BluetoothNonedual-mode: Bluetooth 4.2 BLE or classi
Typical Frequency80 MHz240 MHz
SRAM160 KB520 KB
FlashSPI Flash, up to 16 MBSPI Flash, up to 16 MB, memory mapped to CPU code space.
GPIO1736
Hardware/Software PWMNone/8 channels1/16 channels
SPI/I2S/I2C/UART 2/1/2/2 3/2/2/3
ADC10 bit12-bit, 18 channels
DACNone2
CANNone?
Ethernet MAC Interface None 1
Touch Sensor None Yes
Temperature SensorNoneyes
Working Temperature-40 C - 125 C-40 C - 125 C
Operating Voltage?2.3V to 3.6V C
Power Consumption 77 Î¼A5 μA power consumption in Deep-sleep

Reference: http://espressif.com/en/products/hardware/esp32/overview

My protoboard