PHP'de @ sembolünün kullanımı nedir?


577

@Aşağıdaki gibi bazı işlevlerin önünde kullanımlarını gördüm :

$fileHandle = @fopen($fileName, $writeAttributes);

Bu sembolün kullanımı nedir?


3
Hem RichieHindle hem de Aiden Bell doğru cevabı verdi, ancak sadece bir cevabı kabul edildiği gibi ayarlayabildiğim için ilk cevabı seçeceğim. Üzgünüz Aiden
sv_in

1
Hataları bastırmak (hoş olmasına rağmen) kod tabanını korurken hatalar yol
açabilir

Yanıtlar:


636

Hata mesajlarını bastırır - PHP kılavuzundaki Hata Kontrol Operatörlerine bakın .


46
Bu biraz hızlı bir beraberlikti!
Aiden Bell

6
Evet; aşağı ikinci! İlk kimin geldiğini görmek için answer-id'leri kontrol etmek zorunda kaldım :)
Sampson

3
Gönderdikten sonra bastırma yazımımı düzeltmek için zamanım vardı ... ve aynı anda bir bağlantı ile geliştirmek için lanet olsun öfke : P
Aiden Bell

1
Harika özellik .. Hataların isset()önüne geçmek için gereksizdir undefined offset.
WM

470

Hataları bastırır.

Kılavuzdaki Hata Kontrol Operatörlerine bakın :

PHP bir hata kontrol operatörünü destekler: at işareti (@). PHP'de bir ifadeye eklendiğinde, söz konusu ifadenin üretebileceği hata mesajları yok sayılır.

Set_error_handler () ile özel bir hata işleyici işlevi ayarladıysanız , yine de çağrılır, ancak bu özel hata işleyici , hatayı tetikleyen çağrı bir @ ile geldiğinde 0 döndürecek olan error_reporting () öğesini çağırabilir (ve yapmalıdır). ...


157
diğer cevabı tüm aşkı elde ettiği için oyladı.
ajacian81

10
19 geride ... hadi insanlar hadi yenelim RichieHindle: P
Aiden Bell

Bu cevap ilk cevaptı (İlk cevaplayanla bağlamda).
Mohd Abdul Mujib

227

@Semboldür hata kontrolü operatör (aka "sessizlik" ya da "kapatma yukarı" operatör). PHP'nin ilişkili ifade tarafından üretilen hata mesajlarını (uyarı, uyarı, ölümcül, vb.) Bastırmasını sağlar. Tıpkı tek bir operatör gibi çalışır, örneğin, bir önceliği ve ilişkilendirilebilirliği vardır. Aşağıda bazı örnekler verilmiştir:

@echo 1 / 0;
// generates "Parse error: syntax error, unexpected T_ECHO" since 
// echo is not an expression

echo @(1 / 0);
// suppressed "Warning: Division by zero"

@$i / 0;
// suppressed "Notice: Undefined variable: i"
// displayed "Warning: Division by zero"

@($i / 0);
// suppressed "Notice: Undefined variable: i"
// suppressed "Warning: Division by zero"

$c = @$_POST["a"] + @$_POST["b"];
// suppressed "Notice: Undefined index: a"
// suppressed "Notice: Undefined index: b"

$c = @foobar();
echo "Script was not terminated";
// suppressed "Fatal error: Call to undefined function foobar()"
// however, PHP did not "ignore" the error and terminated the
// script because the error was "fatal"

Standart PHP hata işleyicisi yerine özel bir hata işleyicisi kullanırsanız tam olarak ne olur:

Set_error_handler () ile özel bir hata işleyici işlevi ayarladıysanız, yine de çağrılır, ancak bu özel hata işleyici, hatayı tetikleyen çağrı bir @ ile geldiğinde 0 döndürecek olan error_reporting () öğesini çağırabilir (ve yapmalıdır). .

Bu, aşağıdaki kod örneğinde gösterilmiştir:

function bad_error_handler($errno, $errstr, $errfile, $errline, $errcontext) {
    echo "[bad_error_handler]: $errstr";
    return true;
}
set_error_handler("bad_error_handler");
echo @(1 / 0);
// prints "[bad_error_handler]: Division by zero"

Hata işleyici @sembolün etkin olup olmadığını kontrol etmedi . Kılavuz aşağıdakileri önermektedir:

function better_error_handler($errno, $errstr, $errfile, $errline, $errcontext) {
    if(error_reporting() !== 0) {
        echo "[better_error_handler]: $errstr";
    }
    // take appropriate action
    return true;
}

