PHP/Zmienne i tablice: Różnice pomiędzy wersjami

Usunięta treść Dodana treść
ort.
m Update syntaxhighlight tags - remove use of deprecated <source> tags
 
Linia 60:
Pamiętaj, że PHP potrafi automatycznie rozpoznawać typ wyrażenia i w razie potrzeby odpowiednio go konwertować. Dla przykładu instrukcja ''echo'' wymaga danych tekstowych. W skrypcie:
 
<sourcesyntaxhighlight lang="php" line><?php
echo 7;
</syntaxhighlight>
</source>
 
Interpreter dokona konwersji liczby na tekst, a dopiero potem spowoduje jego wyświetlenie.
Linia 70:
Informatyka wiele zawdzięcza matematyce. W programowaniu występuje wiele pojęć zaczerpniętych bezpośrednio od królowej nauk. Jednym z nich jest funkcja, do której możemy wprowadzać parametry, a w zamian otrzymujemy jakiś wynik. Poniżej będzie pierwszy "naprawdę" dynamiczny skrypt, jaki stworzymy. Skorzystamy w nim z dwóch funkcji, aby wyświetlić aktualny czas:
 
<sourcesyntaxhighlight lang="php" line><?php
 
echo 'Dzisiaj mamy: '.date('d.m.Y').'<br/>';
echo 'Od 1.1.1970 minęło: '.time().' sekund';
 
</syntaxhighlight>
</source>
 
Jak widać, składnia '''funkcji''' jest następująca: <code>nazwaFunkcji(parametry)</code>. Jeśli funkcja nie posiada parametrów, nawiasy są puste. Jeżeli jest ich więcej, niż jeden, oddzielamy je od siebie przecinkiem. Zaś sam parametr jest niczym innym, jak... pewnym wyrażeniem. Wynik działania funkcji również jest wyrażeniem, dlatego możemy ją wpleść w nasz tekst za pomocą operatora kropki.
Linia 102:
Aby przypisać wartość do zmiennej, należy skorzystać z operatora '''='''. Po lewej stronie umieszczamy naszą zmienną, a po prawej dowolne wyrażenie określające wartość, która zostanie zapisana w zmiennej. Oto, jak wygląda to w praktyce:
 
<sourcesyntaxhighlight lang="php" line><?php
// inicjujemy zmienna $czas aktualnym czasem w sekundach od 1.1.1970
$czas = time();
Linia 110:
echo 'Od 1.1.1970 minęło '.$czas2.' minut<br/>';
echo 'Od 1.1.1970 minęło '.($czas / 3600).' godzin';
</syntaxhighlight>
</source>
 
W powyższym przykładzie stworzyliśmy zmienne <code>$czas</code> i $czas2, zapisując w pierwszej z nich liczbę sekund zwróconą przez wywołanie funkcji time(). Następnie wykorzystaliśmy ją w obliczeniach w kolejnej linijce. Poznaliśmy w ten sposób jedno z zastosowań zmiennych. Zachowaliśmy w nich wynik działania jednej sekcji programu, aby potem używać go wielokrotnie gdzie indziej, bez konieczności każdorazowego odwoływania się do funkcji i zbędnego liczenia tego samego.
Linia 116:
PHP, w przeciwieństwie do innych języków programowania, ma bardzo liberalne reguły stosowania zmiennych. Nie trzeba ich nigdzie uprzednio deklarować, a interpreter sam nam dopasuje rodzaj informacji do naszych potrzeb (ustali tzw. typ zmiennej). Dana zmienna jest tworzona podczas pierwszego jej wykorzystania w skrypcie. Jest sporo sytuacji, w których zachowanie to jest pożądane, lecz może też utrudnić pracę. Aby mieć świadomość zagrożenia, wyobraź sobie taką sytuację: programista pisząc szybko, może popełnić literówkę. Jeżeli zostanie ona popełniona podczas wpisywania nazwy, PHP utworzy zmienną zawierającą tę literówkę. W teorii nie jest to żadnym błędem, jednak możemy się domyślać, że zapis obliczeń do innej zmiennej spowoduje błędne działanie programu, a programista będzie musiał spędzić dużo czasu na odnalezienie przyczyny. Słowo "teoria" nie znalazło się tu przypadkowo. Podczas instalowania PHP wspominaliśmy o poziomach raportowania błędów. Im wyższy poziom, tym większej ilości rzeczy czepia się PHP. Na poziomie ''E_ALL'' zdefiniowanym w rekomendowanym pliku ''php.ini'' takie beztroskie podejście do zmiennych nie jest tolerowane. Tutaj PHP wymaga już, aby podczas pierwszego użycia zmiennej została jej przypisana jakaś wartość, ponieważ inaczej otrzymamy powiadomienie (ang. ''notice'') o próbie odwołania się do nieistniejącej zmiennej. Popatrzmy sobie na ten przykład:
 
