2015-06-21 14 views
6

Eksperymentowałem z C++ próbując dowiedzieć się, jak mogę wydrukować liczby od 0 do n tak szybko, jak to możliwe.Jak mogę wydrukować znak nowej linii bez przepłukiwania bufora?

Początkowo tylko drukowanych wszystkich numerów z pętlą:

for (int i = 0; i < n; i++) 
{ 
    std::cout << i << std::endl; 
} 

Myślę jednak, że ten opróżnia bufor po każdej liczbie, że wyjścia, a na pewno, że musi trochę potrwać, więc próbowałem aby najpierw wydrukować wszystkie liczby do bufora (lub tak naprawdę, aż będzie pełna, jak się wydaje, wtedy wydaje się, że automatycznie się przepłukuje), a następnie przepłukać wszystko na raz. Jednak wydaje się, że drukowanie \ n po opróżnia bufor jak std :: endl więc pominięto go:

for (int i = 0; i < n; i++) 
{ 
    std::cout << i << ' '; 
} 
std::cout << std::endl; 

To wydaje się uruchomić około 10 razy szybciej niż w pierwszym przykładzie. Jednak chcę wiedzieć, jak przechowywać wszystkie wartości w buforze i przepłukać je wszystkie naraz, zamiast pozwolić jej wylewać za każdym razem, to staje się pełne, więc mam kilka pytań:

  1. to możliwe, aby wydrukować przełamane bez przepłukiwania bufora?
  2. Jak zmienić rozmiar bufora, aby móc przechowywać wszystkie wartości wewnątrz i wypróżnić je na samym końcu?
  3. Czy ta metoda generowania tekstu jest głupia? Jeśli tak, dlaczego i jaka byłaby lepsza alternatywa dla niego?

EDIT: Wydaje się, że moje wyniki były tendencyjne przez system laggy (Terminal app smartphone) ... Z szybszym systemem czasy wykonania wykazują żadnej znaczącej różnicy.

+0

Przed zapisaniem spróbuj zdekonfigurować flagę [unitbuf] (http://en.cppreference.com/w/cpp/io/manip/unitbuf) na 'cout'. –

+3

Nie używaj 'endl', ponieważ powoduje to przepłukanie itp. Zamiast tego użyj' '\ n'' lub' "\ n" '? Lub możesz dostać się do bardziej skomplikowanych sztuczek ustawiając tryb buforowania 'std :: cout' na pełne buforowanie. –

+0

'std :: cout << '\ n'' wyświetla nową linię. Nie należy ręcznie spłukiwać, chyba że masz ku temu powód. – nwp

Odpowiedz

3

TL, DR: Ogólnie pomocą '\n' zamiast std::endl jest większa od std::endl

Objaśnienie: std::endl powoduje płukanie buforem, podczas '\n' nie. Możesz jednak zauważyć lub nie zauważyć żadnego przyspieszenia w zależności od metody testowania, którą zastosujesz.

Rozważmy następujące pliki testowe:

endl.cpp:

#include <iostream> 

int main() { 
    for (int i = 0 ; i < 1000000 ; i++) { 
     std::cout << i << std::endl; 
    } 
} 

slashn.cpp:

#include <iostream> 

int main() { 
    for (int i = 0 ; i < 1000000 ; i++) { 
     std::cout << i << '\n'; 
    } 
} 

Obie te są opracowywane przy użyciu g++ na mój linux system i przejść następujące testy:

1. time ./a.out

Dla endl.cpp, trwa 19.415s.
Dla slashn.cpp zajmuje to 19,312 s.

2.time ./a.out >/dev/null

Na endl.cpp, trwa 0.397s
Na slashn.cpp, trwa 0.153s

3. time ./a.out >temp

Na endl.cpp, trwa 2.255s
W przypadku pliku slashn.cpp potrzeba to 0,065s.

Wniosek:'\n' to zdecydowanie szybciej (nawet praktycznie), ale różnica w prędkości może być zależna od innych czynników. W przypadku okna terminala czynnik ograniczający wydaje się zależeć od tego, jak szybko terminal może wyświetlić tekst. Ponieważ tekst jest wyświetlany na ekranie, a automatyczne przewijanie itp. Musi się wydarzyć, w trakcie wykonywania występują poważne spowolnienia. Z drugiej strony, w przypadku zwykłych plików (takich jak powyższy przykład: temp), szybkość, z jaką bufor jest przepuszczany, ma na niego duży wpływ. W przypadku niektórych plików specjalnych (takich jak /dev/null powyżej), ponieważ dane są po prostu zatopione w czarnej dziurze, efekt płukania nie wydaje się być skuteczny.

Powiązane problemy