58

Ayrıca, hataların gizlenmesine rağmen, özel hata işleyicilerinin (ile ayarlanmış set_error_handler) yine de yürütüleceğini unutmayın!


34

Daha önce cevaplanmış olanların bazıları gibi: @Operatör, PHP'de bildirimler, uyarılar ve hatta kritik hatalar dahil olmak üzere tüm hataları bastırır.

AMA: Lütfen, gerçekten @operatörü hiç kullanmayın .

Neden?

Çünkü, @operatörü hata bastırma için kullandığınızda, bir hata oluştuğunda nereden başlayacağınıza dair hiçbir fikriniz yoktur. Zaten bazı geliştiricilerin @operatörü oldukça sık kullandığı eski kod ile bazı "eğlenceli" vardı . Özellikle dosya işlemleri, ağ aramaları vb. Durumlarda. Bunların hepsi, birçok geliştiricinin@ operatörün çünkü burada bir hata oluştuğunda bu bazen kapsam dışıdır (örneğin, bir üçüncü taraf API'sine erişilemez, vb.). ).

Ama hala kullanmamanın anlamı nedir? İki açıdan bir bakalım:

Bir geliştirici olarak: Ne zaman@kullanılır, nereden başlayacağım konusunda hiçbir fikrim yok. Hatalı yüzlerce hatta binlerce fonksiyon çağrısı varsa@everyhwere gibi olabilir. Bu durumda makul bir hata ayıklama mümkün değildir. Ve bu sadece bir üçüncü taraf hatası olsa bile - o zaman sorun değil ve hızlı işiniz bitti. ;-) Ayrıca, hata günlüğüne yeterli ayrıntı eklemek daha iyidir, bu nedenle geliştiriciler bir günlük girişinin daha fazla kontrol edilmesi gereken bir şey olup olmadığına veya geliştiricinin kapsamı dışında olan sadece bir üçüncü parti hatası olup olmadığına kolayca karar verebilirler.

Kullanıcı olarak: Kullanıcılar bir hatanın nedeninin ne olduğunu hiç umursamazlar. Çalışmaları, belirli bir görevi bitirmeleri vb. İçin yazılımlar vardır. Geliştiricinin hatası mı yoksa üçüncü taraf sorunu mu umurumda değil. Özellikle kullanıcılar için, kapsam dışı olsalar bile, tüm hataları günlüğe kaydetmenizi önemle tavsiye ederim. Belki belirli bir API'nın sık sık çevrimdışı olduğunu fark edersiniz. Ne yapabilirsin? API iş ortağınızla konuşabilirsiniz ve sabit tutamazlarsa, muhtemelen başka bir iş ortağı aramalısınız.

Kısacası: Şöyle bir şey olduğunu bilmelisiniz @(bilgi her zaman iyidir), ama sadece kullanmayın . Birçok geliştirici (özellikle başkalarının hata ayıklama kodu) çok minnettar olacaktır.


1
Bazı uyarılar yalnızca @ (örneğin, sonucu tahmin etmek için herhangi bir girişimin bir yarış durumuna tabi olduğu fopen ()) kullanılarak güvenilir bir şekilde bastırılabilir, hata durumunu daha düzenli bir şekilde işlemek için kodunuz varsa, usuig @doğru olanı yapar bunu yapmak, özellikle text/htmlistemciye geri dönmüyorsanız (veya benzer bir şey yapmıyorsanız) özellikle yararlıdır . (belki geri dönüyor image/pngya da "json")
Jasen

1
Uyarıları bastırmamalısınız - yanlış bir şey yaptığınızı belirtiyorlar. Durumu düzgün bir şekilde kontrol edemeyeceğiniz veya işleyemeyeceğiniz bir yarış koşulu yoktur.
Ryan Rentfro

1
Birkaç yerde benim kodda aşağıdaki var. if( session_status() == PHP_SESSION_NONE ) session_start(); Bu devralınan eski bir uygulama ve kurulum komut dosyasının birden çok kez çağrıldığı yerler var, bu yüzden test etmek zorundayım. Sadece kullanmanın sorunu ne olurdu @session_start();?
Stephen R

Ne yaptığınızı biliyorsanız ve bunu tutumlu / stratejik olarak kullanıyorsanız, kullanmaya değer. @$this->stats['device_os'][$date][$creative_id][$device_id][$operating_system]['clicks']++;her seviyede isset kontrollerine sahip olmak ve olmadığında doldurmaktan daha iyidir.
dtbarne

