Kāpēc Lambda izteiksme?
Apsveriet šādu apgalvojumu:
int myInt = 52;Šeit myInt ir identifikators, vērtība. 52 ir burtisks, prvalue. Šodien funkciju ir iespējams īpaši kodēt un ievietot 52 pozīcijā. Šādu funkciju sauc par lambda izteiksmi. Apsveriet arī šo īso programmu:
# iekļautizmantojot nosaukumvietu std;
int fn (int par)
int atbilde = par + 3;
atbilde uz atbildi;
int main ()
fn (5);
atgriešanās 0;
Šodien funkciju ir iespējams īpaši kodēt un ievietot funkcijas argumenta 5, funkcijas izsaukuma, fn (5) pozīcijā. Šādu funkciju sauc par lambda izteiksmi. Lambda izteiksme (funkcija) šajā pozīcijā ir sākotnējā vērtība.
Jebkurš literārs, izņemot virknes literālu, ir prvalue. Lambda izteiksme ir īpašs funkcijas dizains, kas derētu kā burtiskais kods. Tā ir anonīma (nenosaukta) funkcija. Šajā rakstā ir izskaidrota jaunā C ++ primārā izteiksme, ko sauc par lambda izteiksmi. Lai saprastu šo rakstu, ir nepieciešamas pamatzināšanas C ++ valodā.
Raksta saturs
- Lambda izteiksmes ilustrācija
- Lambda izteiksmes daļas
- Tver
- Klasiskās atzvanīšanas funkciju shēma ar Lambda izteiksmi
- Aizmugures-atgriešanās tips
- Slēgšana
- Secinājums
Lambda izteiksmes ilustrācija
Šajā programmā mainīgajam tiek piešķirta funkcija, kas ir lambda izteiksme:
# iekļautizmantojot nosaukumvietu std;
auto fn = [] (int param)
int atbilde = param + 3;
atbilde uz atbildi;
;
int main ()
auto mainīgais = fn (2);
cout << variab << '\n';
atgriešanās 0;
Rezultāts ir:
5Ārpus galvenās () funkcijas ir mainīgais fn. Tās tips ir auto. Auto šajā situācijā nozīmē, ka faktisko tipu, piemēram, int vai float, nosaka piešķiršanas operatora pareizais operands (=). Piešķiršanas operatora labajā pusē ir lambda izteiksme. Lambda izteiksme ir funkcija bez iepriekšējā atgriešanās veida. Ievērojiet kvadrātiekavu izmantošanu un atrašanās vietu, []. Funkcija atgriež 5, int, kas noteiks fn tipu.
Funkcijā main () ir paziņojums:
auto mainīgais = fn (2);Tas nozīmē, ka fn ārpus main () nonāk kā funkcijas identifikators. Tās netiešie parametri ir lambda izteiksmes parametri. Mainīgā tips ir auto.
Ņemiet vērā, ka lambda izteiksme beidzas ar semikolu, tāpat kā klases vai struktūras definīcija, beidzas ar semikolu.
Šajā programmā funkcija, kas ir lambda izteiksme, kas atgriež vērtību 5, ir arguments citai funkcijai:
# iekļautizmantojot nosaukumvietu std;
anulēt otherfn (int no1, int (* ptr) (int))
int no2 = (* ptr) (2);
cout << no1 << " << no2 << '\n';
int main ()
otherfn (4, [] (int param)
int atbilde = param + 3;
atbilde uz atbildi;
);
atgriešanās 0;
Rezultāts ir:
4 5Šeit ir divas funkcijas, lambda izteiksme un otrafn () funkcija. Lambda izteiksme ir otrais arguments otherfn (), ko sauc par main (). Ņemiet vērā, ka lambda funkcija (izteiksme) šajā izsaukumā nebeidzas ar semikolu, jo šeit tas ir arguments (nevis atsevišķa funkcija).
Funkcijas lambda parametrs otherfn () funkcijas definīcijā ir rādītājs funkcijai. Rādītājam ir nosaukums, ptr. Nosaukums ptr tiek izmantots definīcijā otherfn (), lai izsauktu lambda funkciju.
Paziņojums,
int no2 = (* ptr) (2);Definīcijā otherfn () tā izsauc funkciju lambda ar argumentu 2. Zvana atgriešanās vērtība "(* ptr) (2)" no lambda funkcijas tiek piešķirta no2.
Iepriekš minētā programma arī parāda, kā lambda funkciju var izmantot C ++ atzvanīšanas funkciju shēmā.
Lambda izteiksmes daļas
Tipiskas lambda funkcijas daļas ir šādas:
[] ()- [] ir uztveršanas klauzula. Tajā var būt preces.
- () ir paredzēts parametru sarakstam.
- ir paredzēts funkcijas ķermenim. Ja funkcija stāv atsevišķi, tad tai jābeidzas ar semikolu.
Tver
Funkcijas lambda definīciju var piešķirt mainīgajam vai izmantot kā argumentu citam funkcijas izsaukumam. Šāda funkcijas izsaukuma definīcijai kā parametram jābūt funkcijas rādītājam, kas atbilst lambda funkcijas definīcijai.
Lambda funkcijas definīcija atšķiras no parastās funkcijas definīcijas. To var piešķirt mainīgajam globālajā tvērumā; šo funkciju, kas piešķirta mainīgajam, var kodēt arī citas funkcijas iekšpusē. Kad tas tiek piešķirts globālās darbības mainīgajam, tā pamatteksts var redzēt citus mainīgos globālajā darbības jomā. Kad tas tiek piešķirts mainīgajam parastas funkcijas definīcijas ietvaros, tā pamatteksts var redzēt citus mainīgos lielumus tikai ar uztveršanas klauzulas palīdzību, [].
Uztveršanas klauzula [], kas pazīstama arī kā lambda ievada, ļauj mainīgos no apkārtējās (funkcijas) darbības jomas nosūtīt lambda izteiksmes funkcijas ķermenī. Tiek teikts, ka lambda izteiksmes funkcijas ķermenis uztver mainīgo, saņemot objektu. Bez uztveršanas klauzulas [] mainīgo nevar nosūtīt no apkārtējās darbības jomas uz lambda izteiksmes funkcijas ķermeni. Nākamā programma to ilustrē ar galveno () funkcijas darbības jomu kā apkārtējo:
# iekļautizmantojot nosaukumvietu std;
int main ()
int id = 5;
auto fn = [id] ()
cout << id << '\n';
;
fn ();
atgriešanās 0;
Rezultāts ir 5. Bez nosaukuma, id, iekšpusē [] lambda izteiksme nebūtu redzējusi main (main) funkcijas funkcijas main () funkciju.
Tveršana, izmantojot atsauci
Iepriekš minētais uztveršanas klauzulas izmantošanas piemērs ir tveršana pēc vērtības (sīkāku informāciju skatiet tālāk). Tverot ar atsauci, mainīgā atrašanās vieta (krātuve), piemēram,.g., ID, kas atrodas apkārt, ir pieejams lambda funkcijas korpusā. Tātad, mainot mainīgā vērtību lambda funkcijas ķermenī, mainīsies tā paša mainīgā vērtība apkārtējā darbības jomā. Lai to panāktu, pirms katra mainīgā, kas atkārtots uztveršanas klauzulā, ir zīme (&). To ilustrē šāda programma:
# iekļautizmantojot nosaukumvietu std;
int main ()
int id = 5; pludiņš ft = 2.3; char ch = 'A';
auto fn = [& id, & ft, & ch] ()
id = 6; pēdas = 3.4; ch = 'B';
;
fn ();
cout << id << ", " << ft << ", " << ch << '\n';
atgriešanās 0;
Rezultāts ir:
6, 3.4, BApstiprinot, ka mainīgo nosaukumi lambda izteiksmes funkcijas ķermenī ir vieni un tie paši mainīgie ārpus lambda izteiksmes.
Tveršana pēc vērtības
Uzņemot pēc vērtības, lambda funkcijas ķermenī tiek darīta pieejama mainīgā atrašanās vietas kopija un apkārtējā darbības joma. Lai gan lambda funkcijas ķermeņa mainīgais ir kopija, tā vērtību ķermeņa iekšienē tagad nevar mainīt. Lai panāktu tveršanu pēc vērtības, pirms katra mainīgā, kas atkārtots tveršanas klauzulā, nekas nav priekšā. To ilustrē šāda programma:
# iekļautizmantojot nosaukumvietu std;
int main ()
int id = 5; pludiņš ft = 2.3; char ch = 'A';
auto fn = [id, pēdas, ch] ()
// id = 6; pēdas = 3.4; ch = 'B';
cout << id << ", " << ft << ", " << ch << '\n';
;
fn ();
id = 6; pēdas = 3.4; ch = 'B';
cout << id << ", " << ft << ", " << ch << '\n';
atgriešanās 0;
Rezultāts ir:
5, 2.3, A6, 3.4, B
Ja komentāru indikators tiek noņemts, programma neapkopo. Sastādītājs izdos kļūdas ziņojumu, ka mainīgos, kas atrodas lambda izteiksmes funkcijas ķermeņa definīcijā, nevar mainīt. Lai gan mainīgos lielumus nevar mainīt lambda funkcijas iekšienē, tos var mainīt ārpus lambda funkcijas, kā parāda iepriekš minētās programmas izeja.
Jauktu uzņemšana
Uzņemšanu ar atsauci un tveršanu pēc vērtības var sajaukt, kā parāda šī programma:
# iekļautizmantojot nosaukumvietu std;
int main ()
int id = 5; pludiņš ft = 2.3; char ch = 'A'; bool bl = patiess;
auto fn = [id, pēdas, & ch, & bl] ()
ch = 'B'; bl = nepatiesa;
cout << id << ", " << ft << ", " << ch << ", " << bl << '\n';
;
fn ();
atgriešanās 0;
Rezultāts ir:
5, 2.3, B, 0Kad visi noķerti, ir norādīti:
Ja visi tveramie mainīgie tiek notverti ar atsauci, tad uztveršanas klauzulā pietiek tikai ar vienu un. To ilustrē šāda programma:
# iekļautizmantojot nosaukumvietu std;
int main ()
int id = 5; pludiņš ft = 2.3; char ch = 'A'; bool bl = patiess;
auto fn = [&] ()
id = 6; pēdas = 3.4; ch = 'B'; bl = nepatiesa;
;
fn ();
cout << id << ", " << ft << ", " << ch << ", " << bl << '\n';
atgriešanās 0;
Rezultāts ir:
6, 3.4, B, 0Ja daži mainīgie jāuztver ar atsauci, bet citi - pēc vērtības, tad viens & būs visu atsauču pārstāvis, un pārējiem pirms katra nekas netiks norādīts, kā parāda šī programma:
izmantojot nosaukumvietu std;int main ()
int id = 5; pludiņš ft = 2.3; char ch = 'A'; bool bl = patiess;
auto fn = [&, id, pēdas] ()
ch = 'B'; bl = nepatiesa;
cout << id << ", " << ft << ", " << ch << ", " << bl << '\n';
;
fn ();
atgriešanās 0;
Rezultāts ir:
5, 2.3, B, 0Ņemiet vērā, ka & atsevišķi (i.e., & kam neseko identifikators) jābūt pirmajai rakstzīmei uztveršanas klauzulā.
Kad visi ir notverti, pēc vērtības:
Ja visi tveramie mainīgie jāaptver pēc vērtības, tad uztveršanas klauzulā pietiek ar vienu =. To ilustrē šāda programma:
# iekļautizmantojot nosaukumvietu std;
int main ()
int id = 5; pludiņš ft = 2.3; char ch = 'A'; bool bl = patiess;
auto fn = [=] ()
cout << id << ", " << ft << ", " << ch << ", " << bl << '\n';
;
fn ();
atgriešanās 0;
Rezultāts ir:
5, 2.3, A, 1Piezīme: = pašlaik ir tikai lasāms.
Ja daži mainīgie jāuztver vērtībai, bet citi - ar atsauci, tad viens = apzīmē visus tikai lasāmos kopētos mainīgos un pārējiem katram būs &, kā parāda šī programma:
# iekļautizmantojot nosaukumvietu std;
int main ()
int id = 5; pludiņš ft = 2.3; char ch = 'A'; bool bl = patiess;
auto fn = [=, & ch, & bl] ()
ch = 'B'; bl = nepatiesa;
cout << id << ", " << ft << ", " << ch << ", " << bl << '\n';
;
fn ();
atgriešanās 0;
Rezultāts ir:
5, 2.3, B, 0Ņemiet vērā, ka vienīgajam = jābūt pirmajai rakstzīmei uztveršanas klauzulā.
Klasiskās atzvanīšanas funkciju shēma ar Lambda izteiksmi
Šī programma parāda, kā klasisko atzvanīšanas funkciju shēmu var veikt ar izteiksmi lambda:
# iekļautizmantojot nosaukumvietu std;
char * izeja;
auto cba = [] (char out [])
izeja = ārā;
;
void basicFunc (char ievade [], void (* pt) (char []))
(* pt) (ievade);
cout<<"for principal function"<<'\n';
anulēt fn ()
cout<<"Now"<<'\n';
int main ()
char input [] = "atzvanīšanas funkcijai";
galvenaisFunc (ievade, cba);
fn ();
cout<