2013-09-27 9 views
9

w C++ 11, jeśli użyję zakresu opartego na pętli na wektorze, czy zagwarantuje kolejność iteracji? powiedz, czy następujące bloki kodu są gwarantowane dla tego samego wyjścia?będzie bazował na pętli w C++ zachowując kolejność indeksów

vector<T> output; 
vector<U> V; 
for(auto v: V) output.push_back(f(v)); 

vs

for(int i =0; i < V.size(); ++i) output.push_back(f(V[i])); 

co jeśli to nie jest vector ale map itp?

+0

Można zoptymalizować nieco niepotrzebną kopię, wykonując 'auto &' zamiast 'auto' –

Odpowiedz

10

Tak, oba kody gwarantują to samo. Chociaż nie mam linku do standardu, możesz mieć wygląd: here. Cytuję: You can read that as "for all x in v" going through starting with v.begin() and iterating to v.end().

+0

lub [tutaj] (http://msdn.microsoft.com/en-us/library/vstudio/jj203382.aspx) Wykonuje instrukcję wielokrotnie i ** sekwencyjnie ** dla każdego elementu w wyrażeniu. – qxixp

10

Tak i nie (To zależy od używanego pojemnika):

  • Zakres oparciu o to jak pętla for (iterator pos = range.begin(); pos = ! range.end(); ++ pos) {/ * ze zmienną zakresu = * pos */...}
  • Operator [] może zrobić coś innego (np. operator std :: map wykonuje wyszukiwanie klucz i utwórz nowy wpis, jeśli klucz nie istnieje)

Przykład:

#include <iostream> 
#include <map> 

int main() 
{ 
    typedef std::map<int, int> map; 
    map m = { { 0, 0 }, { 2, 2 }, { 4, 4 } }; 
    for(const auto& e : m) { 
     std::cout << e.first << " "; 
    } 
    std::cout << std::endl; 
    for(map::size_type i = 0; i < m.size(); ++i) { 
     std::cout << m[i] << " "; 
    } 
    std::cout << std::endl; 
    return 0; 
} 

Wynikiem jest:

0 2 4 
0 0 2 0 4 

(drugi wynik może być dobry strzał w oddzielnym pieszo lub nawet przeznaczone)

+4

Powinieneś zauważyć, że tak czy inaczej, użytkownik robi coś strasznie nie tak w tym przykładzie. Jeśli masz indeksy sekwencyjne na 'mapie' z typem kluczowym' int', to nie powinieneś używać 'map', powinieneś używać' deque' lub 'vector' lub' array'. Jeśli nie masz indeksów sekwencyjnych, powinieneś iterować używając iteratorów, nie używając 'for (int i = 0; i OmnipotentEntity

10

Tak, są równoważne. Standardowe gwarancje w 6.5.4:

dla wielu oparte na zestawieniu postaci

dla (for-zakresie-deklaracji: wyrażenie) instrukcja

let zakres-Init za równoważne wyrażenie w nawiasie (wyrażenie)

i zakres oparte na zestawieniu postaci

dla (na wybiegu-deklaracji: usztywnione-listy startowe) oświadczenie

niech range-init będzie równoważne z listą z zaprogramowanymi początkami. W każdym przypadku, zakres oparty na rachunku odpowiada

{ 
    auto && __range = range-init; 
    for (auto __begin = begin-expr, 
     __end = end-expr; 
     __begin != __end; 
     ++__begin) { 
    for-range-declaration = *__begin; 
    statement 
    } 
} 

gdzie __range, __begin i __end zmienne są zdefiniowane jedynie do ekspozycji, a _RangeT jest typ ekspresji i czasu rozpoczęcia Wyrażenia i wyrażenia końcowe są określane w następujący sposób: wyrażenia, wyrażenia początkowy i końcowy są określane w następujący sposób:

- jeśli _RangeT jest typem tablicy, wyrażeniem początkowym i końcowym wyrażenia __range i __range + __bound, odpowiednio, gdzie __bound jest związaną tablicą.Jeśli _RangeT jest tablicą nieznanego rozmiaru lub tablicą niekompletnego typu, program jest źle sformułowany;

- jeśli _RangeT jest typem klasy, nieuwarunkowane-ids zaczynają i kończą się są wyszukiwane w zakresie klasy _RangeT tak, jak przy wyszukiwaniu dostępu do klasy członka (3.4.5) i jeśli jedno (lub oba) znajdują co najmniej jedno oświadczenie, begin- expr i end-expr to odpowiednio __range.begin() i __range.end();

- w przeciwnym razie, zaczynają lista_wyrażeń_sortowania końcówki wyrażenie to rozpocząć (_ zakres) i na końcu ( _range), odpowiednio, w których rozpoczyna się i kończy się wzrok z odnośnika argumentu zależne (3.4.2). Do celów tego wyszukiwania nazw przestrzeń nazw przestrzeń nazw jest skojarzoną przestrzenią nazw.

Chociaż twoje pytanie o mapę jest trochę bezsensowne. Jeśli jest to uporządkowana mapa i prawidłowo przeglądasz mapę, są one równoważne. Jeśli jest to mapa nieuporządkowana, twoje pytanie nie ma większego sensu.

Powiązane problemy