1
Bana 12+ satır kod eklemenin ve hiçbir değer eklememenin, ancak kodun okunabilirliğini ve kısalığının azaltılmasının, bir yere "düz kirli" olduğu bir yerde okumaktan ve belki de fikrimi değiştirmekten başka iyi bir neden verin.
dtbarne

7

"@" Operatörünü kullanmadığımızı varsayalım, kodumuz şöyle görünür:

$fileHandle = fopen($fileName, $writeAttributes);

Ve açmaya çalıştığımız dosya bulunamazsa ne olur? Bir hata mesajı gösterecektir.

Hata mesajını bastırmak için "@" operatörünü aşağıdaki gibi kullanıyoruz:

$fileHandle = @fopen($fileName, $writeAttributes);

Bu, PHP'nin neden bu tür bir @çözümü geçici olarak kullandığının mükemmel bir örneğidir . Diğer programlama dilleri, bu tür bir senaryo ile başa çıkmak için tekdüze istisna yönetimine sahiptir stackoverflow.com/questions/1087365
dreftymac

@dreftymac Aynen öyle!
Sujeet Kumar

5

Açık başarısız olursa, E_WARNING seviyesinde bir hata oluşur. Bu uyarıyı bastırmak için @ kullanabilirsiniz.


5

@ hata mesajlarını bastırır.

Aşağıdaki kod snippet'lerinde kullanılır:

@file_get_contents('http://www.exaple.com');

" Http://www.exaple.com " etki alanına erişilemezse, bir hata gösterilir, ancak @hiçbir şey gösterilmez.


1

PHP bir hata kontrol operatörünü destekler: (@) . PHP'de bir ifadeye eklendiğinde, söz konusu ifadenin üretebileceği hata mesajları yok sayılır.

Eğer bir özel hata eylemcisini kurduysanız set_error_handler()o zaman yine aradım ama alacak bu özel hata işleyicisi (ve reddedilmesi gereken) çağrısı error_reporting()dönecektir 0hatayı tetikleyen çağrısı öncesinde zaman @.

<?php
/* Intentional file error */
$my_file = @file ('non_existent_file') or
    die ("Failed opening file: error was '$php_errormsg'");

// this works for any expression, not just functions:
$value = @$cache[$key];
// will not issue a notice if the index $key doesn't exist.

?>

Not:-

1) @ -operator yalnızca ifadelerde çalışır.

2) Basit bir kural şudur: Eğer bir şeyin değerini alabiliyorsanız, @ operatörünün başına ekleyebilirsiniz. Örneğin, değişkenlerin başına, işlevine ekleyebilir ve çağrıları, sabitleri vb. Ekleyebilirsiniz. Bu işlevi işlev veya sınıf tanımlarına veya if ve foreach gibi koşullu yapılara başlatamazsınız.

Uyarı:-

Şu anda "@" hata kontrol operatörü öneki, kod yürütmesini sonlandıracak kritik hatalar için hata raporlamayı devre dışı bırakacaktır. Diğer şeylerin yanı sıra, bu, belirli bir işlevdeki hataları bastırmak için "@" kullanırsanız ve ya kullanılabilir değilse ya da yanlış yazılmışsa, komut dosyasının orada neden olduğuna dair hiçbir belirti olmadan öleceğini gösterir.


1

Burada dikkat etmeniz gereken @ kullanırken birkaç işaretçi eklemeye değer olabilir, tam bir tükenme için bu yayını görüntüleyin: http://mstd.eu/index.php/2016/06/30/php- seri ateş-ne olduğunu-sembolü--için-in-php /

  1. Hata işleyicisi @ simgesi önceden eklenmiş olsa bile tetiklenir, yalnızca 0 hata düzeyinin ayarlandığı anlamına gelir, bunun özel bir hata işleyicisinde uygun şekilde ele alınması gerekir.

  2. @ İle bir dahil etme eklemek, içerme dosyasındaki tüm hataları 0 hata seviyesine ayarlar


1

@fonksiyon tarafından atılan hata mesajını bastırır. fopendosya çıkmadığında bir hata atar. @sembolü, dosya mevcut olmasa bile yürütmenin bir sonraki satıra geçmesini sağlar. Benim önerim, bir PHP kodu geliştirdiğinizde bunu yerel ortamınızda kullanmak değildir.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.