<sourcesyntaxhighlight lang="php" line><?php
 
echo $a * 16 + 5;
</syntaxhighlight>
</source>
 
Zmienna <code>$a</code> nie została w tym kodzie nigdzie początkowo zadeklarowana. Otwórz swój plik ''php.ini'', odnajdź dyrektywę ''error_reporting'' i zmień jej wartość na <code>E_ALL | ~E_NOTICE</code>. Wyłączysz w ten sposób wyświetlanie powiadomień. Zrestartuj serwer i uruchom powyższy skrypt. Wynikiem powinno być "5". PHP bez pytania podstawił do <code>$a</code> wartość neutralną 0. Przywróć teraz poprzedni poziom (''E_ALL | E_STRICT'') i ponownie uruchom ten skrypt. Oprócz wyniku, ujrzysz też komunikat:
Linia 127:
Sytuację można rozwiązać, ręcznie inicjując zmienną <code>$a</code> wartością 0:
 
<sourcesyntaxhighlight lang="php" line><?php
$a = 0;
echo $a * 16 + 5;
</syntaxhighlight>
</source>
 
Zalecane jest, aby wszystkie skrypty pracowały bezproblemowo przy włączonych powiadomieniach. Jeżeli zajdzie sytuacja, że odwołanie się do zmiennej, która może jeszcze nie istnieć, jest potrzebne, istnieje kilka sposobów "oszukania" PHP, lecz poznamy je w dalszej części podręcznika.
Linia 136:
Początkujący programiści mają tendencję do tworzenia dużej liczby tzw. ''zmiennych tymczasowych'', które nie wnoszą absolutnie niczego do programu poza wydłużeniem kodu i zmniejszeniem wydajności. Po każdym etapie przetworzenia jakiejś informacji, umieszczana jest ona w nowej zmiennej. Takie podejście jest nieprawidłowe. Oto przykłady "złych" skryptów:
 
<sourcesyntaxhighlight lang="php" line><?php
 
$tekst = 'To jest jakiś tekst';
Linia 142:
$tekstBezpieczny = addslashes($tekstMaly);
echo $tekstBezpieczny;
</syntaxhighlight>
</source>
 
Przykład 2:
 
<sourcesyntaxhighlight lang="php" line><?php
 
$format = 'd.m.Y';
echo date($format);
</syntaxhighlight>
</source>
 
W pierwszym skrypcie niepotrzebnie po każdym etapie przetwarzania tekstu tworzymy dla niego nową zmienną. Możemy to poprawić na dwa sposoby. Pierwszy:
 
<sourcesyntaxhighlight lang="php" line><?php
 
$tekst = 'To jest jakiś tekst';
Linia 160:
$tekst = addslashes($tekst);
echo $tekst;
</syntaxhighlight>
</source>
 
Drugi sposób rozwiązania tego problemu - bez użycia zmiennych (już trochę mniej czytelny):
 
