std::iota în C++

Completează un interval cu valori consecutive: valoare, valoare + 1, valoare + 2...

Sintaxă
void iota(ForwardIt first, ForwardIt last, T valoare);

Ce face std::iota

std::iota (din <numeric>) scrie pe prima poziție valoarea dată, apoi o crește cu ++ pentru fiecare poziție următoare. Este modul rapid de a crea vectorul 1, 2, 3, …, n sau un vector de indici.

Funcționează cu orice tip care are ++, inclusiv char. Pentru un interval generat fără să-l stochezi, există std::views::iota.

Parametri

Parametru Descriere
first, last Intervalul completat.
valoare Prima valoare.

Ce returnează

Nimic.

Exemple

Exemplul 1: Numere și litere consecutive

#include <numeric>
#include <print>
#include <string>
#include <vector>

int main() {
    std::vector<int> locuri(10);
    std::iota(locuri.begin(), locuri.end(), 1);
    std::println("{}", locuri);

    std::string alfabet(6, ' ');
    std::iota(alfabet.begin(), alfabet.end(), 'a');
    std::println("{}", alfabet);
}

Rezultat

[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
abcdef

Exemplul 2: Indici sortați după valori

Sortăm indicii, nu datele: obținem ordinea concurenților fără să mutăm vectorul de timpi.

#include <algorithm>
#include <numeric>
#include <print>
#include <string>
#include <vector>

int main() {
    std::vector<std::string> nume{"Ana", "Bogdan", "Carla", "Dan"};
    std::vector<double> timpi{12.4, 11.8, 12.1, 13.0};

    std::vector<std::size_t> ordine(nume.size());
    std::iota(ordine.begin(), ordine.end(), 0);
    std::ranges::sort(ordine, [&](std::size_t a, std::size_t b) { return timpi[a] < timpi[b]; });

    for (std::size_t loc = 0; loc < ordine.size(); ++loc) {
        std::println("{}. {} ({:.1f} s)", loc + 1, nume[ordine[loc]], timpi[ordine[loc]]);
    }
}

Rezultat

1. Bogdan (11.8 s)
2. Carla (12.1 s)
3. Ana (12.4 s)
4. Dan (13.0 s)

Greșeli frecvente

  • Apelezi iota pe un vector gol: nu se întâmplă nimic. Creează vectorul cu dimensiunea dorită (std::vector<int> v(10);).

Comenzi înrudite

  • std::views::iota: Generează numerele consecutive dintr-un interval (sau la infinit) fără să le stocheze.
  • std::fill: Atribuie aceeași valoare tuturor elementelor unui interval (fill) sau primelor n elemente (fill_n).
  • std::generate: Completează un interval cu valorile returnate de apeluri succesive ale unei funcții.
  • std::accumulate: Adună toate elementele unui interval pornind de la o valoare inițială (sau le combină cu o operație dată).