C++20 on C++-ohjelmointikielen ISO-standardiversio ISO/IEC 14882:2020, jonka kehitys alkoi C++17-standardin valmistumisen jälkeen. Standardiversio äänestettiin valmiiksi 15. helmikuuta 2020 ja hyväksytyksi ISO:n äänestyksessä syyskuussa. Standardiversio on julkaistu joulukuussa 2020. Edellinen standardiversio on ISO/IEC 14882:2017 C++17. Seuraava versio on C++23.
Kehityskohdat
Version kehityskohtia ovat muun muassa: moduulit rinnakkaisuuden jatkokehitys uusi synkronointikirjasto latch ja barrier luokat concepts ranges coroutines lambda-operaattoreiden käytön rajoitteiden vähentäminen decltype -yhteydessä [=, this] -kaappaus kolmisuuntainen vertailu nk. avaruusalusoperaattorilla <=> volatile-tuen merkintä suurelta osin vanhentuneeksi std::span ominaisuustestimakroja esikääntäjälle bittioperaatioita char8_t lisäys, char16_t ja char32_t muutokset (u"foo" ja U"foo") Unicode-tukeen vanhentuneeksi merkittyjen ominaisuuksien poistoja
Haskell-kielen tyyppinen konsepti-ominaisuus, ranges-kirjasto sekä std::future odotetaan olevan myös kehityskohteina.
Bjarne Stroustrup julkaisi työryhmälle paperin nimellä Remember the Vasa! viitaten Vasa-laivaan, jossa hän muistutti perusasioiden tärkeydestä ominaisuuksien määrän sijaan.
Stroustrup on sanonut C++20-standardista sen olevan ”kolmas merkittävä standardi” (kuudesta standardista), jossa merkittävä tarkoittaa sen ”muuttavan ihmisten ajattelutapaa”. Merkittäviksi kohdiksi mainitaan: concepts moduulit coroutines
Moduulien käyttö voi mahdollistaa esikääntäjästä luopumisen.
Lykättyjä tai hylättyjä ominaisuuksia contracts on lykätty versioon C++23/C++26. verkko-ohjelmointituen laajennukset (ISO/IEC TS 19216:2018) reflektio transaktiomuistin tuki
Standardia on kuitenkin myös kritisoitu päätöksistä säilyttää yhteensopivuus ja haluttomuudesta rikkoa ABI-yhteensopivuus. ABI:n muutoksilla pyrittäisiin saavuttamaan parempaa suorituskykyä.
std::format Standardikirjaston lisäys std::format on uusi vaihtoehto merkkijonojen muotoiluun, jonka tavoitteena on tarjota sama joustavuus kuin printf-sarjan funktioilla. Esimerkki: string message = format("The answer is {}.", 42);
Concepts ISO:n tekninen määrittely: ISO/IEC TS 19217:2015 GCC-kääntäjän versiossa 6 on tukea ominaisuudelle. Standardimallikirjasto sisältää ominaisuutta tukevia määrittelyitä.
Concepts on laajennus template-malleihin, jotka voivat toimia rajoitteina sallituille argumenteille tai parametreille. Constraint-rajoitteella voidaan valita ylikuormitukset ja erikoistumiset. Concepts toimii nimettynä joukkona rajoitteita, jotka arvioidaan käännösaikana. Tavoitteena on semanttisen tarkistuksen lisääminen syntaksitarkistuksen lisänä. Ominaisuuden on sanottu olevan puuttuva ominaisuus geneerisen ohjelmoinnin haittapuolien eliminoimiseksi.
Kielen nimettyjä vaatimuksia voidaan esittää Concepts-kirjaston avulla. Esimerkiksi std::hash-tuen vaatimuskonsepti Hashable voidaan ilmaista: template<typename T> concept Hashable = requires(T a) { { std::hash<T>{}(a) } -> std::convertible_to<std::size_t>;
Ranges Eric Nieblerin esimerkkitoteutus on julkaistu osana ehdotusta ominaisuuden lisäämiseksi C++ standardiin ja on myöhemmin hyväksytty standardiin std::ranges-kirjastoksi. Kirjasto rakentuu Concepts-kirjaston ominaisuuksille. Toteutus on koottava abstraktiokerros iteraattoreiden päällä.
Kirjasto tukee Haskell-kielen tapaan laiskaa arviointia, jossa ääretöntä määrää tukevasta toiminnosta suoritetaan vain tarvittava osa. Esimerkiksi kokonaislukujoukosta [1, ..] voidaan valita viisi numeroa ja tulostaa ne seuraavasti: auto num = view::take(view::ints(1), 5); ranges::for_each(num, [](int i){ std::cout << i << " "; });
Esimerkki (std::views on lyhenne std::ranges::views nimiavaruudelle): std::vector<int> ints{0,1,2,3,4,5}; auto even = [](int i){ return 0 == i % 2; }; auto square = [](int i) { return i * i; };
for (int i : ints | std::views::filter(even) | std::views::transform(square)) { std::cout << i << ' ';
.. joka tulostaa annettujen arvojen joukosta (0..5) parillisten numeroiden (0, 2, 4) neliöt seuraavasti: 0 4 16
Coroutines Coroutines on ylemmän tason kielien kuten Simulan ominaisuus, joka toimii vaihtoehtona aliohjelmille (alifunktioille): rutiinit ovat pinottomia. Coroutines on tarkoitettu tilanteisiin, jossa eri funktiot vaihtavat suoritusvuoroaan jatkaen aiemmasta tilasta. Coroutines sallii funktion suorittamisen pysäyttämisen ja jatkamisen ja lisää kolme uutta operaattoria: co_await, pysäyttää väliaikaisesti suorituksen palauttamatta arvoa kutsujalle co_yield, pysäyttää väliaikaisesti ja palauttaa arvon kutsujalle co_return, lopettaa suorituksen ja palauttaa arvon.
Uudet operaattorit mahdollistavat asynkronisen suorituksen, generaattorit ja laiskat funktiot.
Esimerkki: generator<int> iota(int n = 0) { while(true) co_yield n++; }
Boost-kirjastossa on esimerkkitoteutus C++:lle. Coroutines on hyväksytty mukaan C++20:een.
Moduulit Moduulit (modules) on vaihtoehtoinen tapa otsikkotiedostoille, joka muun muassa mahdollistaa makrojen eriyttämisen. Aiemmin ohjelmoijille on ollut mahdollista käyttää kolmea nimettyä kapselointia: muuttujanimi funktionimi luokkanimi
Moduulit lisäävät neljännen nimetyn kapseloinnin, joka sisältää kaikki kolme aikaisempaa yhdessä. Moduulit on hyväksytty mukaan C++20:een.
Epävirallinen tuki toiminnolle on ollut aiemmin Clang-kääntäjässä.
Esimerkki: // moduulissa: // helloworld.cpp export module helloworld; // module declaration import <iostream>; // import declaration
export void hello() { // export declaration std::cout << "Hello world!\n"; }
// moduulin käyttö: // main.cpp import helloworld; // import declaration
int main() { hello(); }
Lähteet
Aiheesta muualla Standardivedokset
Luokka:C++