<sourcesyntaxhighlight lang="php" line><?php
echo addslashes(strtolower('To jest jakiś tekst'));
</syntaxhighlight>
</source>
 
W drugim "złym" skrypcie w ogóle niepotrzebnie tworzymy zmienną - format daty możemy wpisać bezpośrednio do funkcji.
 
<sourcesyntaxhighlight lang="php" line><?php
echo date('d.m.Y');
</syntaxhighlight>
</source>
 
Jednak nie zawsze jest to lepsza wersja. Jeżeli nasz skrypt bardzo często będzie formatować różne daty, a my będziemy chcieli mieć możliwość zmieniania tych formatów w przyszłości, użycie zmiennych bardzo ułatwiłoby sprawę - zmieniamy format daty w jednej zmiennej, zamiast w kilku czy kilkudziesięciu wywołaniach date().
Linia 186:
Pierwszym typem skalarnym jest ''liczba całkowita''. Jej angielskim określeniem jest ''integer'', używany bywa skrót ''int''. Może być ona zapisana w trzech systemach liczbowych: dziesiętnym, szesnastkowym albo ósemkowym:
 
<sourcesyntaxhighlight lang="php" line><?php
$a = 1234; // liczba całkowita
$a = -123; // liczba całkowita ujemna
$a = 0123; // zapis ósemkowy (odpowiednik dziesiętnego 83)
$a = 0x1A; // zapis szesnastkowy (odpowiednik dziesiętnego 26)
</syntaxhighlight>
</source>
 
Możemy także korzystać z wartości ułamkowych zwanych ''liczbami zmiennoprzecinkowymi'' (ang. ''floating point numbers'' albo skrótowo ''float''), które są przybliżeniem liczb rzeczywistych (ważne - nigdy nie zawierają dokładnej wartości, prawie zawsze jest to odrobinę różniąca się liczba, dlatego mówi się o "przybliżeniu"). Przy ich zapisywaniu obowiązują reguły języka angielskiego, więc części całkowite od ułamkowych oddzielamy za pomocą kropki. Także i tu mamy do wyboru kilka sposobów zapisu:
 
<sourcesyntaxhighlight lang="php" line><?php
$a = 1.234;
$a = 1.2e3;
$a = 7E-10;
</syntaxhighlight>
</source>
 
Kolejnym typem jest typ logiczny (''boolean''), przyjmujący jedynie wartości '''FALSE''' i '''TRUE'''. Jest on używany przez wiele funkcji do zwracania rezultatu, czy operacja się powiodła. Wyrażenia porównawcze (czy równy, czy większy itd.) także generują wartości logiczne.
Linia 205:
Ostatnim z typów skalarnych jest ciąg tekstowy (ang. ''string''). Zdążyliśmy już wspomnieć nieco o nim, m.in. o istnieniu dwóch składni zapisywania ciągów. Ta oparta na apostrofach dopuszcza mniejszy zestaw kodów formatujących (pozwalających na wstawienie do tekstu innych apostrofów oraz ukośników wstecznych):
 
<sourcesyntaxhighlight lang="php" line><?php
echo 'To jest tekst zapisany w apostrofach. Kody formatujące pozwalają
umieścić w tekście wyłącznie inne apostrofy: \' albo backslashe: \\. Wszystko inne,
np. \n zostanie wyświetlone jako zwyczajny tekst, zamiast znaku nowej linii';
</syntaxhighlight>
</source>
 
