dart::ffi.

Dart i Flutter z dart::ffi jeszcze bardziej mi się podobają!

Kliknij aby otworzyć pliki źródłowe.

std::variant, std::any i ranges-v3 czyli prawie jak w Pythonie.

Ostatnio w ramach „się odstresowywania” czytam sobie o zmianach w standardzie c++17 i c++20 (wielkie dzięki Bartkowi Filipkowi za jego bloga). Dużo tego, ale zmiany są ogromne i dzisiejszy C++ jest po prostu fascynujący. Nawet nie komentuje poniższego kodu. Wklejam tu dla samego siebie i powiem tylko, że jak g++/clang++ będą z c++20 zgodne, to ja już nie chcę nic więcej. Może jeszcze tylko ogarnięcie parallelstl. Intel-tbb działa pięknie. Tylko jeden cytat apropos:

„Do you know how much of the processing power of a typical desktop machine we can utilize using only the core version of C++/Standard Library? 50%, 100%? 10%?[…] we can usually access only around 0,25% with single-threaded C++ code and maybe a few percent when you add threading from C++11/14.” (Sean Parent).

Przyznam szczerze, że nieco otworzyło mi to oczy:

GPU power CPU vectorization CPU threading Single Thread
75% 20% 4% 0,25%
#include <iostream>
#include <vector>
#include <variant>
#include <any>

using namespace std;

template <typename T1, typename T2>
class T {
    T1 a; T2 b;    
    public:
    T(T1 a, T2 b) : a(a), b(b) {}
    void show() {        
        cout << a << b;
    }    
};

int main() {
    T<char, const char*> t1('C', "++");
    T<int, const char*> t2(17, " nie taki straszny ;)\n");
    T<string, int> t3("66.", 6);

    typedef variant<T<char, const char*>, T<int, const char*>, T<string, int>> var_t;
    vector<var_t> var_v {t1, t2, t3};

    auto callShow = [](auto& obj) { obj.show(); };

    for (auto& obj : var_v)
        std::visit(callShow, obj);   

    cout << endl << "------" << endl;

    vector<any>anyv {1, 2.0, "trzy"};

    for(auto &i: anyv) {
        if (i.type() == typeid(int))
            cout << any_cast<int>(i) << endl;     
        if (i.type() == typeid(double))
            cout << any_cast<double>(i) << endl;     
        if (i.type() == typeid(const char *))
            cout << any_cast<const char *>(i) << endl;   
        if (i.type() == typeid(string))
            cout << any_cast<string>(i) << endl;    
    }
}

PS E:\cpp_fun> .\templ1.exe
C++17 nie taki straszny 😉
66.6
——
1
2
trzy

#include <iostream>
#include <range/v3/all.hpp> 
#include <string>
#include <vector>

using namespace std;
using namespace ranges;

int main()
{
    auto print = [](auto &i) {cout << i << " "; };    
    auto even = [](int i){ return 0 == i % 2; };
    auto square = [](int i) { return i * i; };
    auto end = ranges::end;

    vector<int> ints = views::ints(1, 50)  | views::filter(even) | 
                       views::transform(square) | views::slice(end-5, end) | 
                       ranges::to<vector>();

    ranges::for_each(ints, print);

    auto chars = views::iota('a', 'z'+1) | views::reverse
                       | ranges::to<vector>();
    
    ranges::for_each(chars, print);

    auto t = views::ints(0, 50) | 
         views::filter([](int i) { return i<20 ? true : false; }) | 
         ranges::to<vector>();
    
    ranges::for_each(t, print);
    cout << endl;    
}

PS E:\cpp_fun> .\ranges2.exe
1600 1764 1936 2116 2304 z y x w v u t s r q p o n m l k j i h g f e d c b a 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19

BTW: dzięki Bartkowi odkryłem, że nie boję się już lambd, a nawet je trochę lubię 😉

Flutter for the Web.

Flutter for the Web

Aplikacje Flutter w przeglądarce? Właśnie na Google Developers Days pojawiło się info o tym, że Flutter for the Web znalazło się w głównym repozytorium. Wystarczy zmienić flutter channel ze stable na master aby zgodnie z opisem tutaj odpalić aplikację w przeglądarce.  Drugi brakujący feature: Foreign Function Interface (FFI). Przyznam szczerze – te zmiany robią wrażenie. Kawał ciekawej i przydatnej technologii. Jedno jest pewne – będzie się działo!

