Käyttämällä std::apply on std::odotettu C++23

C++

Virheenkäsittelyn virtaviivaistaminen C++23:ssa

Tehokas virheiden käsittely ja palautusarvojen hallinta on olennaista nykypäivän C++-kehityksessä. Tyypillinen tapa työskennellä {std::expected}-tyyppiä palauttavien funktioiden kanssa sisältää paljon tarkistuksia ja virheenkäsittelykoodia, mikä voi monimutkaistaa logiikkaa ja vaikeuttaa koodin ylläpitoa.

Tässä artikkelissa tutkitaan kehittyneemmän ja yleisemmän menetelmän käyttöä virheenhallinnan yksinkertaistamiseksi. Vähentääksemme tiivistelmäkoodia ja parantaaksemme luettavuutta, tutkimme `magic_apply`-menetelmän rakentamista, joka yhdistää monien {std::expected}-arvojen tulokset ja välittää ne toiselle funktiolle.

Komento Kuvaus
std::expected Mallityyppi, jota käytetään C++:ssa virheiden käsittelyyn ja joka pystyy tallentamaan sekä arvoja että virheitä.
std::unexpected Kun sitä käytetään std::expectedin kanssa, se edustaa odottamatonta virhearvoa.
template<typename...> Piirtää vaihtelevan mallin, jossa on ääretön määrä malliargumentteja, jotka se voi hyväksyä.
decltype Käytetään malliohjelmoinnissa, erityisesti lausekkeen tyypin selvittämiseen.
args.value() Jos std::expected-objektilla on arvo, se käyttää sen sisältämää arvoa.
args.has_value() Tarkistaa, onko std::expected-objektissa arvo.
(... && args.has_value()) Taita lauseke määrittääksesi, onko jokaisella std::expected-objektilla arvoja.
func(args.value()...) Käyttää std::expected-objektien arvoja kutsumaan menetelmää func.
return unexpected<Err>(args.error()...) Palauttaa odottamattoman virheen, joka sisältää virheet std::expected-objekteista.

Tehokas virheiden hallinta muuttuvien mallien avulla

The tyyppiä käytetään komentosarjoissa helpottamaan virheiden käsittelyä C++23:ssa. Päätavoitteena on kehittää yleinen toiminto nimeltä joka voi lähettää useiden tulosten arvot toiseen funktioon. Tekemällä tämän työläs virheentarkistus, joka on yleensä tarpeen työskennellessäsi monien kanssa std::expected arvot pienenevät. on melko joustava, koska se voi kestää minkä tahansa määrän parametreja käyttämällä vaihtelevia malleja. Ennen kuin kutsut funktion sisällön minkä tahansa objekti, peruslogiikka magic_apply käyttää fold-ilmaisua, , varmistaaksesi kaikki objekteilla on kelvolliset arvot.

Tämä idea on havainnollistettu ensimmäisessä komentosarjaesimerkissä käyttämällä yksinkertaisia ​​​​tyyppejä, kuten ja . Se määrittelee a funktio, joka suorittaa peruslaskennan, ja getA ja funktiot, jotka palaavat tyyppejä. Jos molemmat arvot alkaen ja getB ovat laillisia, voimme soittaa käyttämällä ; jos ei, virhe leviää. Tämä menetelmä parantaa luettavuutta ja ylläpidettävyyttä vähentämällä yleiskoodia. Samanlainen ajatus esitetään toisessa käsikirjoituksessa, mutta lähestymistavan monipuolisuuden korostamiseksi tyypit ja lambda functions käytetään.