Uruchom powyższy skrypt, aby zobaczyć jaki tekst zostanie wyświetlony. Spróbuj usunąć backslash sprzed apostrofu (w tekście: \') i zobacz, co się stanie. Skrypt się nie uruchomi, ponieważ wystąpił błąd składni. PHP napotka w sumie trzy apostrofy, a więc między drugim i trzecim będzie nierozpoznany dla parsera tekst, natomiast trzeci będzie niedomknięty.
Linia 215:
Więcej możliwości formatowania posiada tekst ograniczony cudzysłowami:
 
<sourcesyntaxhighlight lang="php" line><?php
echo "To jest tekst zapisany w cudzysłowach. Za pomocą kodów formatujących możemy
umieszczać wiele rzeczy: znak cudzysłowu \" backslash \\ znak nowej linii \n i inne: \t \r \$";
</syntaxhighlight>
</source>
 
Cudzysłowy zezwalają na "proste" umieszczanie wewnątrz tekstu wartości zmiennych, co zilustrujemy w prymitywnym przykładzie:
 
<sourcesyntaxhighlight lang="php" line><?php
$czas = time();
echo "Aktualny czas w sekundach: $czas sek.";
</syntaxhighlight>
</source>
 
Wartym zapamiętania jest fakt, że wstawianie zmiennych w ten sposób jest kilka razy wolniejsze, niż łączenie ich z ciągiem operatorem kropki.
 
<sourcesyntaxhighlight lang="php" line><?php
// tutaj można użyć cudzysłowu jak i apostrofu
echo "Aktualny czas w sekundach: ".time()." sek.";
</syntaxhighlight>
</source>
 
Niektórzy początkujący programiści niezbyt rozumieją ideę tej możliwości - próbują wykorzystywać ciągi do wprowadzania wartości zmiennych jako parametrów do funkcji:
 
<sourcesyntaxhighlight lang="php" line><?php
$formatDaty = 'd.m.Y';
echo date("$formatDaty");
</syntaxhighlight>
</source>
 
Powinno się unikać takiej konstrukcji, i choć PHP ją akceptuje, nie jest to prawidłowe użycie tej struktury języka. Co więcej, przy złożonych typach powoduje zniekształcenie danych. Jeżeli spotkasz kogoś piszącego w ten sposób, poinformuj go o tym. Do tego wyświetlanie danych zawartych w cudzysłowach przebiega wolniej niż w apostrofach.
Linia 254:
Przyjrzyjmy się wspomnianemu w trzecim punkcie poleceniu. Czasem jakąś zmienną trzeba zniszczyć. Najlepiej nadaje się do tego polecenie <code>unset()</code>:
 
<sourcesyntaxhighlight lang="php" line><?php
$zmienna = 4856;
 
Linia 260:
 
echo $zmienna;
</syntaxhighlight>
</source>
 
Zmiennej już nie ma, dlatego polecenie '''echo''' pokaże nam powiadomienie o nieistniejącej zmiennej.
Linia 270:
Możemy sami wymusić konwersję typów:
 
<sourcesyntaxhighlight lang="php" line><?php
// wyświetl liczbę całkowitą jako ułamek
echo (float) 10;
</syntaxhighlight>
</source>
 
W nawiasie przed wartością piszemy angielską nazwę typu: ''integer'', ''int'', ''string'', ''boolean'', ''float'', ''double'' (liczba zmiennoprzecinkowa mogąca przybierać znacznie większe wartości). Unikaj jakiejkolwiek konwersji typów złożonych: tablic, obiektów, zasobów, gdyż w każdym z tych przypadków informacje zostają całkowicie utracone; zamiast nich zwracana jest po prostu nazwa typu złożonego - to dlatego ostrzegaliśmy przed wprowadzaniem wartości zmiennych do funkcji przez cudzysłowy.
Linia 279:
PHP posiada funkcję <code>gettype()</code> zwracającą nazwę aktualnego typu danych zawartych w zmiennej:
 
<sourcesyntaxhighlight lang="php" line><?php
$a = 547;
echo 'Typ zmiennej $a to: '.gettype($a);
</syntaxhighlight>
</source>
 
=== Więcej o operatorach ===
Linia 349:
Zwróć uwagę na cztery ostatnie pozycje. Wyszczególnione zostały tam tzw. operatory jednoargumentowe, czyli takie, które operują wyłącznie na jednym wyrażeniu. W dodatku koniecznie musi być ono zmienną, ponieważ modyfikują one jej wartość, powiększając lub zmniejszając o jeden. Każdy z tych operatorów został podany podwójnie, ponieważ w zależności od tego, czy postawimy go przed, czy po zmiennej, otrzymamy nieco inne rezultaty. Porównaj:
 
<sourcesyntaxhighlight lang="php" line><?php
// najpierw składnia $zmienna++
 
Linia 363:
echo 'Stan 1: '.(++$zmienna).'<br/>';
echo 'Stan 2: '.$zmienna.'<br/>';
</syntaxhighlight>
</source>
 
Skrypt ten wygeneruje nam kilka linijek:
Linia 378:
Zajmijmy się teraz przypisywaniem danych do zmiennej. Wiemy już, że operator przypisania po lewej stronie wymaga zmiennej, po prawej wyrażenia, którego wartość trzeba w niej umieścić. Skoro operator to też jest wyrażenie, to jaką wartość ono reprezentuje? Okazuje się, że tę, która jest przypisywana. Możemy wobec tego zastosować sprytną sztuczkę, o której wbrew pozorom wie niezbyt wielu programistów. Zainicjujmy pięć zmiennych naraz tą samą wartością:
 
<sourcesyntaxhighlight lang="php" line><?php
$a = $b = $c = $d = $e = 5;
</syntaxhighlight>
</source>
 
PHP najpierw przypisze "5" do zmiennej <code>$e</code>, zwracając jednocześnie "5" tak, by mogło być ono przypisane do <code>$d</code>, potem do <code>$c</code>, <code>$b</code> i na końcu <code>$a</code>. W ten sposób jednym wielkim wyrażeniem zainicjowaliśmy pięć zmiennych naraz.
Linia 426:
Te operatory po prostu skracają zapis i czynią go czytelniejszym. Warto o nich pamiętać szczególnie przy operacjach na ciągach tekstu, kiedy nasz algorytm składa jakąś treść, doczepiając kolejne jej partie do wybranej zmiennej:
 
<sourcesyntaxhighlight lang="php" line><?php
 
$tekst = 'Litwo, ojczyzno moja! Ty jesteś jak zdrowie<br/>';
Linia 434:
 
echo $tekst;
</syntaxhighlight>
</source>
 
Rezultat:
Linia 481:
Wiemy już, że tablica jest zmienną, która grupuje sobie mniejsze zmienne opisywane przez ich indeksy (wartości ''x'' w naszej tabelce funkcji). Najważniejsze jest jednak to, że przy odwoływaniu się do nich, potrzebny nam indeks możemy określić zwyczajnym wyrażeniem! To oznacza, że zadanie wymienione akapit wyżej staje się realne. Zanim je zaprogramujemy, nieco informacji o składni tablic. Na początek utwórzmy pustą tablicę:
 
<sourcesyntaxhighlight lang="php" line><?php
$tablica = array();
</syntaxhighlight>
</source>
 
Spróbujmy wprowadzić do niej wartości naszej funkcji:
 
<sourcesyntaxhighlight lang="php" line><?php
$tablica = array(0 => 5, 3, 8, 7, 9, 24, 15, 2, 19);
</syntaxhighlight>
</source>
 
Początkowe "0" określa, od jakiej liczby zacząć numerowanie kolejnych elementów. Po strzałce wymieniamy ich wartości oddzielone przecinkiem. Należy pamiętać, że PHP (tak jak wiele popularnych języków programowania) zaczyna numerację zmiennych (indeksów) w tablicy od 0. Dlatego też możemy śmiało pominąć zapis 0 =>. Zapis ten przyda się nam jeżeli nie chcemy zacząć numeracji od 0, ale np. od 1, piszemy wtedy array( 1=> 5.... Teraz spróbujmy dostać się do jakiejś z nich.
 
<sourcesyntaxhighlight lang="php" line><?php
$tablica = array(0 => 5, 3, 8, 7, 9, 24, 15, 2, 19);
echo 'Pod numerem 5 kryje się wartość '.$tablica[5];
</syntaxhighlight>
</source>
 
Pomiędzy nawiasami kwadratowymi wprowadzić musimy wyrażenie określające indeks tablicy, który chcielibyśmy odczytać. Możemy teraz pokusić się o napisanie skryptu losującego elementy:
 
<sourcesyntaxhighlight lang="php" line><?php
$tablica = array(0 => 5, 3, 8, 7, 9, 24, 15, 2, 19);
$liczba_losowa = rand(0, 7);
echo 'Pod numerem '.$liczba_losowa.' kryje się wartość '.$tablica[$liczba_losowa];
</syntaxhighlight>
</source>
 
W tym skrypcie za wybranie indeksu tablicy odpowiada funkcja <code>rand()</code> zwracająca losową<ref>Tak naprawdę komputer nie potrafi losować liczb. Za całą tą zasłonką kryją się różne skomplikowane wzory matematyczne inicjowane najczęściej aktualnym czasem, dające wrażenie losowości wyników.</ref> wartość z tablicy.
Linia 510:
Indeksy tablicy wcale nie muszą być numeryczne. PHP dopuszcza także tekstowe wersje. Mamy wtedy do czynienia z tablicami asocjacyjnymi.
 
<sourcesyntaxhighlight lang="php" line><?php
$artykul = array(
'tytul' => 'Tytuł artykułu',
Linia 520:
echo '<p>Napisany dnia '.$artykul['data'].'</p>';
echo '<p>'.$artykul['tresc'].'</p>';
</syntaxhighlight>
</source>
 
Mogą istnieć także tablice mieszane, w których występują zarówno indeksy tekstowe, jak i numeryczne. Pamiętaj, że każdy element tablicy zachowuje się, jak zwykła zmienna, dlatego także możesz przypisywać do niego dowolne wartości już po utworzeniu tablicy.
 
<sourcesyntaxhighlight lang="php" line><?php
 
$tablica = array(0 => 5, 3, 8, 7, 9, 24, 15, 2, 19);
Linia 532:
 
var_dump($tablica);
</syntaxhighlight>
</source>
 
Najpierw przypisaliśmy do losowego elementu tablicy nową wartość: 6. Całość wyświetlamy funkcją <code>var_dump()</code>. Przydaje się ona przy poszukiwaniu błędów w skrypcie. Potrafi zaprezentować w czytelnej formie każdy typ danych, więc możemy za jej pomocą kontrolować, czy na danym etapie wykonywania rezultaty są takie, jakie być powinny. Podobne działanie ma funkcja <code>print_r()</code>, przy czym <code>var_dump()</code> generuje gotowy kod HTML, otoczony znacznikami <code>&lt;pre&gt; &lt;/pre&gt;</code> i sformatowany, podczas gdy <code>print_r()</code> zwraca tekst sformatowany, ale bez znaczników HTML.
Linia 538:
Zobacz teraz, jak zachowuje się <code>$tablica</code>, kiedy próbujemy ją wywołać samodzielnie:
 
<sourcesyntaxhighlight lang="php" line><?php
$tablica = array(0 => 5, 3, 8, 7, 9, 24, 15, 2, 19);
 
echo $tablica;
</syntaxhighlight>
</source>
 
Skrypt ten pokaże nam tylko jeden napis: ''Array'', czyli... nazwę typu. Właśnie z tego powodu ostrzegaliśmy przed wprowadzaniem danych do funkcji jako <code>funkcja("$zmienna");</code>. Gdyby w zmiennej była tablica, do funkcji zamiast niej dotarłby napis ''Array'' i całość przestałaby działać. Osobną kwestią jest wydajność takiego zmuszania do konwersji do tekstu, a potem z powrotem na tekst właściwy.