Flutter for the Desktop

Dart i Flutter.

Fajny ten Dart. Jakoś wcześniej nie mogłem się do niego przekonać, ale moje ostatnie eksperymenta z ES6 trochę mi to ułatwiły.

Analizator i system typów robi spore wrażenie. OOP w Dart to chyba najlepsze co do tej pory widziałem – dziedziczenie, interfejsy, klasy i metody abstrakcyjne, mixins, overrides, listy inicjalizacyjne konstruktora, prosta inicjalizacja argumentów nazwanych konstruktora, po prostu trzeba to zobaczyć. Flutter to temat na kilka osobnych wpisów ;), a StatefullWidget mnie zachwycił. Poniżej mój pierwszy eksperyment – kolejne wcielenie apki do sterowania esp8266 za pomocą http request.

Kliknij w obrazek powyżej żeby zobaczyć plik źródłowy.

Widać w tym przyszłość i to raczej pozytywną, zarówno dla użytkowników, jak i programistów. A i jeszcze jedno – nie sądziłem, że to kiedyś powiem, ale Visual Studio Code to świetny edytor ;).

Mój plan na ten rok:

  • ogarnąć lepiej współczesną Javę (co tam w wersji >=10?)
  • dobrze poznać Dart + Flutter (coś mi mówi, że się przyda)
  • Kotlin – coś mi nie leży, muszę zidentyfikować dlaczego. Może to tylko kwestia przyzwyczajenia do niektórych elementów składni.

Aktualizacja: oficjalnie zaliczam Dart i Flutter do grona zjawisk i technologii, które mnie zafascynowały (patrz strip na górze ;)).

Kliknij w obrazek powyżej żeby zobaczyć plik źródłowy.

Syncthing + AspeQt-1.0.62.

Z najnowszej wersji AspeQt-1.0.62 (dostępna w Google Play i na Github) jestem wyjątkowo dumny pomimo, że nie ma w niej żadnych rewolucyjnych zmian:

  • Przebudowane z Qt-5.9.7 (min. API 16 = Android 4.1).
  • Poprawione błędy sterownika ftdi – działa z HSINDEX 0 = 115200bps.
  • Sprawdzanie dostępu do karty SD na Mashmallow i nowszych wersjach Androida

Jednak ta druga pozycja… to chyba najbardziej dołujący jak dotąd błąd z jakim przyszło mi się zmierzyć. Ale o co chodzi? Na nie-rootowanym Androidzie jedyna sensowna opcja obsługi portu szeregowego, a taki jest potrzebny do emulacji urządzeń SIO w 8-bitowym Atari, to tzw. usb-host mode i próba dogadania się z najpopularniejszym i najbardziej sensownym układem pozwalającym na taką komunikację, czyli FT232R firmy FTDI. Firma wypuściła w tym celu bibliotekę d2xx dla Androida, jednak nie jest ona zbyt szybka, a dodatkowo, licencja jest co najmniej problematyczna. Dawno temu odkryłem więc usb-serial-for-android. Dostęp do obiektów Javy w Qt5 i vice versa opisywałem już wcześniej – wystarczy wspomnieć, że bez JNI nie da rady tego ogarnąć, ale co zaskakujące, działa to bardzo szybko i wydajnie. Pod warunkiem, że działa ;). No i tu zaczyna się demotywująca część historii. Na niektórych urządzeniach AspeQt śmigał aż miło, ale użytkownicy zaczęli zgłaszać, że pomimo prawidłowej obsługi usb-host, na niektórych całkiem porządnych urządzeniach z Androidem nie działa. Niestety usb-serial-for-android od dwóch lat praktycznie rozwija tylko jedna osoba – Kai Morich w swoim forku – i to dzięki niemu udało się problem rozwiązać.

A teraz o moim ostatnim odkryciu: syncthing. AspeQt z HSINDEX 0 śmiga całkiem szybko, więc podmontowałem w nim na androidowym TVBoxie katalog, który przez syncthing jest synchronizowany po Wifi z laptopem i telefonem. Dzięki temu wszystko co ściągnę z internetów mogę od razu, bez skomplikowanych operacji, uruchomić na moim 8-bitowym super sprzęcie ;). Syncthing jest świetny, darmowy i bez reklam. W archowych repozytoriach są gotowe paczki dla Linuksa, a w Google Play apk dla Androida. Długo czegoś takiego szukałem: