Niezalogowany [ logowanie ]
Subskrybuj kanał ATOM Kanał ATOM

Autor wpisu: Zyx, dodany: 15.01.2011 15:10, tagi: php

Na planecie PHP niedawno pojawił się wpis batmana poświęcony magicznym elementom języka PHP. Jako sam opis sprawdzał się całkiem fajnie, ale jak to już przy tego typu materiałach bywa - zabrakło porządnego rozwinięcia, kiedy i czy w ogóle magię powinno się stosować w swoich aplikacjach WWW. Ten wpis ma za zadanie wypełnić przynajmniej częściowo tę lukę, tym bardziej że obecnie największe projekty PHP zaczęły się od magii odwracać.

Autor wpisu: batman, dodany: 14.01.2011 22:43, tagi: javascript, jquery

14 stycznia 2006 roku światło dzienne ujrzała pierwsza wersja najpopularniejszej biblioteki JavaScript. Dzisiaj, w piąte urodziny, wydana została pierwsza beta jQuery 1.5. Według roadmap stabilna wersja ma się pojawić ostatniego dnia stycznia. Co nowego pojawi się w najnowszym wydaniu jQuery? Przede wszystkim przebudowany zostanie moduł $.ajax. Do tego dochodzi szereg usprawnień poprawiających i wydajność biblioteki oraz poprawiających błędy. Pełną listę zmian można znaleźć na blogu jQuery.

Autor wpisu: batman, dodany: 13.01.2011 08:00, tagi: php

Każdy język programowania ma swoje smaczki. W przypadku PHP smaczkiem tym są magiczne metody – znienawidzone przez jednych, nadużywane przez innych. Zastosowane z rozwagą i dobrze użyte mogą znacząco wpłynąć na rozwój kodu. Każda magiczna metoda rozpoczyna się dwoma znakami podkreślenia ( __ ). Twórcy języka wyraźnie zaznaczyli, że konwencja ta jest zarezerwowana wyłącznie dla magicznych metod i nie powinna być stosowana w innych przypadkach.

Konstruktor

Najczęściej używaną przez programistów PHP magią jest konstruktor. Oznaczony jako __construct odpowiada za inicjalizację obiektu. Konstruktor może przyjąć dowolną liczbę argumentów i wbrew pozorom nic nie zwraca.

class Foo
{
    protected $_zmienna;

    public function __construct($arg1 = null)
    {
        $this->_zmienna = $arg1;
    }
}

Jeśli zwrócimy coś w konstruktorze, dopiero jego jawne wywołanie spowoduje, że wartość ta będzie dostęna.

class Foo
{
    public function __construct()
    {
        return null;
    }
}

$foo = new Foo();
var_dump($foo->__construct()); // wyswieli NULL

Konstruktory mogą być podstępne, zwłaszcza jeśli korzystamy z dziedziczenia. Należy pamiętać, iż nadpisanie konstruktora spowoduje, że wykona się konstruktor zadeklarowany najniżej w hierarchii. Pozostałe musimy sami wywołać.

class Foo
{
    public function __construct()
    {
        echo 'Konstruktor Foo';
    }
}

class Bar extends Foo
{
    public function __construct()
    {
        echo 'Konstruktor Bar';
    }
}

class Baz extends Bar
{
    public function __construct()
    {
        echo 'Konstruktor Baz';
    }
}

$baz = new Baz();

Powyższy kod wyświetli tylko jeden tekst – Konstruktor Baz. Dopiero jawne wskazanie, że konstruktor rodzica też ma się wykonać, spowoduje wyświetlenie pozostałych tekstów.

class Foo
{
    public function __construct()
    {
        echo 'Konstruktor Foo';
    }
}

class Bar extends Foo
{
    public function __construct()
    {
        parent::__construct();
        echo 'Konstruktor Bar';
    }
}

class Baz extends Bar
{
    public function __construct()
    {
        parent::__construct();
        echo 'Konstruktor Baz';
    }
}

$baz = new Baz();

Powyższy kod wyświetli

Konstruktor Foo
Konstruktor Bar
Konstruktor Baz

Jak widać konstruktory wykonują się po kolei. Dzieje się tak dlatego, że wywołanie konstruktora rodzica jest pierwszą instrukcją. Dzięki możliwości sterowania momentem wywołania konstruktora rodzica mamy wpływ na proces inicjalizacji obiektów.

Destruktor

Przeciwieństwem konstruktora jest destruktor, który służy do sprzątania bałaganu po obiekcie. Metoda ta zostanie wywołana w momencie, gdy na dany obiekt nie wskazuje żadna referencja. Podobnie jak w przypadku konstruktorów, destruktory klas nadrzędnych należy wywołać samemu.

class Foo
{
    public function __destruct()
    {
        echo 'Destruktor Foo';
    }
}

class Bar extends Foo
{
    public function __destruct()
    {
        parent::__destruct();
        echo 'Destruktor Bar';
    }
}

class Baz extends Bar
{
    public function __destruct()
    {
        parent::__destruct();
        echo 'Destruktor Baz';
    }
}

$baz = new Baz();

Przeciążanie metod

W PHP nie ma możliwości zdefiniowania dowolnej ilości takich samych metod z różnymi parametrami. Jeśli ktoś spróbuje takie coś zrobić, niemiło się rozczaruje. Z pomocą przychodzi kolejna magia w postaci dwóch metod: __call oraz __callStatic. Obie metody działają w taki sam sposób, przy czym __call działa z poziomu obiektu, a __callStatic z poziomu klasy. Obie metody zostaną wywołane w przypadku gdy na obiekcie (__call) lub klasie (__callStatic) wywołana zostanie niezdefiniowana metoda.

Zarówno metoda __call jak i __callStatic przyjmują dwa argumenty. Pierwszym z nich jest nazwa wywołanej (nieistniejącej) metody, drugim tablica przekazanych do niej argumentów.

Czytaj dalej tutaj (rozwija treść wpisu)
Czytaj dalej na blogu autora...

Autor wpisu: Daniel Burchardtt, dodany: 12.01.2011 23:05, tagi: php

Rosyjska firma ONsec opublikowała ciekawy raport dotyczący tego, jak PHP na Windowsie traktuje nazwy plików. Badanie pokazuje, że wszyscy którzy hostują swoje webaplikacje napisane w PHP na Windows, powinni jeszcze raz przyjrzeć się wszelkim regexpom i regułkom na IDS-ach…

Nazwy plików a PHP na Windows

Do stworzenia raportu badaczy zainspirował fakt, że w Windows interpreter PHP może z sukcesem odwołać się do pliku na 4 poniższe sposoby:

  • example.phP
  • example.php
  • example.ph>
  • example.ph<

Z przeprowadzonych przez ONsec testów wynika, że za błąd odpowiedzialna jest funkcja WinAPI FindFirstFile(). Badacze zauważyli, że znak > zastępowany jest tak naprawdę przez ? a < przez * i dodatkowo “ zastępowany jest przez .. Co ciekawe, ten bug jest znany Microsoftowi od roku 2007.

Po całość wpisu zapraszam na niebezpiecznik lub pouczyć się historii.

Autor wpisu: sokzzuka, dodany: 12.01.2011 09:29, tagi: php

Marcin Babij z naszej klasy w swoim wpisie na php.internals poinformował społeczność php, o wykonanych przez nich optymalizacjach interpretera. Dotyczą one implementacji hash table czyli znanych nam wszystkim php-owych „arrayów”. Jako, że są one wykorzystywane wszędzie, nie tylko w kodzie napisanym przez użytkowników ale również w wielu miejscach w samym interpreterze, każda poprawka, która przyspiesza funkcje operujące na tej strukturze danych jest mile widziana (jak podaje Babij średnio ich wywołania zajmują 10%-20% czasu każdego skryptu).

Nie wgłębiając się zbytnio w techniczne szczegóły, które można znaleźć w oryginalnym wpisie, programistom nk.pl udało się zmniejszyć obciążenie procesora przy operacjach na tablicach o 4% do 6% przy niewielkim wzroście użycia pamięci. Patch, który dostarczył został sprawdzony względem php 5.3.4 i apc-3.1.3p1 i można go ściągnąć z githuba.

Wypada tylko podziękować programistom naszej klasy, że są tak uprzejmi i dzielą się swoimi osiągnięciami. Może to zachęci inne osoby z naszego pięknego kraju do przyłączenia się do projektu.

Autor wpisu: widmogrod, dodany: 11.01.2011 21:58, tagi: php, eclipse

Eclipse, dla wielu może być ociężałą kobyłą – zgodzę się – ale jej ociężałóść znika po 15min uruchamiania i gdy zacznie się wykorzystywać moc jaką daje Eclipse.

Pracując w Eclipse od ok 3lat z przerwami na wypróbowanie Netbeans. Dopiero niedawno zdałem sobie sprawę że zapomniałem nie tylko o myszce ale również o bloku navigacji projektu.

Skróty klawiaturowe, których używam kilka razy dziennie:

  • Ctrl + Shift + R – znajdź i otwórz plik (można używać *. by znaleźć wszystkie możliwości gdy nie pamięta się nazwy pliku)
  • Ctrl + Shift  + T – znajdź i otwórz typ pliku (rozpoznaje skrócone nazwy np.: ZVH -> Zend_View_Helper)
  • Ctrl + Shift + M – znajdź i otwórz metodę – bez komentarza ;)
  • Zanacz tekst i Ctrl + Alt + G – wyszukaj w projekcie wszystkie wystąpienia zaznaczonego tekstu

Jak widać tylko cztery skróty wystarczą by nawigacja po projekcie była błyskawiczna i bez potrzeby sięgania myszki by coś odgrzebać :)

Czy też macie swoje ulubione skróty klawiaturowe w Eclipsie?

Autor wpisu: batman, dodany: 10.01.2011 08:00, tagi: php

