İşlev değiştirgeleri

Bir işleve veri, virgül ayraçlı ifadelerden oluşan bir değiştirge listesi ile aktarılır. Değitirgeler soldan sağa doğru değerlendirilir.

PHP, değiştirgelerin değerleriyle aktarılmalarını (öntanımlı), gönderimli aktarımı ve öntanımlı değiştirge kullanımını destekler. Değiştirge sayısı değişken işlevler de desteklenmektedir.

Örnek 1 - İşlevlere dizi aktarımı

<?php
function dizi_kabul_eder($girdi)
{
    echo 
"$girde[0] + $girdi[1] = "$girdi[0]+$girdi[1];
}
?>

Gönderimli değiştirge kullanımı

Öntanımlı olarak, işlev değiştirgeleri değerleriyle aktarılırlar (bu durumda bir değiştirgenin değeri işlev içinde değiştirildiğinde işlevin çağrıldığı yerdeki değeri bundan etkilenmez. İşlevin çağrıldığı yerdeki değerinin de değişmesini istiyorsanız gönderimli değiştirge kullanmalısınız.

Bir işleve bir değiştirgenin daima gönderimli olarak aktarılmasını istiyorsanız, işlev tanımladığınız yerde o değiştirgenin başına & karakterini koyarak bunu sağlayabilirsiniz:

Örnek 2 - Gönderimli işlev değiştirgelerinin aktarımı

<?php
function şunu_da_ekle(&$dizge)
{
    
$dizge .= 've bir kaç karakter eklenmiştir.';
}
$dzg 'Bu bir dizgedir ';
şunu_da_ekle($dzg);
echo 
$dzg;    // 'Bu bir dizgedir ve bir kaç karakter eklenmiştir.'
              //  çıktısını verir.
?>

Öntanımlı değiştirge değerleri

Bir işlevde, sayıl değiştirgeler için C++ tarzı öntanımlı değerler aşağıdaki biçimde tanımlanabilir:

Örnek 3 - İşlev içinde öntanımlı değiştirge kullanımı

<?php
function kahveyap($hangisi "orta şekerli")
{
    return 
"Bir fincan $hangisi kahve yapalım.\n";
}
echo 
kahveyap();
echo 
makecoffee(null);
echo 
kahveyap("az şekerli");
?>

Yukarıdaki örneğin çıktısı:

Bir fincan orta şekerli kahve yapalım.
Bir fincan kahve yapalım.
Bir fincan az şekerli kahve yapalım.

PHP ayrıca, öntanımlı değer olarak dizilerin ve özel NULL türünün kullanımına da izin verir, örneğin:

Örnek 4 - Sayıl olmayan türlerin öntanımlı değer olarak kullanımı

<?php
function kahveyap($hangi = array("orta şekerli"), $neyde NULL)
{
    
$neyde is_null($neyde) ? "ocakta" $neyde;
    return 
"Bir fincan ".join(" bir fincan "$hangi)." kahve $neyde yapıldı.\n";
}
echo 
kahveyap();
echo 
kahveyap(array("çok şekerli""az şekerli"), "mangalda");
?>

Öntanımlı değer bir değişken, bir sınıf üyesi ya da bir işlev çağrısı değil, bir sabit ifadesi olmalıdır.

Öntanımlı değiştirgeleri kullanırken, öntanımlama yapılmış tüm değiştirgelerin öntanımlama yapılmamış tüm değiştirgelerin sağında yer almasına gerektiğine dikkat edin. Aksi takdirde işler yolunda gitmeyebilir. Aşağıdaki kod parçasını inceleyin:

Örnek 5 - Öntanımlı değiştirgelerin hatalı kullanımı

<?php
function yoğurtyap($nekadar "az"$neli)
{
    return 
"Bir kase $nekadar $neli yoğurt yap.\n";
}

echo 
yoğurtyap("çilekli");   // beklendiği gibi çalışmayacaktır
?>

Yukarıdaki örneğin çıktısı:

Warning: Missing argument 2 for yoğurtyap(), called in
/home/nilgun/dnm/php-dnm on line 7 and defined in
/home/nilgun/dnm/php-dnm on line 2
Bir kase çilekli  yoğurt yap.

Şimdi, yukarıdakini bununla karşılaştıralım:

Örnek 6 - Öntanımlı değiştirgelerin doğru kullanımı

<?php
function yoğurtyap($neli$nekadar"az")
{
    return 
"Bir kase $nekadar $neli yoğurt yap.\n";
}

echo 
yoğurtyap("çilekli");   // beklendiği gibi çalışır
?>

Yukarıdaki örneğin çıktısı:

Bir kase az çilekli yoğurt yap.

Bilginize: PHP 5'den itibaren, gönderimli aktarılabilen değiştirgeler öntanımlı değer içerebilmektedir.

Tür Bildirimleri

Bilginize:

Tür bildirimleri PHP 5'de tür önerileri olarak da bilinir.

Tür bildirimleri işlevlerin çalıştırılması sırasında belli bir tür gerektirmesini sağlar. Eğer değer uygun olmayan bir türdeyse PHP 5'de kurtarılabilir bir ölümcül hata oluşurken, PHP 7'de TypeError istisnası oluşur.

Tür bildirimini belirtmek için, tür ismi değiştirge isminden önce gelmelidir. Değiştirgenin öntanımlı değeri NULL olacaksa bildirim NULL kabul edecek şekilde yapılabilir.

Geçerli türler

Tür Açıklama Minimum PHP sürümü
Sınıf/arayüz ismi Tür olarak bir sınıf veya arayüz ismi belirtilmişse değiştirge bir instanceof olmalıdır. PHP 5.0.0
self Tür, yöntemin tanımlandığı sınıf olarak belirtilirse değiştirge bir instanceof olmalıdır. Bu sadece sınıfın veya örneğinin yöntemlerinde kullanılabilir. PHP 5.0.0
array Değiştirge geçerli bir dizi olmalıdır. PHP 5.1.0
callable Değiştirge geçerli bir işlev olmalıdır. PHP 5.4.0
bool Değiştirge geçerli bir mantıksal değer olmalıdır. PHP 7.0.0
float Değiştirge geçerli bir gerçel değer olmalıdır. PHP 7.0.0
int Değiştirge geçerli bir tamsayı olmalıdır. PHP 7.0.0
string Değiştirge geçerli bir dizge olmalıdır. PHP 7.0.0
iterable Değiştirge ya bir array ya da bir instanceof Traversable olmalıdır. PHP 7.1.0
object Değiştirge bir object olmalıdır. PHP 7.2.0
Uyarı

Yukarıdaki türler için takma ad kullanımı desteklenmemektedir. Ancak, bunlar bir sınıf veya arayüz adı olarak ele alınabilir. Örneğin, boolean türünün bool türü yerine, bir değiştirge gerektiren bir dönüş türü veya instanceof sınıfı bir dönüş değeri veya boolean arayüzü veya bir değiştirge olarak kullanımı:

<?php
 
function test(boolean $param) {}
 
test(true);
 
?>

Yukarıdaki örneğin çıktısı:

 Fatal error: Uncaught TypeError: Argument 1 passed to test() must be an instance of boolean, boolean given, called in - on line 1 and defined in -:1
 

Örnekler

Örnek 7 Temel sınıf türü bildirimi

<?php
class {}
class 
extends {}

// Bu C sınıfını örnek almıyor.
class {}

function 
f(C $c) {
    echo 
get_class($c)."\n";
}

f(new C);
f(new D);
f(new E);
?>

Yukarıdaki örneğin çıktısı:

C
D

Fatal error: Uncaught TypeError: Argument 1 passed to f() must be an instance of C, instance of E given, called in - on line 14 and defined in -:8
Stack trace:
#0 -(14): f(Object(E))
#1 {main}
  thrown in - on line 8

Örnek 8 Temel arayüz türü bildirimi

<?php
interface { public function f(); }
class 
implements { public function f() {} }

// Bu I'yi gerçeklemez.
class {}

function 
f(I $i) {
    echo 
get_class($i)."\n";
}

f(new C);
f(new E);
?>

Yukarıdaki örneğin çıktısı:

C

Fatal error: Uncaught TypeError: Argument 1 passed to f() must implement interface I, instance of E given, called in - on line 13 and defined in -:8
Stack trace:
#0 -(13): f(Object(E))
#1 {main}
  thrown in - on line 8

Örnek 9 Boş olabilen tür bildirimi

<?php
class {}

function 
f(C $c null) {
    
var_dump($c);
}

f(new C);
f(null);
?>

Yukarıdaki örneğin çıktısı:

object(C)#1 (0) {
}
NULL

Kesin tür belirtimi

Öntanımlı olarak PHP yanlış türde belirtilmiş değerleri eğer mümkünse bilinen bir türe zorlar. Örneğin, bir işleve string türünde beklenirken integer türünde bir değer belirtilmişse string türünde bir değişken elde edilir.

Dosyaya özel olmak kaydıyla kesin kipi etkin kılmak mümkündür. Kesin kipte sadece tür belirtiminde belirtilmiş türde bir değer kabul edilir, aksi takdirde bir TypeError istisnası oluşur. Bu kuralın tek istisnası, float türünde bir değer beklenen bir işleve integer türünde bir değer belirtilebilmesidir. Dahili işlevlerin içinden yapılan işlev çağrıları kesin tür belirtiminden etkilenmez.

Kesin kipi etkin kılmak için declare deyimi strict_types bildirimi ile birlikte kullanılır:

Dikkat

Kesin kipi etkin kılmak ayrıca dönen tür bildirimlerini de etkiler.

Bilginize:

Kesin kipin uygulanabilmesi için işlev tanımlarının işlev çağrısının yapıldığı kesin kipli dosyada bulunması gerekmez. Ancak kesin kipli olmayan bir dosyadan yapılan bir işlev çağrısı kesin kipli dosyada tanımlı bir işlevi çağırıyorsa çağrıcının tercihine (zayıf tür) uyulur ve değer zorlanabilir.

Bilginize:

Kesin tür sadece sayısal tür bildirimlerine uygulanır dolayısıyla bunun için PHP 7.0.0 ve sonrası gerekir. Bunun sebebi sayısal tür bildirimlerinin bu sürümde eklenmiş olmasıdır.

Örnek 10 Kesin tür örneği

<?php
declare(strict_types=1);

function 
sum(int $aint $b) {
    return 
$a $b;
}

var_dump(sum(12));
var_dump(sum(1.52.5));
?>

Yukarıdaki örneğin çıktısı:

int(3)

Fatal error: Uncaught TypeError: Argument 1 passed to sum() must be of the type integer, float given, called in - on line 9 and defined in -:4
Stack trace:
#0 -(9): sum(1.5, 2.5)
#1 {main}
  thrown in - on line 4

Örnek 11 Zayıf tür örneği

<?php
function sum(int $aint $b) {
    return 
$a $b;
}

var_dump(sum(12));

// bunlar tamsayıya zorlanacaktır; aşağıdaki çıktıya bakın!
var_dump(sum(1.52.5));
?>

Yukarıdaki örneğin çıktısı:

int(3)
int(3)

Örnek 12 TypeError yakalama

<?php
declare(strict_types=1);

function 
sum(int $aint $b) {
    return 
$a $b;
}

try {
    
var_dump(sum(12));
    
var_dump(sum(1.52.5));
} catch (
TypeError $e) {
    echo 
'Error: '.$e->getMessage();
}
?>

Yukarıdaki örneğin çıktısı:

int(3)
Error: Argument 1 passed to sum() must be of the type integer, float given, called in - on line 10

Değiştirge sayısı değişken işlevler

Değiştirge sayısı değişken kullanıcı tanımlı işlevler desteklenmektedir. PHP 5.6 ve sonrasında bu ... ile, PHP 5.5 ve öncesinde ise func_num_args(), func_get_arg() ve func_get_args() işlevleri sayesinde bu özelliği kolayca kullanabilirsiniz.

PHP 5.6 ve sonrasında ...

PHP 5.6 ve sonrasında, işlevin değişken sayıda değiştirge içerebilmesini sağlamak için değiştirge listesine ... dizgeciği konulabilir. Değiştirgeler belirtilen değikene bir dizi olarak aktarılır. Örnek:

Örnek 13 Değişkenin değiştirgelerine erişim için ... kullanımı

<?php
function sum(...$numbers) {
    
$acc 0;
    foreach (
$numbers as $n) {
        
$acc += $n;
    }
    return 
$acc;
}

echo 
sum(1234);
?>

Yukarıdaki örneğin çıktısı:

10

Bir diziyi, bir Traversable değişkeni veya bir sabiti değiştirge listesi haline getirmek için işlev çağrılırken de ... kullanılabilir. Örnek:

Örnek 14 Değiştirgelere erişmek için ... kullanımı

<?php
function add($a$b) {
    return 
$a $b;
}

echo 
add(...[12])."\n";

$a = [12];
echo 
add(...$a);
?>

Yukarıdaki örneğin çıktısı:

3
3

... dizgeciğinden önce normal konumsal değiştirgeler belirtilebilir. Bu durumda ... ile üretilen diziye sadece bir konumsal değiştirge ile eşleşmeyen tokeni izleyen değiştirgeler eklenir.

... dizgeciğinin önüne bir tür dayatıcı eklemek de mümkündür. Böyle bir durumda, ... tarafından işleme sokulacak tüm değiştirgeler dayatılan sınıfın nesneleri olmalıdır

Örnek 15 Değişken değiştirgelerinde tür dayatma

<?php
function total_intervals($unitDateInterval ...$intervals) {
    
$time 0;
    foreach (
$intervals as $interval) {
        
$time += $interval->$unit;
    }
    return 
$time;
}

$a = new DateInterval('P1D');
$b = new DateInterval('P2D');
echo 
total_intervals('d'$a$b).' gün';

// Bir DateInterval nesnesi olmadığından bu başarısız olur.
echo total_intervals('d'null);
?>

Yukarıdaki örneğin çıktısı:

3 gün
Catchable fatal error: Argument 2 passed to total_intervals() must be an instance of DateInterval, null given, called in - on line 14 and defined in - on line 2

Son olarak, ... dizgeciğinin önüne bir & ekleyerek değişken değiştirgelerini gönderimli olarak da aktarabilirsiniz.

Daha eski PHP sürümlerinde

Bir işlevin değişken sayıda değiştirge içerebilmesi özel bir sözdizimi gerekmez; ancak işlevin değiştirgelerine erişim için func_num_args(), func_get_arg() ve func_get_args() kullanmak gerekir.

PHP 5.5 ve öncesinde yukarıdaki ilk örnek şöyle gerçeklenirdi;

Örnek 16 PHP 5.5 ve öncesinde değişken değiştirgelerine erişim

<?php
function sum() {
    
$acc 0;
    foreach (
func_get_args() as $n) {
        
$acc += $n;
    }
    return 
$acc;
}

echo 
sum(1234);
?>

Yukarıdaki örneğin çıktısı:

10