Strategie optymalizacji wydajności w ostateczności [zamknięty]

Jest już wiele pytań dotyczących wydajności na tej stronie, ale wydaje mi się, że prawie wszystkie są bardzo specyficzne dla problemów i dość wąskie. I prawie wszystkie powtórzyć porady, aby uniknąć przedwczesnej optymalizacji.

Załóżmy:

  • Kod już działa poprawnie
  • wybrane algorytmy są już optymalne dla okoliczności problemu
  • kod został zmierzony, a procedury wykroczeń zostały odizolowane
  • wszystkie próby Optymalizacja będzie również mierzona, aby upewnić się, że nie pogarszają sprawy

To, czego szukam, to strategie i sztuczki, aby wycisnąć się do ostatnich kilku procent w krytycznym algorytmie, gdy nie ma nic innego do zrobienia, ale wszystko, co trzeba.

Najlepiej, staraj się, aby odpowiedzi były agnostyczne i wskazuj wszelkie strony w dół sugerowanych strategii, gdzie ma to zastosowanie.

Dodam odpowiedź z własnymi wstępnymi sugestiami i czekam na inne społeczność Stack Overflow może myśleć.

Author: jerryjvl, 2009-05-29

30 answers

Ok, definiujesz problem tam, gdzie wydaje się, że nie ma zbyt wiele miejsca na poprawę. To dość rzadkie, z mojego doświadczenia. Próbowałem to wyjaśnić w artykule dr Dobbs w listopadzie ' 93, zaczynając od konwencjonalnie dobrze zaprojektowanego nietrywialnego programu bez oczywistych strat i przeprowadzając go przez serię optymalizacji, aż jego czas zegar ścienny został zmniejszony z 48 sekund do 1,1 sekundy, a rozmiar kodu źródłowego został zmniejszony o współczynnik 4. Moje narzędzie diagnostyczne było to . Sekwencja zmian była następująca:

  • Pierwszym znalezionym problemem było użycie klastrów list (zwanych teraz "iteratorami" i "klasami kontenerów"), które zajmowały ponad połowę czasu. Zostały one zastąpione dość prostym kodem, co skróciło czas do 20 sekund.

  • Teraz największy czas-taker jest bardziej tworzenie listy. W procentach nie było tak duże wcześniej, ale teraz jest tak, ponieważ większy problem został usunięty. Znajduję sposób, aby to przyspieszyć, a czas spada do 17 sek.

  • Teraz jest trudniej znaleźć oczywistych winowajców, ale jest kilka mniejszych, z którymi mogę coś zrobić, a czas spada do 13 sek.

Teraz wygląda na to, że uderzyłem w ścianę. Próbki mówią mi dokładnie, co robi, ale nie mogę znaleźć niczego, co mogę poprawić. Następnie zastanawiam się nad podstawowym projektem programu, nad jego strukturą opartą na transakcjach i pytam, czy całe wyszukiwanie list, które robi, jest rzeczywiście wymagane przez wymagania problemu.

Potem natknąłem się na przeprojektowanie, gdzie kod programu jest generowany (za pomocą makr preprocesora) z mniejszego zestawu źródeł, i w którym program nie jest stale zastanawiając się rzeczy, które programista wie, że są dość przewidywalne. Innymi słowy, nie "interpretuj" sekwencji rzeczy do zrobienia, "Kompiluj" ją.

  • to przeprojektowanie zostało wykonane, zmniejszając kod źródłowy o współczynnik 4, a czas jest zredukowany do 10 sekund.

Teraz, ponieważ robi się tak szybko, że trudno jest go wypróbować, więc daję mu 10 razy więcej pracy do zrobienia, ale poniższe czasy są oparte na oryginalnym obciążeniu.

  • Więcej diagnozy ujawnia, że spędza czas w zarządzaniu kolejką. Podszewka skraca czas do 7 sekund.

  • Teraz dużym wyzwaniem jest druk diagnostyczny, który robiłem. Spłucz to-4 sekundy.

  • Teraz najwięcej chętnych to Telefony do malloc i za darmo . Recykling obiektów-2,6 sekundy.

  • Kontynuując próbkowanie, nadal znajduję operacje, które nie są ściśle konieczne - 1,1 sekundy.

Total speedup factor: 43.6

Teraz nie ma dwóch takich samych programów, ale w oprogramowaniu nie-zabawkowym zawsze widziałem taki postęp. Najpierw dostajesz rzeczy łatwe, a potem trudniejsze, aż dojdziesz do punktu malejących zwrotów. Wtedy wgląd, który uzyskasz, może prowadzić do przeprojektowanie, rozpoczęcie nowej rundy przyspieszeń, aż ponownie trafisz malejące zwroty. Teraz jest to punkt, w którym może mieć sens zastanawianie się, czy ++i lub i++ lub for(;;) lub while(1) są szybsze: rodzaje pytań, które widzę tak często na tak.

P. S. można się zastanawiać, dlaczego nie użyłem profilera. Odpowiedź jest taka, że prawie każdy z tych "problemów"był miejscem wywołania funkcji, które układają próbki. Profilerzy, nawet dzisiaj, ledwo dochodzą do wniosku, że instrukcje i instrukcje wywołania są ważniejsze do zlokalizowania i łatwiejsze do naprawienia niż całe funkcje. Zbudowałem do tego profilera, ale dla prawdziwej, brudnej intymności z tym, co robi kod, nie ma substytutu, aby wsadzić palce w to. Nie jest problemem, że liczba próbek jest mała, ponieważ żaden z problemów, które można znaleźć, nie jest tak mały, że łatwo je przegapić.

Dodał: jerryjvl Oto pierwszy problem. Informatyka składa się z niewielkiej liczby oddzielnych linii kodu, razem zajmując ponad połowę czasu:

 /* IF ALL TASKS DONE, SEND ITC_ACKOP, AND DELETE OP */