Poprzedni tekst traktujący o SPL rozpoczął serię wpisów poświęconych standardowej bibliotece PHP (Standard PHP Library). Poznaliśmy w nim trzy klasy ułatwiające pracę z plikiem. Podczas poznawania tych klas, okazało się, że korzystają z dobrodziejstw iteratorów oraz wbudowanych interfejsów. Dzisiaj skupimy się jedynie na interfejsach dostarczanych razem z SPL z wyłączeniem SplObserver oraz SplSubject. O obserwatorze napiszę innym razem. Obok interfejsów dostępnych w ramach SPL, PHP oferuje kilka dodatkowych interfejsów, o których również dzisiaj napiszę.

Traversable

Jest to pusty interfejs służący do oznaczenia klasy jako “iterowalnej”. Każdy obiekt klasy implementującej interfejs Traversalbe może zostać użyty w pętli foreach jako wyrażenie. Interfejs ten nie może zostać użyty bezpośrednio w klasie. Zamiast tego należy skorzystać z interfejsu dziedziczącego po Traversable, np Iterator lub IteratorAggregate.

Iterator

Interfejs ten służy jako rozwinięcie idei interfejsu Traversable. Wprowadza on metody, które zostaną wykorzystane przez pętlę foreach podczas iteracji po obiekcie. Domyślnie pętla foreach przejdzie po wszystkich właściwościach publicznych obiektu. W przypadku użycia interfejsu wykorzystane zostaną metody:

  • current – zwraca bieżący element
  • key – zwraca klucz aktualnego elementu
  • next – przesuwa wewnętrzny wskaźnik na kolejny element
  • rewind – przesuwa wewnętrzny wskaźnik na pierwszy element
  • valid – sprawdza czy bieżąca pozycja jest poprawna

Zobaczmy przykład prostej klasy korzystającej z tego interfejsu

class Foo implements Iterator
{
    protected $_position;
    protected $_someData = array('123', 'abc', 'qwe');

    public function __construct()
    {
        $this->_position = 0;
    }

    public function current()
    {
        return $this->_someData[$this->_position];
    }

    public function key()
    {
        return $this->_position;
    }

    public function next()
    {
        ++$this->_position;
    }

    public function rewind()
    {
        $this->_position = 0;
    }

    public function valid()
    {
        return isset($this->_someData[$this->_position]);
    }
}

$foo = new Foo();
foreach($foo as $key => $value) {
    echo $key . ' = ' . $value;
}

Zgodnie z oczekiwaniami, wynikiem działania będzie

0 = 123
1 = abc
2 = qwe

Po co nam klasa, która robi to samo co tablica? Odpowiedź jest tylko jedna – po nic. Interfejs ten ma zastosowanie wszędzie tam, gdzie mamy do czynienia z kolekcjami obiektów, na których będziemy wykonywać dodatkowe operacje. Może to być na przykład kolekcja złożona z obiektów, gdzie każdy z nich odpowiada wierszowi w bazie danych.

IteratorAggregate

Interfejs ten jest o tyle ciekawy, że pozwala “oddelegować” iterowanie po danym obiekcie do innej klasy implementującej interfejs Traversable (lub inny interfejs po nim dziedziczący).

class Foo implements Iterator
{
    protected $_position = 0;
    protected $_someData = array();

    public function __construct($data)
    {
        $this->_someData = $data;
        $this->rewind();
    }

    public function current()
    {
        return $this->_someData[$this->_position];
    }

    public function key()
    {
        return $this->_position;
    }

    public function next()
    {
        $this->_position = $this->_position + 1;
    }

    public function rewind()
    {
        $this->_position = 0;
    }

    public function valid()
    {
        return isset($this->_someData[$this->_position]);
    }
}

class Bar implements IteratorAggregate
{
    protected $_data = array('123', 'abc', 'qwe');

    public function getIterator()
    {
        return new Foo($this->_data);
    }
}

$bar = new Bar();
foreach($bar as $key => $value) {
    echo $key . ' = ' . $value;
}

Do czego jest to nam potrzebne? Przykładów zastosowania jest co najmniej kilka. Najprostszym z nich jest udostępnienie chronionych lub prywatnych danych na zewnątrz.

class Foo implements IteratorAggregate
{
    protected $_data = array(123, 'abc', 'qwe');

    public function getIterator()
    {
        return new ArrayIterator($this->_data);
    }
}

$foo = new Foo();
foreach($foo as $key => $value) {
    echo $key . ' = ' . $value;
}

Nie przejmujcie się klasą ArrayIterator, omówię ją przy okazji iteratorów. Wystarczy, że będziecie wiedzieć, iż klasa ta pozwala na modyfikowanie i usuwanie kluczy i wartości tablic oraz obiektów.

Countable

Implementacja tego interfejsu oznacza, iż naszą klasę można policzyć. Interfejs definiuje tylko jedną publiczną metodę, która zwraca liczbę opisującą ilość elementów w naszej klasie.

Czytaj dalej tutaj (rozwija treść wpisu)
Czytaj dalej na blogu autora...

Wszystkie wpisy należą do ich twórców. PHP.pl nie ponosi odpowiedzialności za treść wpisów.