Skocz do zawartości

Rekomendowane odpowiedzi

Opublikowano

Witam,

Mam na ukończeniu mój duży projekt, ale jedna rzecz nie daję mi spokoju - optymalizacja. Ogólnie jest ona na wysokim poziomie, skupiałem się na tym, aby było jak najlepiej wykonane i zachowane zasoby, które tych operacji wymagają. Mimo to, został mi pewien nie dosyć patrząc na to:

SELECT COUNT(*) AS 'allTransactions' 
(SELECT SUM( `amount` ) FROM `ibf_fg_transactions` WHERE `sender_id` = $uid OR is_system = 1) AS 'minusBilance',
(SELECT SUM( `amount` ) FROM `ibf_fg_transactions` WHERE `recipient_id` = $uid OR is_system = 1) AS 'plusBilance' 
FROM `ibf_fg_transactions` WHERE ( `sender_id` = $uid OR `recipient_id` = $uid ) AND MONTH( FROM_UNITIME( `date` ) ) = $selectedMonth;

W czym jest rzecz? Patrząc na to zapytanie nasuwa się jedno słowo - podzapytania. O dziwo nie mam problemu z ich wykonaniem - wykorzystuję $this->DB->allow_sub_select = 1; :-) Mimo to, sam fakt, że te wyniki są danymi na głównym module jak i sekcji aplikacji, będzie on wykonywany zawsze i to na dodatek jako jeden z pierwszych operacji. Z logicznego punktu widzenia zamknięcie tego w podzapytania daję nam tylko jeden komfort - wynikiem jest 1 zapytanie do MySQL. Ale prawda jest taka, że wykonujemy aż 3 zapytania!

Do sedna - skrypt ma pokazać 4 dane:

  • Ilość transakcji - w tym podzielone na systemowe!
  • Kwota, którą wysłaliśmy ( Nadawca )
  • Kwota, którą otrzymaliśmy ( Odbiorca )

O ile nie ma problemu z wydobyciem tych danych o tyle jest problem z faktem optymalizacji. Czy ma ktoś pomysł jak to rozwiązać? Moje obecne rozwiązanie opiera się na polach klasy i w czasie listowania transakcji są zliczane do tablicy dane, ale jest wada - odbywa się na dla strony! A to ma być globalne dla miesiąca.

Liczę na Wasze pomysły!

Pozdrawiam,

Largo

Jeżeli Ci pomogłem, nie zapomnij proszę o kliknięciu - add.png

Możesz liczyć na moją pomoc z zakresu: PHP5, MySQL, JavaScript i Ajax | W trakcie nauki CSS i xHTML!

W sprawie pomocy z zakresu IP.Board służę pomocą w dziale Zaawansowane programowanie IP.Board

Proszę o nie wysyłanie próśb PW o prywatną pomoc - pomagam JEDYNIE na forum lub na zlecenie!

Opublikowano

Witam,

bez testów - pobierz wszystkie dane, a dopiero na poziomie kodu policz ilość transakcji i obie kwoty. Wg mnie lepsze rozwiązanie, skoro chcesz optymalizować. :-)

OK, rozumiem to, ale nie kapuję jaki to ma sens. Obecny kod wygląda tak:

		/* Different Month? */
	$selectedMonth = ( $inputMonth ) ? $inputMonth : $actualMonth;

	/* Get logs */
	$this->SQL->getTransactionsData( $memberData, $sortKey, $orderType, $selectedMonth, $currentPage, $perPage );

	/* Any logs available? */
	if( $this->DB->getTotalRows() )
	{
		while( ( $row = $this->DB->fetch() ) )
		{
			/* Invisible transaction? */
			if( $row['invisible'] && !$this->library->isAdministrator )
			{
				continue;
			}

			/* Parse transaction! */
			$logsData[] = $this->parseTransaction( $row, $memberData );
		}							 
	}

	/* Create Base URL! */
	$baseURL = 'app=fg';

	if( $this->isModeratorSection )
	{
		$baseURL = 'showtransactions='.$memberData['member_id'];
	}
	else
	{
		/* With month? */
		if( $inputMonth )
		{
			$baseURL .= '&selectedMonth='.$inputMonth;
		}
	}

	$statsData = $this->SQL->getTransactionsStats( $memberData, $selectedMonth );

W miejsce funkcji do zapytania z transakcji mamy prawie takie same, jakbym listował dla tej propozycji co Ty. Co mi to da? Nie dość, że dodatkowy kod ( tamtego nie wykorzystam ze względu na klauzulę LIMIT ), to jeszcze prawie identyczny zapytania MySQL. Widzisz w tym sens?