if (ptop->current_task >= ILST_LENGTH(ptop->tasklist){
. . .
/* FOR EACH OPERATION REQUEST */
for ( ptop = ILST_FIRST(oplist); ptop != NULL; ptop = ILST_NEXT(oplist, ptop)){
. . .
/* GET CURRENT TASK */
ptask = ILST_NTH(ptop->tasklist, ptop->current_task)

Używały one klastra list ILST (podobnego do klasy list). Są one zaimplementowane w zwykły sposób, przy czym "ukrywanie informacji" oznacza, że użytkownicy klasy nie powinni przejmować się tym, jak zostały zaimplementowane. Kiedy te linie zostały napisane (z około 800 linijek kodu), nie przyszło do głowy, że mogą one być "wąskim gardłem" (nienawidzę tego słowa). Są to po prostu zalecany sposób robienia rzeczy. Łatwo powiedzieć z perspektywy czasu , że należało ich unikać, ale z mojego doświadczeniawszystkie problemy z wydajnością są takie. Ogólnie rzecz biorąc, dobrze jest unikać tworzenia problemów z wydajnością. Jeszcze lepiej jest znaleźć i naprawić te, które są tworzone, mimo że "powinno się ich unikać" (z perspektywy czasu). Mam nadzieję, że to da trochę smaku.

Oto drugi problem, w dwóch oddzielnych linie:

 /* ADD TASK TO TASK LIST */ 
ILST_APPEND(ptop->tasklist, ptask)
. . .
/* ADD TRANSACTION TO TRANSACTION QUEUE */
ILST_APPEND(trnque, ptrn)

Są to listy budujące poprzez dołączanie elementów do ich końców. (Poprawka polegała na zebraniu elementów w tablicach i zbudowaniu wszystkich list naraz.) Ciekawostką jest to, że te stwierdzenia kosztowały tylko (tzn. były na stosie połączeń) 3/48 pierwotnego czasu, więc nie były w rzeczywistości dużym problemem na początku. Jednak po usunięciu pierwszego problemu kosztowały 3/20 czasu i tak były teraz "większe ryby". Ogólnie tak to jest.

I można dodać, że ten projekt został wydestylowany z prawdziwego projektu, w którym pomogłem. W tym projekcie problemy z wydajnością były znacznie bardziej dramatyczne( podobnie jak przyspieszenie), takie jak wywołanie procedury dostępu do bazy danych w wewnętrznej pętli, aby sprawdzić, czy zadanie zostało ukończone.

DODANO ODNIESIENIE: Kod źródłowy, zarówno oryginalny, jak i przeprojektowany, można znaleźć w www.ddj.com , za rok 1993, w aktach 9311.zip, files slug.asc i slug.zip .

EDIT 2011/11/26: Jest teraz sourceforge projekt zawierający kod źródłowy w Visual C++ i opis sposobu jego dostrojenia. Przechodzi tylko przez pierwszą połowę scenariusza opisanego powyżej i nie podąża dokładnie tą samą sekwencją, ale nadal otrzymuje przyspieszenie rzędu 2-3 wielkości.

 407
Author: Mike Dunlavey,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-23 10:31:30

Sugestie:

  • Pre-compute zamiast re-calculate : wszelkie pętle lub powtarzające się wywołania, które zawierają obliczenia, które mają stosunkowo ograniczony zakres wejść, rozważ wykonanie wyszukiwania (tablicy lub słownika), który zawiera wynik tych obliczeń dla wszystkich wartości w prawidłowym zakresie wejść. Następnie użyj prostego wyszukiwania wewnątrz algorytmu.
    Down-sides: Jeśli kilka z wstępnie obliczonych wartości są rzeczywiście używane, Może to pogorszyć sprawę, również wyszukiwanie może zająć znaczną pamięć.
  • nie używaj metod bibliotecznych: większość bibliotek musi być napisana, aby działały poprawnie w szerokim zakresie scenariuszy i wykonywały zerowe kontrole parametrów itp. Poprzez ponowną implementację metody możesz być w stanie usunąć wiele logiki, która nie ma zastosowania w dokładnych okolicznościach, których używasz.
    Down-sides: napisanie dodatkowego kodu oznacza większą powierzchnię dla błędów.
  • Użyj metod bibliotecznych : aby zaprzeczyć ja, biblioteki językowe są pisane przez ludzi, którzy są o wiele mądrzejsi niż ty lub ja; szanse są, że zrobili to lepiej i szybciej. Nie wdrażaj go samodzielnie, chyba że możesz go przyspieszyć (np.: zawsze mierz!)
  • Cheat: w niektórych przypadkach, chociaż dokładne obliczenia mogą istnieć dla Twojego problemu, możesz nie potrzebować "dokładnego", czasami przybliżenie może być "wystarczająco dobre" i znacznie szybsze w transakcji. Zadaj sobie pytanie, czy to naprawdę ważne, czy odpowiedź jest o 1%? 5%? parzyste 10%?
    Down-sides : No cóż... odpowiedź nie będzie dokładna.
 179
Author: jerryjvl,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-29 15:16:46

Jeśli nie możesz już poprawić wydajności-sprawdź, czy możesz poprawić postrzeganą wydajność.

Możesz nie być w stanie przyspieszyć algorytmu fooCalc, ale często istnieją sposoby, aby Twoja aplikacja wydawała się bardziej responsywna dla użytkownika.

Kilka przykładów:

  • przewidywanie, co będzie robił użytkownik aby zażądać i rozpocząć pracę nad tym before then
  • wyświetlanie wyników jako wchodzą, zamiast wszystkich naraz na end
  • dokładny miernik postępu

To nie sprawi, że twój program będzie szybszy, ale może sprawić, że użytkownicy będą zadowoleni z szybkości, jaką posiadasz.

 158
Author: kenj0418,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-09-13 15:37:49

Większość życia spędzam właśnie w tym miejscu. Szeroki zakres uderzeń polega na uruchomieniu profilera i doprowadzeniu go do nagrywania:

  • Brak pamięci podręcznej . Data cache jest źródłem # 1 straganów w większości programów. Popraw szybkość uderzeń pamięci podręcznej poprzez reorganizację naruszających struktury danych, aby miały lepszą lokalizację; struktury pakietów i typy numeryczne w celu wyeliminowania zmarnowanych bajtów (a tym samym zmarnowanych pobrań pamięci podręcznej); prefetch danych, gdzie to możliwe, aby zmniejszyć stragany.
  • Load-hit-stores . Założenia kompilatora dotyczące aliasingu wskaźników i przypadków przenoszenia danych między odłączonymi zestawami rejestrów za pośrednictwem pamięci mogą powodować pewne patologiczne zachowanie, które powoduje, że cały procesor jest oczyszczany podczas operacji ładowania. Znajdź miejsca, w których pływaki, wektory i Int są rzucane do siebie i eliminuj je. Użyj __restrict, Aby Obiecać kompilatorowi aliasing.
  • operacje Mikrokodowane. Większość procesorów ma pewne operacje, których nie można pipelinować, ale zamiast tego Uruchom mały podprogram zapisany w ROM. Przykładami PowerPC są mnożenie, dzielenie i przesunięcie przez zmienną kwoty. Problem polega na tym, że cały rurociąg przestaje działać podczas wykonywania tej operacji. Spróbuj wyeliminować użycie tych operacji lub przynajmniej podzielić je na ich składowe operacje pipelined, aby uzyskać korzyści supersalarnej wysyłki na cokolwiek robi reszta programu.
  • / Align = "center" bgcolor = "# e0ffe0 " / cesarz chin / / align = center / Te też opróżniają rurociąg. Znajdź przypadki, w których procesor spędza dużo czasu na uzupełnianiu rury po gałęzi i używa hintingu gałęzi, jeśli jest dostępny, aby częściej przewidywać poprawne przewidywanie. Albo jeszcze lepiej, jeśli to możliwe, zastąp gałęzie ruchami warunkowymi, szczególnie po operacjach zmiennoprzecinkowych, ponieważ ich pipe jest zwykle głębszy, a odczytanie FLAG warunkowych po fcmp może spowodować zatrzymanie.
  • sekwencyjne operacje zmiennoprzecinkowe . Zrób te SIMD.

I jeszcze jedna rzecz, którą lubię do:

  • Ustaw kompilator na output Assembly listings i spójrz, co emituje dla funkcji hotspot w Twoim kodzie. Wszystkie te sprytne optymalizacje, które "dobry kompilator powinien być w stanie zrobić dla ciebie automatycznie"? Możliwe, że Twój kompilator ich nie robi. Widziałem jak GCC emituje naprawdę kod WTF.
 132
Author: Crashworks,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-29 22:37:01

Rzuć w nią więcej sprzętu!

 76
Author: sisve,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-29 14:32:26

Więcej propozycji:

  • Avoid I/o: dowolne I / O (dysk, sieć, porty itp.) jest zawsze będzie znacznie wolniejszy niż jakikolwiek kod, który jest wykonywanie obliczeń, więc pozbądź się wszelkich I / O, które robisz nie koniecznie.

  • Move I / O up-front: załaduj wszystkie dane, które zamierzasz potrzeba do obliczeń z góry, tak, że nie powtarzające się wejścia/Wyjścia wewnątrz rdzenia krytycznego algorytmu (i być może w wyniku wielokrotnego szukania dysku, gdy Ładowanie wszystkie dane w jednym trafieniu mogą uniknąć poszukiwania).

  • Delay I / O: nie zapisuj swoich wyników, dopóki obliczanie jest skończone, przechowywać je w strukturze danych i potem wyrzuć to za jednym zamachem na koniec, gdy ciężka praca zrobione.

  • Threaded I / o: dla odważnych, połącz " I / O z góry " lub "opóźnienie we / wy" z faktycznym obliczeniem przez przesuwając ładunek w równoległy wątek, tak aby podczas ładujesz więcej danych, nad którymi możesz pracować obliczenia na danych, które już posiadasz, lub podczas obliczania następnego partii danych można jednocześnie zapisywać wyniki z ostatniej partii.

 56
Author: Peter Mortensen,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-09-13 16:06:59

Ponieważ wiele problemów z wydajnością dotyczy problemów z bazą danych, podam Ci kilka konkretnych rzeczy, na które powinieneś zwrócić uwagę podczas strojenia zapytań i procedur składowanych.

Unikaj kursorów w większości baz danych. Unikaj zapętlania. W większości przypadków dostęp do danych powinien być oparty na ustawieniach, a nie na przetwarzaniu rekordów. Obejmuje to nie ponowne użycie procedury składowanej pojedynczego rekordu, gdy chcesz wstawić 1 000 000 rekordów na raz.

Nigdy nie używaj select *, zwracaj tylko pola, których potrzebujesz. To jest szczególnie prawdziwe, jeśli są jakieś połączenia, ponieważ pola przyłączenia zostaną powtórzone, a tym samym spowodują nienecesary obciążenia zarówno na serwerze, jak i w sieci.

Unikaj stosowania skorelowanych zapytań podrzędnych. Użyj joins (w tym joins do tabel pochodnych, o ile to możliwe) (wiem, że to prawda w przypadku Microsoft SQL Server, ale przetestuj porady Podczas korzystania z różnych backendów).

Indeks, indeks, indeks. I zaktualizuj te statystyki, jeśli mają zastosowanie do twojej bazy danych.

Wykonaj zapytanie sargable . Znaczenie unikaj rzeczy, które uniemożliwiają użycie indeksów, takich jak używanie wieloznacznych znaków w pierwszym znaku klauzuli like lub funkcji w join lub jako lewej części instrukcji where.

Użyj poprawnych typów danych. Szybciej jest wykonać obliczenia daty na polu daty niż próbować przekonwertować typ danych łańcuchowych na typ danych daty, a następnie wykonać obliczenia.

Nigdy nie wkładaj żadnej pętli do spustu!

Większość baz danych ma sposób na sprawdzenie wykonania zapytania będzie po wszystkim. W Microsoft SQL Server jest to tzw. plan wykonania. Sprawdź te pierwsze, aby zobaczyć, gdzie leżą obszary problemowe.

Zastanów się, jak często zapytanie jest uruchamiane, a także jak długo trwa, określając, co należy zoptymalizować. Czasami możesz uzyskać więcej wydajności od niewielkiego dostosowania do zapytania, które działa miliony razy dziennie, niż od usunięcia zapytania long_running, które działa tylko raz w miesiącu.

Użyj jakiegoś narzędzia do profilowania, aby dowiedzieć się, co jest naprawdę są wysyłane do i z bazy danych. Pamiętam jeden raz w przeszłości, kiedy nie mogliśmy dowiedzieć się, dlaczego strona była tak powolna, aby załadować, gdy procedura składowana była szybka i okazało się poprzez profilowanie, że strona internetowa pytała o zapytanie wiele razy, a nie raz.

Profiler pomoże Ci również znaleźć, kto kogo blokuje. Niektóre zapytania, które wykonują się szybko, gdy działają samodzielnie, mogą stać się naprawdę powolne z powodu blokad z innych zapytań.

 46
Author: HLGEM,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-01-26 17:26:24

Obecnie najważniejszym czynnikiem ograniczającym jest limitowana pamięć bandwitdh . Multicores tylko to pogarsza, ponieważ przepustowość jest dzielona między rdzenie. Ponadto ograniczony obszar chipów poświęcony implementacji pamięci podręcznej jest również podzielony między rdzenie i wątki, pogarszając ten problem jeszcze bardziej. Wreszcie, sygnalizacja międzyukładowa potrzebna do zachowania spójności różnych pamięci podręcznych również wzrasta wraz ze zwiększoną liczbą rdzeni. To również dodaje karę.

Są to efekty, którymi musisz zarządzać. Czasami poprzez mikro zarządzanie kodem, ale czasami poprzez uważne rozważenie i refaktoryzację.

Wiele komentarzy już wspomina o kodzie przyjaznym pamięci podręcznej. Istnieją co najmniej dwa różne smaki tego:

  • unikaj opóźnień pobierania pamięci.
  • niższe ciśnienie szyny pamięci (przepustowość).

Pierwszy problem polega głównie na tym, aby wzorce dostępu do danych były bardziej regularne, umożliwiając prefetcher sprzętowy pracuj wydajnie. Unikaj dynamicznej alokacji pamięci, która rozprzestrzenia obiekty danych w pamięci. Używaj kontenerów liniowych zamiast połączonych list, skrótów i drzew.

Drugi problem ma związek z poprawą ponownego wykorzystania danych. Zmodyfikuj algorytmy tak, aby działały na podzbiorach danych, które mieszczą się w dostępnej pamięci podręcznej, i wykorzystuj je ponownie w miarę możliwości, gdy są jeszcze w pamięci podręcznej.

Ściślejsze Pakowanie danych i upewnienie się, że wszystkie dane są używane w liniach pamięci podręcznej w pętlach hot, pomoże unikaj tych innych efektów i pozwól na dopasowanie większej ilości użytecznych danych w pamięci podręcznej.

 29
Author: Mats N,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-06-19 16:51:08
  • na jakim sprzęcie pracujesz? Czy możesz używać optymalizacji specyficznych dla platformy (takich jak wektoryzacja)?
  • możesz dostać lepszy kompilator? Np. przesiadka z GCC na Intela?
  • Czy możesz sprawić, że Twój algorytm będzie działał równolegle?
  • Czy można zmniejszyć liczbę braków pamięci podręcznej poprzez reorganizację danych?
  • Czy można wyłączyć asserts?
  • Micro-optimize dla Twojego kompilatora i platformy. W stylu, "W if / else, umieść najpowszechniejsze stwierdzenie jako pierwsze"
 25
Author: Johan Kotlinski,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-31 00:52:09
  • procedury Inline (eliminacja wywołania/powrotu i wypychania parametrów)
  • spróbuj wyeliminować testy/przełączniki za pomocą table look ups (jeśli są szybsze)
  • rozwiń pętle (urządzenie Duffa) do punktu, w którym po prostu mieszczą się w pamięci podręcznej procesora
  • Zlokalizuj dostęp do pamięci, aby nie uszkodzić pamięci podręcznej
  • Zlokalizuj powiązane obliczenia, jeśli optymalizator jeszcze tego nie robi
  • wyeliminuj niezmienniki pętli, jeśli optymalizator jeszcze tego nie robi
 15
Author: plinth,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-29 15:05:04

Powinieneś prawdopodobnie rozważyć "perspektywę Google", tzn. określić, w jaki sposób Twoja aplikacja może stać się w dużej mierze równoległa i współbieżna, co nieuchronnie oznacza również w pewnym momencie spojrzenie na dystrybucję aplikacji na różnych maszynach i sieciach, tak aby mogła idealnie skalować się prawie liniowo ze sprzętem, który na nią rzucasz.

Z drugiej strony ludzie z Google są również znani z tego, że rzucają dużo siły roboczej i zasobów w rozwiązywaniu niektórych problemów w projekty, narzędzia i infrastruktura, z których korzystają, takie jak na przykład optymalizacja całego programu dla gcc poprzez dedykowany zespół inżynierów hakujących wnętrza gcc w celu przygotowania go do typowych dla Google scenariuszy przypadków użycia.

Podobnie profilowanie aplikacji nie oznacza już po prostu profilowania kodu programu, ale także wszystkich otaczających go systemów i infrastruktury (sieci, przełączniki, serwer, macierze RAID) w celu identyfikacji nadmiarowości i optymalizacji potencjał z punktu widzenia systemu.

 15
Author: none,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-09-13 19:31:54

Chociaż podoba mi się odpowiedź Mike 'a Dunlavey' a, w rzeczywistości jest to świetna odpowiedź z podporowym przykładem, myślę, że można ją wyrazić bardzo prosto w ten sposób:

Najpierw dowiedz się, co zajmuje najwięcej czasu i zrozum dlaczego.

Jest to proces identyfikacji Wieprzy czasu, który pomaga zrozumieć, gdzie należy udoskonalić algorytm. Jest to jedyna wszechogarniająca odpowiedź językowa, jaką mogę znaleźć na problem, który już powinien być w pełni zoptymalizowany. Również zakładając, że chcesz być architekturą niezależną w dążeniu do prędkości.

Więc chociaż algorytm może być zoptymalizowany, jego implementacja może nie być. Identyfikacja pozwala wiedzieć, która część jest która: algorytm lub implementacja. Więc ten, który ma najwięcej czasu, jest twoim głównym kandydatem do przeglądu. Ale skoro mówisz, że chcesz wycisnąć kilka ostatnich%, możesz również zbadać mniejsze części, Części, których nie zbadałeś tak dokładnie na początku.

Wreszcie odrobina prób i błędów z wynikami dotyczącymi różnych sposobów wdrożenia tego samego rozwiązania lub potencjalnie różnych algorytmów może przynieść spostrzeżenia, które pomagają zidentyfikować marnowanie czasu i oszczędzanie czasu.

HPH, asoudmove.

 15
Author: asoundmove,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-01-28 03:37:45
  • kiedy dojdziesz do punktu, w którym używasz wydajnych algorytmów, pojawia się pytanie, Czego Potrzebujesz więcej prędkości lub pamięci. Użyj buforowania, aby" zapłacić " w pamięci dla większej prędkości lub użyj obliczeń, aby zmniejszyć ślad pamięci.
  • Jeśli to możliwe (i bardziej opłacalne) rzuć sprzęt w problem - szybszy procesor, więcej pamięci lub HD może rozwiązać problem szybciej niż próbuje go kodować.
  • Użyj paralelizacji jeśli to możliwe-Uruchom część kodu na wiele wątków.
  • Użyj odpowiedniego narzędzia do zadania . niektóre języki programowania tworzą bardziej wydajny kod, używając kodu zarządzanego (np. Java/. NET) przyspieszają rozwój, ale natywne języki programowania tworzą szybciej działający kod.
  • Micro optimize . Można użyć zoptymalizowanego montażu, aby przyspieszyć małe kawałki kodu, przy użyciu optymalizacji SSE/wektorowej w odpowiednich miejscach może znacznie zwiększyć wydajność.
 12
Author: Dror Helper,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-30 15:39:32

Divide and conquer

Jeśli przetwarzany zbiór danych jest zbyt duży, wykonaj pętlę nad jego fragmentami. Jeśli dobrze wykonałeś swój kod, implementacja powinna być łatwa. Jeśli masz program monolityczny, teraz wiesz lepiej.

 12
Author: MPelletier,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-03-22 03:21:21

Przede wszystkim, jak wspomniano w kilku wcześniejszych odpowiedziach, dowiedz się, co gryzie wydajność - czy to pamięć, procesor, sieć, baza danych lub coś innego. Zależy od tego...

  • ...jeśli to pamięć-znajdź jedną z książek napisanych dawno temu przez Knutha, jedną z serii" Sztuka programowania komputerowego". Najprawdopodobniej chodzi o sortowanie i wyszukiwanie - jeśli moja pamięć jest zła, musisz się dowiedzieć, w którym mówi o tym, jak radzić sobie z powolnym przechowywaniem danych na taśmie. Mentalnie przekształć swoją parę pamięci/taśmy w parę pamięci podręcznej/pamięci głównej (lub odpowiednio w parze pamięci podręcznej L1/L2). Przestudiuj wszystkie sztuczki, które opisuje-jeśli nie znajdziesz czegoś, co rozwiąże twój problem, zatrudnij profesjonalnego informatyka do przeprowadzenia profesjonalnych badań. Jeśli twój problem z pamięcią jest przez przypadek z FFT (pamięć podręczna chybiona przy indeksach odwróconych bitami podczas wykonywania radix-2) to nie zatrudniaj naukowca - zamiast tego, ręcznie Optymalizuj przechodzi jeden po drugim, aż albo wygrasz, albo trafisz w ślepy zaułek. Wspomniałeś o wyciśnięciu do ostatnich kilku procent, prawda? Jeśli jest to kilka rzeczywiście najprawdopodobniej wygrasz.

  • ...jeśli jest to procesor-Przełącz na język asemblacji. Study processor specification - what takes klecks , VLIW, SIMD. Wywołania funkcji są najprawdopodobniej zamiennymi kleszczożercami. Poznaj transformacje pętli-rurociąg, rozwiń. Mnożenia i podziały mogą być wymienne / interpolowane za pomocą przesunięć bitowych (mnożenia przez małe liczby całkowite mogą być wymienne z dodatkami). Spróbuj trików z krótszymi danymi - jeśli masz szczęście jedna instrukcja z 64 bitami może okazać się wymienna z dwoma na 32 lub nawet 4 na 16 lub 8 na 8 bitach go figure. Spróbuj również dłuższe DANE - np. twoje obliczenia float mogą okazać się wolniejsze niż podwójne w danym procesorze. Jeśli masz rzeczy trygonometryczne, walczyć z wstępnie obliczonych tabel; należy również pamiętać, że sinus o małej wartości może być zastąpiony przez tę wartość, jeśli utrata precyzja mieści się w dozwolonych granicach.

  • ...jeśli jest to sieć-pomyśl o kompresji danych, które przekazujesz. Zamień transfer XML na binarny. Protokoły badań. Spróbuj UDP zamiast TCP, jeśli w jakiś sposób poradzisz sobie z utratą danych.

  • ...jeśli to baza danych, to wejdź na dowolne forum bazy danych i poproś o radę. Dane w pamięci-siatka, optymalizacja planu zapytań itp itd.

HTH:)

 11
Author: gnat,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-07-29 03:28:14

Myślę, że zostało to już powiedziane w inny sposób. Ale kiedy masz do czynienia z algorytmem intensywnym dla procesora, powinieneś uprościć wszystko wewnątrz najbardziej wewnętrznej pętli kosztem wszystkiego innego.

Dla niektórych może to wydawać się oczywiste, ale staram się skupić na tym, niezależnie od języka, z którym pracuję. Jeśli na przykład masz do czynienia z zagnieżdżonymi pętlami i znajdziesz okazję, aby obniżyć poziom kodu, możesz w niektórych przypadkach drastycznie przyspieszyć Twój kod. Innym przykładem są małe rzeczy do przemyślenia, takie jak praca z liczbami całkowitymi zamiast zmiennoprzecinkowymi, gdy tylko możesz, i używanie mnożenia zamiast dzielenia, gdy tylko możesz. Ponownie, Są to rzeczy, które powinny być brane pod uwagę dla najbardziej wewnętrznej pętli.

Czasami możesz odnieść korzyść z wykonywania operacji matematycznych na liczbie całkowitej wewnątrz pętli wewnętrznej, a następnie skalowania jej do zmiennej zmiennoprzecinkowej, z którą możesz później pracować. Jest to przykład poświęcania prędkości w jednej sekcji, aby poprawić prędkość w innej, ale w niektórych przypadkach zapłata może być tego warta.

 8
Author: Steve Wortham,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-29 22:07:45

Buforowanie! tanim sposobem (w wysiłku programisty), aby zrobić prawie wszystko szybciej, jest dodanie warstwy abstrakcji buforowania do dowolnego obszaru ruchu danych programu. Czy to we / wy, czy tylko przekazywanie / tworzenie obiektów lub struktur. Często łatwo jest dodać bufory do klas fabrycznych i czytników / pisarzy.

Czasami pamięć podręczna nie zyska wiele, ale jest to łatwa metoda, aby po prostu dodać pamięć podręczną i wyłączyć ją tam, gdzie to nie pomaga. Często spotykałem się z tym, że zyskało to ogromne wydajność bez konieczności mikro-analizy kodu.

 8
Author: Killroy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-09-13 19:29:36

Bardzo trudno udzielić ogólnej odpowiedzi na to pytanie. To naprawdę zależy od domeny problemu i implementacji technicznej. Ogólna technika, która jest dość neutralna językowo: identyfikuje hotspoty kodu, których nie można wyeliminować, i ręcznie optymalizuje kod asemblera.

 7
Author: dschwarz,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-29 14:32:36

Ostatnie kilka % jest bardzo zależne od procesora i aplikacji....

  • architektury pamięci podręcznej różnią się, niektóre układy mają wbudowaną pamięć RAM można mapować bezpośrednio, ARM ' s (czasami) mają wektor Jednostka, SH4 to użyteczny kod matrycy. Czy istnieje GPU - może shader jest dobrym rozwiązaniem. TMS320 są bardzo wrażliwe na gałęzie wewnątrz pętli (czyli oddzielne pętle i przenieść warunki Na Zewnątrz, jeśli to możliwe).

Lista jest długa.... Ale takie rzeczy naprawdę są The last Ośrodek wypoczynkowy...

Build for x86, and run Valgrind / Cachegrind against the code dla prawidłowego profilowania wydajności. Lub Texas Instruments" CCStudio ma słodki profiler. Wtedy naprawdę będziesz wiedział, gdzie żeby się skupić...

 7
Author: Peter Mortensen,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-09-13 16:03:00

Did you know that a CAT6 cable is capable of 10x better shielding off extrenal inteferences than a default Cat5e UTP cable?

Dla wszelkich projektów nie-offline, mając najlepsze oprogramowanie i najlepszy sprzęt, jeśli przepustowość jest słaba, to ta cienka linia będzie wyciskać Dane i daje opóźnienia, choć w milisekundach... ale jeśli mówisz o ostatnich kroplach, to jest kilka kropli zdobytych, 24/7 dla każdego opakowania wysłanego lub otrzymanego.

 7
Author: Sam,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-01-29 02:23:07

Spędziłem trochę czasu pracując nad optymalizacją systemów biznesowych klientów / serwerów działających w sieciach o niskiej przepustowości i długim opóźnieniu (np. satelitarnych, zdalnych, offshore) i byłem w stanie osiągnąć kilka dramatycznych ulepszeń wydajności przy dość powtarzalnym procesie.

  • Miara: zacznij od zrozumienia podstawowej przepustowości i topologii sieci. Rozmawiaj z odpowiednimi ludźmi sieciowymi w firmie i korzystaj z podstawowych narzędzi, takich jak ping i traceroute ustalenie (co najmniej) opóźnienia sieci z każdej lokalizacji klienta, w typowych okresach operacyjnych. Następnie wykonaj dokładne pomiary czasu konkretnych funkcji użytkownika końcowego, które wyświetlają problematyczne objawy. Zapisz wszystkie te pomiary, wraz z ich lokalizacjami, datami i godzinami. Rozważ wbudowanie funkcji "testowania wydajności sieci" użytkownika końcowego w aplikacji klienckiej, umożliwiając zaawansowanym użytkownikom udział w procesie doskonalenia; wzmocnienie ich w ten sposób może mieć ogromny wpływ psychologiczny, gdy masz do czynienia z użytkownikami sfrustrowanymi przez słabo działający system.

  • Analizuj : używając wszelkich dostępnych metod rejestrowania, aby dokładnie określić, jakie dane są przesyłane i odbierane podczas wykonywania dotkniętych operacji. Idealnie, aplikacja może przechwytywać dane przesyłane i odbierane zarówno przez Klienta, jak i serwer. Jeśli obejmują one również znaczniki czasu, jeszcze lepiej. Jeśli wystarczające logowanie NIE JEST dostępne (np. zamknięty system lub niemożność wdrożenia modyfikacji w środowisku produkcyjnym), użyj sniffera sieciowego i upewnij się, że naprawdę rozumiesz, co dzieje się na poziomie sieci.

  • Cache : poszukaj przypadków powtarzalnego przesyłania statycznych lub rzadko zmienianych danych i rozważ odpowiednią strategię buforowania. Typowe przykłady obejmują wartości "wybierz listę" lub inne "jednostki referencyjne" , które mogą być zaskakująco duże w niektórych firmach aplikacje. W wielu przypadkach użytkownicy mogą zaakceptować, że muszą ponownie uruchomić lub odświeżyć aplikację, aby zaktualizować rzadko aktualizowane dane, zwłaszcza jeśli może to znacznie skrócić czas od wyświetlania powszechnie używanych elementów interfejsu użytkownika. Upewnij się, że rozumiesz rzeczywiste zachowanie już wdrożonych elementów buforowania - wiele popularnych metod buforowania (np. w sumie z innym podejściem do buforowania.

  • Parallelise : poszukaj sekwencyjnych transakcji, które nie muszą być logicznie wydawane ściśle sekwencyjnie, i przerobić system, aby wystawiać je równolegle. Zajmowałem się jednym przypadkiem, w którym żądanie typu end-to-end miało nieodłączne opóźnienie sieciowe ~2s, co nie stanowiło problemu w przypadku pojedynczej transakcji, ale gdy wymagane były 6 sekwencyjnych podróży w obie strony 2s, zanim użytkownik odzyskał kontrolę nad aplikacją kliencką, stało się ogromne źródło frustracji. Odkrycie, że transakcje te były w rzeczywistości niezależne, pozwoliło na ich równoległe wykonanie, zmniejszając opóźnienie użytkownika końcowego do bardzo zbliżonego do kosztu jednej podróży w obie strony.

  • Połącz : Jeśli sekwencyjne żądania muszą być wykonywane sekwencyjnie, poszukaj możliwości połączenia ich w jedno bardziej kompleksowe żądanie. Typowe przykłady to tworzenie nowych podmiotów, a następnie wnioski o powiązanie tych podmiotów z inne istniejące podmioty.

  • Compress : poszukaj możliwości wykorzystania kompresji ładunku, albo poprzez zastąpienie formy tekstowej binarną, albo przy użyciu rzeczywistej technologii kompresji. Wiele nowoczesnych (tj. w ciągu dekady) stosów technologii obsługuje to prawie przejrzyście, więc upewnij się, że jest skonfigurowany. Często byłem zaskoczony znaczącym wpływem kompresji, gdzie wydawało się jasne, że problemem było zasadniczo opóźnienie, a nie przepustowość, odkrywanie po tym, że pozwoliło to transakcji zmieścić się w jednym pakiecie lub w inny sposób uniknąć utraty pakietów, a tym samym mają wpływ na wydajność.

  • Powtórz: wróć do początku i ponownie Zmierz swoje operacje (w tych samych miejscach i godzinach) z ulepszeniami, Zapisz i zgłoś swoje wyniki. Podobnie jak w przypadku całej optymalizacji, niektóre problemy mogły zostać rozwiązane, ujawniając inne, które teraz dominują.

In the steps powyżej skupiam się na procesie optymalizacji aplikacji, ale oczywiście musisz upewnić się, że sama sieć bazowa jest skonfigurowana w najbardziej efektywny sposób, aby wspierać również Twoją aplikację. Zaangażuj specjalistów sieciowych w firmie i ustal, czy są w stanie zastosować poprawę przepustowości, QoS, kompresję sieci lub inne techniki, aby rozwiązać problem. Zazwyczaj nie rozumieją potrzeb Twojej aplikacji, dlatego ważne jest, abyś był wyposażony (po Przeanalizuj krok), aby omówić to z nimi, a także przedstawić uzasadnienie biznesowe dla wszelkich kosztów, o które będziesz ich prosił. Napotkałem przypadki, w których błędna konfiguracja sieci spowodowała, że dane aplikacji były przesyłane przez powolne łącze satelitarne, a nie łącze lądowe, po prostu dlatego, że używało portu TCP, który nie był "dobrze znany" przez specjalistów od sieci; oczywiście usunięcie takiego problemu może mieć dramatyczny wpływ na wydajność, bez kodu oprogramowania lub oprogramowania. zmiany konfiguracyjne w ogóle niezbędne.

 7
Author: Pat,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-04-17 04:03:18

Nie tak dogłębne i złożone jak poprzednie odpowiedzi, ale oto idzie: (są to bardziej poziom początkujący / średniozaawansowany)

  • oczywiste: suche
  • Uruchom pętle do tyłu, więc zawsze porównujesz do 0, a nie zmiennej
  • używaj operatorów bitowych, gdy tylko możesz
  • podziel powtarzalny kod na moduły / funkcje
  • obiekty pamięci podręcznej
  • zmienne lokalne mają niewielką przewagę wydajności
  • ograniczaj jak najwięcej manipulacji łańcuchami
 6
Author: Aaron,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-08-30 16:01:33

Trudno powiedzieć. To zależy od tego, jak wygląda kod. Jeśli możemy założyć, że kod już istnieje, to możemy po prostu spojrzeć na niego i dowiedzieć się z tego, jak go zoptymalizować.

Lepsza lokalizacja pamięci podręcznej, rozwijanie pętli, próba wyeliminowania długich łańcuchów zależności, aby uzyskać lepszą równoległość na poziomie instrukcji. Preferuj warunkowe ruchy nad gałęziami, jeśli to możliwe. Wykorzystaj instrukcje SIMD, jeśli to możliwe.

Zrozumieć, co robi twój kod i zrozumieć sprzęt działa. Następnie dość łatwo jest określić, co należy zrobić, aby poprawić wydajność kodu. To naprawdę jedyna naprawdę ogólna rada, jaką mogę wymyślić.

Cóż, to i "Pokaż kod NA SO i poproś o poradę optymalizacyjną dla tego konkretnego kawałka kodu".

 5
Author: jalf,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-29 15:10:12

Jeśli lepszy sprzęt jest opcją, to zdecydowanie na to skorzystaj. Otherwise

  • Sprawdź, czy używasz najlepszych opcji kompilatora i linkera.
  • Jeśli funkcja hotspot w innej bibliotece do częstego rozmówcy, rozważ przeniesienie lub klonowanie jej do modułu wywołującego. Eliminuje część narzutu wywołań i może poprawić trafienia w pamięci podręcznej (CF jak AIX łączy statycznie strcpy () do oddzielnie połączonych obiektów współdzielonych). Może to oczywiście zmniejszyć również Cache hits, dlatego jeden miara.
  • Sprawdź, czy istnieje możliwość użycia specjalistycznej wersji procedury hotspot. Minusem jest więcej niż jedna wersja do utrzymania.
  • # Patrz asembler Jeśli uważasz, że mogłoby być lepiej, zastanów się, dlaczego kompilator tego nie rozgryzł i jak możesz pomóc kompilatorowi. Zastanów się: czy naprawdę używasz najlepszego algorytmu? Czy jest to najlepszy algorytm dla Twojego rozmiaru wejściowego?
 5
Author: mealnor,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-09-13 15:52:22

Sposób google jest jedną z opcji " buforuj go.. W miarę możliwości nie dotykaj dysku "

 5
Author: asyncwait,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-10-09 11:01:10

Oto kilka szybkich i brudnych technik optymalizacji, których używam. Uważam to za optymalizację "pierwszego przejścia".

Dowiedz się, gdzie spędzany jest czas Dowiedz się, co dokładnie zajmuje czas. Czy to plik IO? Czy to czas procesora? Chodzi o sieć? Chodzi o bazę danych? Optymalizacja dla IO jest bezużyteczna, jeśli nie jest to wąskie gardło.

Poznaj swoje środowisko wiedza, gdzie optymalizować, zazwyczaj zależy od środowiska programistycznego. Na przykład w VB6, przekazywanie przez odniesienie jest wolniejsze niż przekazywanie przez wartość, ale w C i C++, przez odniesienie jest znacznie szybsze. W C rozsądne jest, aby spróbować czegoś i zrobić coś innego, jeśli kod powrotu wskazuje na niepowodzenie, podczas gdy w. Net, przechwytywanie wyjątków jest znacznie wolniejsze niż sprawdzanie poprawnego warunku przed próbą.

Indeksy budują indeksy na często zadawanych pytaniach polach bazy danych. Prawie zawsze możesz wymienić przestrzeń na prędkość.

Unikaj szukania wewnątrz pętla do optymalizacji, unikam konieczności robienia jakichkolwiek poszukiwań. Znajdź offset i / lub indeks poza pętlą i ponownie użyj danych wewnątrz.

Minimalizuj IO spróbuj zaprojektować w sposób, który zmniejsza liczbę razy trzeba czytać lub pisać, zwłaszcza przez połączenie sieciowe

Reduce Abstractions im więcej warstw abstrakcji kod musi pracować, tym wolniej. Wewnątrz pętli krytycznej, redukują abstrakcje (np. ujawniają metody niższego poziomu, które unikaj dodatkowego kodu)

Spawn Threads w przypadku projektów z interfejsem użytkownika, wywołanie nowego wątku do preformowania wolniejszych zadań sprawia, że aplikacja czuje się bardziej responsywna, chociaż nie jest.

Pre-process ogólnie można handlować przestrzenią na szybkość. Jeśli istnieją obliczenia lub inne intensywne operacje, sprawdź, czy możesz wstępnie obliczyć niektóre informacje, zanim znajdziesz się w pętli krytycznej.

 5
Author: Andrew Neely,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-07-20 13:15:33

Czasami zmiana układu danych może pomóc. W języku C można przełączyć się z tablicy lub struktur na strukturę tablic lub odwrotnie.

 4
Author: Nosredna,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-05-29 22:20:29

Dostosuj system operacyjny i framework.

Może to zabrzmieć przesadą, ale pomyśl o tym w ten sposób: systemy operacyjne i frameworki są zaprojektowane do wykonywania wielu rzeczy. Twoja aplikacja robi tylko bardzo konkretne rzeczy. Jeśli możesz uzyskać system operacyjny dokładnie to, czego potrzebuje Twoja aplikacja i aby Twoja aplikacja zrozumiała,jak działa framework (php,. NET, java), możesz znacznie lepiej wykorzystać swój sprzęt.

Facebook, na przykład, zmienił niektóre jądra poziom thingys w Linuksie zmieniono sposób działania memcached (na przykład napisali Memcached proxy, a użyli udp zamiast tcp ).

Innym przykładem tego jest Window2008. Win2K8 ma wersję, w której można zainstalować tylko podstawowy system operacyjny potrzebny do uruchomienia aplikacji X (np. aplikacje webowe, aplikacje serwerowe). Zmniejsza to wiele kosztów, które System operacyjny ma na uruchomionych procesach i zapewnia lepszą wydajność.

Oczywiście, zawsze należy dorzucić więcej sprzętu jako pierwszy krok...

 4
Author: Nir Levy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-01-17 13:42:02

Pass by reference zamiast by value

 4
Author: l--''''''---------'''''''''''',
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-03-06 05:21:33

Reduce variable sizes (in embedded systems)

Jeśli rozmiar zmiennej jest większy niż rozmiar słowa na określonej architekturze, może to mieć znaczący wpływ zarówno na rozmiar kodu,jak i szybkość. Na przykład, jeśli masz system 16 bitowy i używasz zmiennej long int bardzo często, a później zdasz sobie sprawę, że nigdy nie może wyjść poza zakres (-32.768 ... 32.767) rozważmy redukcję do short int.

Z mojego osobistego doświadczenia, jeśli program jest gotowy lub prawie gotowy, ale zdajemy sobie z tego sprawę zajmuje około 110% lub 120% pamięci programu docelowego sprzętu, szybka normalizacja zmiennych zwykle rozwiązuje problem częściej niż nie.

W tym czasie optymalizacja algorytmów lub części samego kodu może stać się frustrująco daremna:]}
  • zreorganizuj całą strukturę i program przestanie działać zgodnie z przeznaczeniem, a przynajmniej wprowadzasz wiele błędów.
  • wykonaj kilka sprytnych sztuczek: zazwyczaj spędzasz dużo czasu na optymalizacji czegoś i brak lub bardzo mały spadek rozmiaru kodu, ponieważ kompilator i tak by go zoptymalizował.

Wiele osób popełnia błąd, mając zmienne, które dokładnie przechowują wartość liczbową jednostki, do której używają zmiennej: na przykład ich zmienna time przechowuje dokładną liczbę milisekund, nawet jeśli istotne są tylko kroki czasowe powiedzmy 50 ms. Może gdyby twoja zmienna reprezentowała 50 ms dla każdego przyrostu o jeden, byłabyś w stanie zmieścić się w zmiennej mniejszej lub równej wielkość słowa. Na przykład w systemie 8-bitowym nawet proste dodanie dwóch 32-bitowych zmiennych generuje sporą ilość kodu, zwłaszcza jeśli brakuje rejestrów, podczas gdy 8-bitowe dodatki są zarówno małe, jak i szybkie.

 4
Author: vsz,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-06-25 16:03:01