C++-virheenkäsittelyn monimutkaisuuden vähentäminen komennolla `std::expected}

C++23-skripti, jossa käytetään vaihtelevia malleja

#include <expected>
#include <string>
#include <iostream>
#include <tuple>

using namespace std;

template<typename Func, typename... Args, typename Err>
auto magic_apply(Func func, const expected<Args, Err>&... args) -> expected<decltype(func(args.value()...)), Err> {
    if ((... && args.has_value())) {
        return func(args.value()...);
    } else {
        return unexpected<Err>(args.error()...);
    }
}

expected<int, string> getA(int x) {
    if (x > 0) return x;
    return unexpected<string>("Error in getA");
}

expected<double, string> getB(double y) {
    if (y > 0) return y;
    return unexpected<string>("Error in getB");
}

double compute_all(int a, double b) {
    return a + b;
}

int main() {
    auto result = magic_apply(compute_all, getA(10), getB(20.5));
    if (result) {
        cout << "Result: " << result.value() << endl;
    } else {
        cout << "Error: " << result.error() << endl;
    }
    return 0;
}

Erilaisten {std::expected} yhdistäminen tuottaa C++23-arvot

Lambda-funktioita käyttävä C++23-skripti

#include <expected>
#include <string>
#include <iostream>

using namespace std;

template<typename Func, typename... Args, typename Err>
auto magic_apply(Func func, const expected<Args, Err>&... args) -> expected<decltype(func(args.value()...)), Err> {
    bool all_valid = (args.has_value() && ...);
    if (all_valid) {
        return func(args.value()...);
    } else {
        return unexpected<Err>(args.error()...);
    }
}

expected<string, string> getA(bool flag) {
    if (flag) return "SuccessA";
    return unexpected<string>("Failed A");
}

expected<string, string> getB(bool flag) {
    if (flag) return "SuccessB";
    return unexpected<string>("Failed B");
}

string compute_all(const string& a, const string& b) {
    return a + " and " + b;
}

int main() {
    auto result = magic_apply(compute_all, getA(true), getB(true));
    if (result) {
        cout << "Result: " << result.value() << endl;
    } else {
        cout << "Error: " << result.error() << endl;
    }
    return 0;
}

C++-virheiden käsittelyn parantaminen variadic-malleilla

Kapasiteetti parantaa huomattavasti virheiden käsittelyä monimutkaisissa järjestelmissä on toinen tärkeä etu sen käyttämisestä C++:ssa. Monien asynkronisten toimien tulosten yhdistäminen saumattomasti on välttämätöntä tilanteissa, joissa ne antavat periksi tyyppejä. Sen lisäksi, että tämä menetelmä yksinkertaistaa koodia, se takaa vahvan virheenkäsittelyn. Monipuolisempia ja yleisempiä toimintoja voidaan luoda yhdistämällä mielivaltainen määrä arvot kanssa variadic templates.

Sen monipuolisuus mahdollistaa sen käytön funktioiden kanssa, jotka ottavat vastaan ​​erilaisia ​​argumentteja. Käyttöönotto yksinkertaistuu entisestään hyödyntämällä , joka päättelee automaattisesti yhdistetyn funktiokutsun palautustyypin. Lisäksi tätä tekniikkaa voidaan laajentaa hallitsemaan monimutkaisempia tehtäviä, mukaan lukien yhdistäminen arvot muilla virhetyypeillä tai arvojen muuttaminen ennen niiden lähettämistä funktioon. Mukautumiskykynsä ansiosta mallia voidaan käyttää monenlaisiin tehtäviin yksinkertaisista laskutoimituksista monimutkaisiin operaatioihin.

Usein kysyttyjä kysymyksiä Variadic-malleista ja std::expectedistä

  1. Mikä on ?
  2. Se on C++-mallipohja, joka voi sisältää virheen tai kelvollisen arvon ja jota käytetään virheiden hallintaan.
  3. Miten työtä?
  4. Se eliminoi toistuvien virhetarkistusten tarpeen yhdistämällä useiden tulosten tulokset arvot ja välittää ne funktiolle.
  5. Mitä ovat vaihtelevat mallit?
  6. Muuttujamallit tarjoavat suuren vapauden funktioiden suunnittelussa sallimalla funktioiden hyväksyä mielivaltaisen määrän parametreja.
  7. Miksi käyttää sisään ?
  8. Hyödyntämällä arvoja objektit määrittääkseen automaattisesti kutsuttavan funktion palautustyypin.
  9. Is pystyy käsittelemään erilaisia ​​virhetyyppejä?
  10. Kyllä, se voidaan saada toimimaan arvot, joissa on erilaisia ​​virhetyyppejä muutamalla säädöllä.
  11. Mitä etuja sen hyödyntäminen tuo tarjous?
  12. Virheiden käsittelyssä se tarjoaa ilmeisemmän ja selkeämmän lähestymistavan kuin perinteisemmät tekniikat, kuten poikkeukset tai palautuskoodit.
  13. Is osa ?
  14. Lisäksi , edustaa itse asiassa väärää arvoa.
  15. Voidaanko asynkronisia toimintoja käyttää ?
  16. Se on todellakin mukautuva käsiteltäväksi asynkronisten toimintojen palauttamat arvot.
  17. Mikä on taittoilmaisu?
  18. Tässä C++:n ominaisuutta nimeltä fold expression käytetään tarkistamaan, onko kaikki objektit sisältävät kelvollisia arvoja yksinkertaisella tavalla.

C++23:ssa yleisfunktion toteuttaminen useiden std::expected-arvojen käsittelemiseksi parantaa huomattavasti koodin luettavuutta ja yksinkertaistaa huomattavasti virheiden käsittelyä. Magic_apply-toiminto vähentää vakiokoodia ja parantaa ylläpidettävyyttä käyttämällä vaihtelevia malleja varmistaakseen, että kaikki odotetut arvot ovat oikein ennen käsittelyä. Tämä menetelmä tarjoaa joustavan ratkaisun, jota voidaan soveltaa erilaisiin tilanteisiin ja antaa nykyaikaiselle C++-ohjelmoinnille selkeämmän ja tehokkaamman tavan käsitellä vikoja.