Pozdrawiam,

Largo

Jeżeli Ci pomogłem, nie zapomnij proszę o kliknięciu - add.png

Możesz liczyć na moją pomoc z zakresu: PHP5, MySQL, JavaScript i Ajax | W trakcie nauki CSS i xHTML!

W sprawie pomocy z zakresu IP.Board służę pomocą w dziale Zaawansowane programowanie IP.Board

Proszę o nie wysyłanie próśb PW o prywatną pomoc - pomagam JEDYNIE na forum lub na zlecenie!

  • Manager
Opublikowano

Dla mnie Largo szukasz dziury w całym. Pierwsze podane zapytanie przez Ciebie zapytanie wg mnie jest konieczne do wykonania. Z drugiej jednak strony joiny i to dwa, przy każdym wywołaniu, jak to pisałeś, nie jest dobre.

Wg mnie mógłbyś pomyśleć o zapisywaniu takich danych w cache użytkownika, i przy każdej jej zmianie jej aktualizację, a 'na codzień' wyświetlanie z cache.

intermedia - profesjonalne rozwiązania Invision Power Board

---

Chcesz uzyskać szybko i sprawnie pomoc? Uzupełnij wersję i adres w profilu.

Opublikowano

Dla mnie Largo szukasz dziury w całym. Pierwsze podane zapytanie przez Ciebie zapytanie wg mnie jest konieczne do wykonania. Z drugiej jednak strony joiny i to dwa, przy każdym wywołaniu, jak to pisałeś, nie jest dobre.

Wg mnie mógłbyś pomyśleć o zapisywaniu takich danych w cache użytkownika, i przy każdej jej zmianie jej aktualizację, a 'na codzień' wyświetlanie z cache.

Taki urok człowieka, że szuka dziury w całym? :-) OK, lekki żart na wstęp dyskusji.

Myślałem o rozwiązaniu Cache, ale problem jest o tyle nie banalny, że te dane są zależne od czynnika zewnętrznego - wyboru miesiąca. Nie ma sensu zapisywać tego w Cache bo i co to da? Standardowo skrypt ma pobierać dla danego miesiąca ( od jego początku do jego końca ) i tak aż do 12 miesięcy od jego daty rejestracji lub jeżeli użytkownik jest dłużej niż 12 miesięcy każdy kolejny od tamtej daty ( lista ma być nie za duża, jak i sprawdzania danych przez użytkownika, od tego mają Archiwum transakcji ). Czyli jeżeli miałbym zapisywać w Cache to aż 12 miesięcy, a potem także kontrolować czy dany miesiąc jest sens trzymać w Cache.

Oficjalnie bym się tym nie przejmował, ale jeżeli teraz coś robię ( na najnowsze IP.Board, które wspiera naprawdę mocno OO i PHP5 ) nie chcę spartolić roboty. Co zrobię potem, kiedy zapytania będą tak mało wydajne na bazę danych? OK, istnieje opcja wyłączenia danych, ale aż tak daleko nie posuwam myśli.

I nie denerwuj się :-) Znasz mnie już trochę i wiesz, że wolę się upewnić i dmuchać na zimne, w końcu to dyskusja nie podejmujemy żadnych kroków, a może w między czasie wpadnie złoty pomysł? :-)

Pozdrawiam,

Largo

Jeżeli Ci pomogłem, nie zapomnij proszę o kliknięciu - add.png

Możesz liczyć na moją pomoc z zakresu: PHP5, MySQL, JavaScript i Ajax | W trakcie nauki CSS i xHTML!

W sprawie pomocy z zakresu IP.Board służę pomocą w dziale Zaawansowane programowanie IP.Board

Proszę o nie wysyłanie próśb PW o prywatną pomoc - pomagam JEDYNIE na forum lub na zlecenie!

Jeśli chcesz dodać odpowiedź, zaloguj się lub zarejestruj nowe konto

Jedynie zarejestrowani użytkownicy mogą komentować zawartość tej strony.

Zarejestruj nowe konto

Załóż nowe konto. To bardzo proste!

Zarejestruj się

Zaloguj się

Posiadasz już konto? Zaloguj się poniżej.

Zaloguj się
  • Ostatnio przeglądający   0 użytkowników

    • Brak zarejestrowanych użytkowników przeglądających tę stronę.
×
×
  • Dodaj nową pozycję...

Powiadomienie o plikach cookie

Umieściliśmy na Twoim urządzeniu pliki cookie, aby pomóc Ci usprawnić przeglądanie strony. Możesz dostosować ustawienia plików cookie, w przeciwnym wypadku zakładamy, że wyrażasz na to zgodę.