Referensi PHP 7.2
Referensi PHP 7.1
PHP 7 dirilis pada tanggal 3 Desember 2015. PHP 7 hadir dengan sejumlah fitur baru, perubahan, dan gangguan kompatibilitas mundur yang diuraikan di bawah ini.
Pertunjukan
Fitur
Operator Perbandingan Gabungan
Operator Penggabungan Null
Deklarasi Tipe Skalar
Deklarasi Jenis Pengembalian
Kelas Anonim
Sintaks Pelarian Unicode Codepoint
call()
Metode
Memfilter unserialize()
Kelas IntlChar
Harapan
Deklarasi use
kelompok
Ekspresi Pengembalian Generator
Delegasi Pembangkit
Pembagian Integer dengan intdiv()
session_start()
Opsi
preg_replace_callback_array()
Fungsi
Fungsi CSPRNG
Dukungan untuk Konstanta Array di define()
Penambahan Refleksi
Perubahan
Melonggarkan Batasan Kata yang Dicadangkan
Sintaks Variabel Seragam
Pengecualian di Mesin
Antarmuka yang Dapat Dilempar
Semantik Integer
Ekstensi JSON Diganti dengan JSOND
Kegagalan ZPP karena Melimpah
Perbaikan pada Perilaku foreach()
Perubahan pada Perilaku list()
Perubahan Pembagian dengan Semantik Nol
Perbaikan pada Nilai Pengembalian Pengendali Sesi Kustom
Penghentian Konstruktor Gaya 4 PHP
Penghapusan Peringatan tanggal.zona waktu
Penghapusan Tag PHP Alternatif
Penghapusan Beberapa Blok Default di Pernyataan Switch
Penghapusan Definisi Ulang Parameter dengan Nama Duplikat
Penghapusan API Server Mati
Penghapusan Dukungan Hex dalam String Numerik
Penghapusan Fungsionalitas yang Tidak Digunakan Lagi
Klasifikasi Ulang dan Penghapusan Pemberitahuan E_STRICT
Penghentian Opsi Salt untuk password_hash()
Kesalahan pada Literal Oktal Tidak Valid
substr()
Perubahan Nilai Pengembalian
Pertanyaan Umum
Apa yang terjadi dengan PHP 6?
Tidak diragukan lagi, bagian terbesar dari PHP 7 adalah peningkatan kinerja luar biasa yang diberikannya pada aplikasi. Hal ini merupakan hasil dari pemfaktoran ulang Zend Engine agar menggunakan struktur data yang lebih ringkas dan alokasi/dealokasi heap yang lebih sedikit.
Peningkatan kinerja pada aplikasi dunia nyata akan bervariasi, meskipun banyak aplikasi tampaknya menerima peningkatan kinerja ~100% - dengan konsumsi memori yang lebih rendah juga!
Basis kode yang difaktorkan ulang juga memberikan peluang lebih lanjut untuk pengoptimalan di masa mendatang (seperti kompilasi JIT). Jadi sepertinya versi PHP mendatang juga akan terus mengalami peningkatan kinerja.
Perbandingan grafik kinerja PHP 7:
Turbocharging Web dengan PHP 7
Tolok ukur dari Rasmus's Sydney Talk
Operator perbandingan gabungan (atau operator pesawat ruang angkasa) adalah notasi singkat untuk melakukan perbandingan tiga arah dari dua operan. Ini memiliki nilai pengembalian bilangan bulat yang dapat berupa:
bilangan bulat positif (jika operan sebelah kiri lebih besar dari operan sebelah kanan)
0 (jika kedua operan sama)
bilangan bulat negatif (jika operan sebelah kanan lebih besar dari operan sebelah kiri)
Operator tersebut memiliki prioritas yang sama dengan operator kesetaraan ( ==
, !=
, ===
, !==
) dan memiliki perilaku yang sama persis dengan operator perbandingan longgar lainnya ( <
, >=
, dll). Ini juga non-asosiatif seperti mereka, jadi rangkaian operan (seperti 1 <=> 2 <=> 3
) tidak diperbolehkan.
// membandingkan string lexicallyvar_dump('PHP' <=> 'Node'); // int(1)// membandingkan angka berdasarkan sizevar_dump(123 <=> 456); // int(-1)// membandingkan elemen array yang bersesuaian dengan satu-lainvar_dump(['a', 'b'] <=> ['a', 'b']); // ke dalam(0)
Objek tidak dapat dibandingkan, sehingga menggunakannya sebagai operan dengan operator ini akan menghasilkan perilaku yang tidak terdefinisi.
RFC: Operator Perbandingan Gabungan
Operator penggabungan nol (atau operator ternary isset) adalah notasi singkat untuk melakukan pemeriksaan isset()
pada operator ternary. Ini adalah hal yang umum dilakukan dalam aplikasi, sehingga sintaksis baru telah diperkenalkan untuk tujuan ini.
// Pra kode PHP 7$route = isset($_GET['route']) ? $_GET['route'] : 'index';// kode PHP 7+$route = $_GET['route'] ?? 'indeks';
RFC: Operator Penggabungan Null
Deklarasi tipe skalar hadir dalam dua bentuk: coercive (default) dan strict . Tipe parameter berikut sekarang dapat diterapkan (baik secara paksa atau ketat): string ( string
), bilangan bulat ( int
), angka floating-point ( float
), dan boolean ( bool
). Mereka menambah tipe lain yang diperkenalkan dalam versi PHP 5.x: nama kelas, antarmuka, array
dan callable
.
// Fungsi mode koersif sumOfInts(int ...$ints) { kembalikan array_sum($ints); }var_dump(jumlahInts(2, '3', 4.1)); // ke dalam(9)
Untuk mengaktifkan mode ketat, satu declare()
harus ditempatkan di bagian atas file. Ini berarti ketatnya pengetikan skalar dikonfigurasikan berdasarkan per file. Arahan ini tidak hanya memengaruhi deklarasi tipe parameter, namun juga tipe pengembalian fungsi (lihat Deklarasi Tipe Pengembalian), fungsi PHP bawaan, dan fungsi dari ekstensi yang dimuat.
Jika pemeriksaan tipe gagal, maka pengecualian TypeError
(lihat Pengecualian di Mesin) akan ditampilkan. Satu-satunya keringanan hukuman yang ada dalam pengetikan ketat adalah konversi otomatis bilangan bulat menjadi float (tetapi tidak sebaliknya) ketika bilangan bulat disediakan dalam konteks float.
menyatakan(strict_types=1);fungsi berkembang biak(float $x, float $y) { kembalikan $x * $y; }penambahan fungsi(int $x, int $y) { kembalikan $x + $y; }var_dump(kalikan(2, 3,5)); // float(7)var_dump(tambahkan('2', 3)); // Kesalahan fatal: TypeError Tidak Tertangkap: Argumen 1 yang diteruskan ke add() harus bertipe integer, string diberikan...
Perhatikan bahwa hanya konteks pemanggilan yang berlaku ketika pemeriksaan tipe dilakukan. Ini berarti pengetikan ketat hanya berlaku untuk pemanggilan fungsi/metode, dan bukan pada definisi fungsi/metode. Dalam contoh di atas, kedua fungsi tersebut bisa saja dideklarasikan dalam file strict atau coercive, namun selama keduanya dipanggil dalam file strict, aturan pengetikan ketat akan berlaku.
Istirahat SM
Kelas dengan nama int
, string
, float
, dan bool
kini dilarang.
RFC: Deklarasi Tipe Skalar
Deklarasi tipe pengembalian memungkinkan untuk menentukan tipe pengembalian suatu fungsi, metode, atau penutupan. Tipe pengembalian berikut ini didukung: string
, int
, float
, bool
, array
, callable
, self
(hanya metode), parent
(hanya metode), Closure
, nama kelas, dan nama antarmuka.
fungsi arrayJumlah(array ...$array): array{ return array_map(function(array $array): int { return array_sum($array); }, $array); }print_r(arraysSum([1,2,3], [4,5,6], [7,8,9]));/* OutputArray( [0] => 6 [1] => 15 [2] => 24)*/
Sehubungan dengan subtipe, invarian telah dipilih untuk tipe pengembalian. Ini berarti bahwa ketika suatu metode ditimpa dalam kelas subtipe atau diimplementasikan seperti yang ditentukan dalam kontrak, tipe pengembaliannya harus sama persis dengan metode yang diimplementasikan (kembali).
kelas A {}kelas B memperluas A {}kelas C { tes fungsi publik() : A { kembalikan A baru; } }kelas D meluas C { // mengganti metode C::test() : Fungsi publik test() : B // Kesalahan fatal karena ketidakcocokan varians { kembalikan B baru; } }
Metode utama D::test() : B
menyebabkan E_COMPILE_ERROR
karena kovarians tidak diperbolehkan. Agar ini berfungsi, metode D::test()
harus memiliki tipe kembalian A
.
kelas A {}antarmuka SomeInterface { tes fungsi publik() : A; }kelas B mengimplementasikan SomeInterface { tes fungsi publik() : A // semuanya baik-baik saja! { kembalikan nol; // Kesalahan fatal: TypeError Tidak Tertangkap: Nilai kembalian B::test() harus berupa instance A, null dikembalikan... } }
Kali ini, metode yang diterapkan menyebabkan pengecualian TypeError
(lihat Pengecualian di Mesin) dilempar saat dijalankan. Hal ini karena null
bukan tipe pengembalian yang valid - hanya instance kelas A
yang dapat dikembalikan.
RFC: Deklarasi Jenis Pengembalian
Kelas anonim berguna ketika objek sederhana dan hanya sekali perlu dibuat.
// Logger kelas kode Pra PHP 7 { log fungsi publik($pesan) { gema $pesan; } }$util->setLogger(Logger baru());// kode PHP 7+$util->setLogger(kelas baru { log fungsi publik($msg) { gema $pesan; } });
Mereka dapat meneruskan argumen ke konstruktornya, memperluas kelas lain, mengimplementasikan antarmuka, dan menggunakan sifat-sifat seperti yang dapat dilakukan oleh kelas normal:
kelas SomeClass {}antarmuka SomeInterface {}sifat SomeTrait {}var_dump(kelas baru(10) extends SomeClass mengimplementasikan SomeInterface { private $num; public function __construct($num) { $ini->angka = $angka; } gunakan Beberapa Sifat; });/** Output:object(class@anonymous)#1 (1) { ["Kode baris perintah0x104c5b612":"class@anonymous":private]=> int(10)}*/
Menyatukan kelas anonim di dalam kelas lain tidak memberikannya akses ke metode atau properti privat atau terlindung apa pun dari kelas luar tersebut. Untuk menggunakan properti atau metode kelas luar yang dilindungi, kelas anonim dapat memperluas kelas luar. Untuk menggunakan properti privat atau terlindungi dari kelas luar di kelas anonim, properti tersebut harus melewati konstruktornya:
<?phpclass Luar { pribadi $prop = 1; dilindungi $prop2 = 2; fungsi yang dilindungi func1() { kembali 3; } fungsi publik fungsi2() { return new class($this->prop) extends Luar { private $prop3; fungsi publik __konstruksi($prop) { $ini->prop3 = $prop; } fungsi publik func3() { kembalikan $ini->prop2 + $ini->prop3 + $ini->func1(); } }; } }echo (Baru Luar)->func2()->func3(); // 6
RFC: Kelas Anonim
Hal ini memungkinkan titik kode unicode yang dikodekan UTF-8 menjadi keluaran dalam string yang diberi tanda kutip ganda atau dokumen heredoc. Titik kode apa pun yang valid diterima, dengan awalan 0
bersifat opsional.
gema "u{aa}"; // ªgema "u{0000aa}"; // ª (sama seperti sebelumnya tetapi dengan awalan 0 opsional)echo "u{9999}"; // 香
RFC: Sintaks Pelarian Unicode Codepoint
Metode call()
baru untuk penutupan digunakan sebagai cara singkat untuk memanggil penutupan sambil mengikat lingkup objek ke dalamnya. Hal ini menciptakan kode yang lebih berkinerja dan ringkas dengan menghilangkan kebutuhan untuk membuat penutupan perantara sebelum menjalankannya.
kelas A {pribadi $x = 1;}// Pra kode PHP 7$getXCB = function() {return $this->x;};$getX = $getXCB->bindTo(new A, 'A'); // penutupan perantara $getX(); // 1// PHP 7+ kode$getX = function() {return $this->x;};echo $getX->call(new A); // 1
RFC: Penutupan::panggilan
unserialize()
Fitur ini berupaya memberikan keamanan yang lebih baik saat membatalkan serialisasi objek pada data yang tidak tepercaya. Ini mencegah kemungkinan injeksi kode dengan memungkinkan pengembang memasukkan kelas ke dalam daftar putih yang dapat di-unserialisasi.
// mengubah semua objek menjadi __PHP_Incomplete_Class object$data = unserialize($foo, ["allowed_classes" => false]);// mengubah semua objek menjadi objek __PHP_Incomplete_Class kecuali objek MyClass dan MyClass2$data = unserialize($foo, [" diperbolehkan_classes" => ["MyClass", "MyClass2"]]);// perilaku default (sama dengan menghilangkan argumen kedua) yang menerima semua kelas$data = unserialize($foo, ["allowed_classes" => true]);
RFC: Difilter unserialize()
IntlChar
Kelas IntlChar
baru berupaya untuk mengekspos fungsionalitas ICU tambahan. Kelas itu sendiri mendefinisikan sejumlah metode statis dan konstanta yang dapat digunakan untuk memanipulasi karakter unicode.
printf('%x', IntlChar::CODEPOINT_MAX); // 10ffffecho IntlChar::charName('@'); // ATvar_dump KOMERSIAL(IntlChar::ispunct('!')); // bodoh(benar)
Untuk menggunakan kelas ini, ekstensi Intl
harus diinstal.
Istirahat SM
Kelas dalam namespace global tidak boleh dipanggil IntlChar
.
RFC: kelas IntlChar
Ekspektasi merupakan peningkatan yang kompatibel dengan fungsi assert()
yang lebih lama. Mereka memungkinkan pernyataan tanpa biaya dalam kode produksi, dan memberikan kemampuan untuk memberikan pengecualian khusus pada kesalahan.
Prototipe fungsi assert()
adalah sebagai berikut:
void assert (mixed $expression [, mixed $message]);
Seperti API lama, jika $expression
berupa string, maka akan dievaluasi. Jika argumen pertama salah, maka pernyataan tersebut gagal. Argumen kedua bisa berupa string biasa (menyebabkan AssertionError terpicu), atau objek pengecualian khusus yang berisi pesan kesalahan.
ini_set('assert.Exception', 1);class CustomError extends AssertionError {}assert(false, new CustomError('Beberapa pesan kesalahan'));
Dengan fitur ini hadir dua pengaturan PHP.ini (bersama dengan nilai defaultnya):
zend.pernyataan = 1
menegaskan.pengecualian = 0
zend.assertions memiliki tiga nilai:
1 = menghasilkan dan mengeksekusi kode (mode pengembangan)
0 = menghasilkan kode dan melompatinya saat runtime
-1 = jangan buat kode apa pun (tanpa biaya, mode produksi)
menegaskan.pengecualian berarti pengecualian dilemparkan ketika pernyataan gagal. Ini dinonaktifkan secara default agar tetap kompatibel dengan fungsi assert()
yang lama.
RFC: Harapan
use
kelompok Hal ini memberikan kemampuan untuk mengelompokkan beberapa deklarasi use
berdasarkan namespace induk. Ini berupaya menghilangkan verbositas kode saat mengimpor beberapa kelas, fungsi, atau konstanta yang berada di bawah namespace yang sama.
// Pra kode PHP 7gunakan somenamespaceClassA;gunakan somenamespaceClassB;gunakan somenamespaceClassC sebagai C;gunakan fungsi somenamespacefn_a;gunakan fungsi somenamespacefn_b;gunakan fungsi somenamespace fn_c;gunakan const somenamespaceConstA;gunakan const somenamespaceConstB;gunakan const somenamespaceConstC;// penggunaan kode PHP 7+ somenamespace{ClassA, ClassB, ClassC as C};gunakan fungsi somenamespace{fn_a, fn_b, fn_c};gunakan const somenamespace{ConstA, ConstB, ConstC};
RFC: Deklarasi Penggunaan Grup
Fitur ini dibangun berdasarkan fungsionalitas generator yang diperkenalkan ke PHP 5.5. Hal ini memungkinkan pernyataan return
digunakan dalam generator untuk memungkinkan ekspresi akhir dikembalikan (return by reference tidak diperbolehkan). Nilai ini dapat diambil menggunakan metode Generator::getReturn()
baru, yang hanya dapat digunakan setelah generator selesai menghasilkan nilai.
// Sintaks IIFE sekarang dimungkinkan - lihat subbagian Sintaks Variabel Seragam di bagian Perubahan$gen = (function() { hasil 1; hasil 2; pengembalian 3; })();foreach ($gen sebagai $val) { echo $val, PHP_EOL; }gema $gen->getReturn(), PHP_EOL;// keluaran:// 1// 2// 3
Mampu mengembalikan nilai akhir secara eksplisit dari generator adalah kemampuan yang berguna untuk dimiliki. Hal ini karena memungkinkan nilai akhir dikembalikan oleh generator (mungkin dari beberapa bentuk komputasi coroutine) yang secara khusus dapat ditangani oleh kode klien yang mengeksekusi generator. Ini jauh lebih sederhana daripada memaksa kode klien untuk terlebih dahulu memeriksa apakah nilai akhir telah dihasilkan, dan kemudian jika demikian, menangani nilai tersebut secara spesifik.
RFC: Ekspresi Pengembalian Generator
Delegasi generator dibangun berdasarkan kemampuan untuk mengembalikan ekspresi dari generator. Hal ini dilakukan dengan menggunakan sintaksis yield from <expr>
, yang dapat berupa objek atau larik Traversable
apa pun. Ini akan dilanjutkan hingga tidak valid lagi, dan kemudian eksekusi akan dilanjutkan di generator panggilan. Fitur ini memungkinkan pernyataan yield
dipecah menjadi operasi yang lebih kecil, sehingga mendorong kode yang lebih bersih dan lebih dapat digunakan kembali.
fungsi gen() { hasil 1; hasil 2; mengembalikan hasil dari gen2(); }fungsi gen2() { hasil 3; kembali 4; }$gen = gen();foreach ($gen sebagai $val) { gema $val, PHP_EOL; }echo $gen->getReturn();// keluaran// 1// 2// 3// 4
RFC: Delegasi Generator
intdiv()
Fungsi intdiv()
telah diperkenalkan untuk menangani pembagian di mana bilangan bulat akan dikembalikan.
var_dump(intdiv(10, 3)); // ke dalam(3)
Istirahat SM
Fungsi dalam namespace global tidak boleh dipanggil intdiv
.
RFC: intdiv()
session_start()
Opsi Fitur ini memberikan kemampuan untuk meneruskan serangkaian opsi ke fungsi session_start()
. Ini digunakan untuk mengatur opsi php.ini berbasis sesi:
session_start(['cache_limiter' => 'pribadi']); // menyetel opsi session.cache_limiter ke pribadi
Fitur ini juga memperkenalkan pengaturan php.ini baru ( session.lazy_write
) yang, secara default, disetel ke true dan berarti data sesi hanya ditulis ulang jika berubah.
RFC: Perkenalkan opsi session_start()
preg_replace_callback_array()
Fungsi Fungsi baru ini memungkinkan kode ditulis lebih rapi saat menggunakan fungsi preg_replace_callback()
. Sebelum PHP 7, callback yang perlu dieksekusi per ekspresi reguler memerlukan fungsi callback (parameter kedua preg_replace_callback()
) untuk dicemari dengan banyak percabangan (paling baik metode hacky).
Sekarang, callback dapat didaftarkan ke setiap ekspresi reguler menggunakan array asosiatif, dengan kuncinya adalah ekspresi reguler dan nilainya adalah callback.
Tanda Tangan Fungsi:
string preg_replace_callback_array(array $regexesAndCallbacks, string $input);
$tokenStream = []; // [tokenName, leksem] berpasangan$input = <<<'end'$a = 3; // inisialisasi variabelakhir;// Pra PHP 7 codepreg_replace_callback( [ '~$[a-z_][azd_]*~i', '~=~', '~[d]+~', '~;~', '~//.*~' ], fungsi ($match) gunakan (&$tokenStream) { if (strpos($match[0], '$') === 0) { $tokenStream[] = ['T_VARIABLE', $match[0]] ; } elseif (strpos($match[0], '=') === 0) { $tokenStream[] = ['T_ASSIGN', $match[0]]; } elseif (ctype_digit($match[0])) { $tokenStream[] = ['T_NUM', $match[0]]; } elseif (strpos($match[0], ';') === 0) { $tokenStream[] = ['T_TERMINATE_STMT', $match[0]]; } elseif (strpos($match[0], '//') === 0) { $tokenStream[] = ['T_COMMENT', $match[0]]; } }, $input);// PHP 7+ codepreg_replace_callback_array( [ '~$[a-z_][azd_]*~i' => fungsi ($match) gunakan (&$tokenStream) { $tokenStream[] = ['T_VARIABLE', $match[0]]; }, '~=~' => fungsi ($match) gunakan (&$tokenStream) { $tokenStream[] = ['T_ASSIGN', $match[0]]; }, '~[d]+~' => fungsi ($match) gunakan (&$tokenStream) { $tokenStream[] = ['T_NUM', $match[0]]; }, '~;~' => fungsi ($match) gunakan (&$tokenStream) { $tokenStream[] = ['T_TERMINATE_STMT', $match[0]]; }, '~//.*~' => fungsi ($match) gunakan (&$tokenStream) { $tokenStream[] = ['T_COMMENT', $match[0]]; } ], $masukan);
Istirahat SM
Fungsi dalam namespace global tidak boleh dipanggil preg_replace_callback_array
.
RFC: Tambahkan Fungsi preg_replace_callback_array
Fitur ini memperkenalkan dua fungsi baru untuk menghasilkan bilangan bulat dan string yang aman secara kriptografis. Mereka mengekspos API sederhana dan tidak bergantung pada platform.
Tanda tangan fungsi:
string random_bytes(int length); int random_int(int min, int max);
Kedua fungsi akan mengeluarkan pengecualian Error
jika sumber keacakan yang memadai tidak dapat ditemukan.
Istirahat SM
Fungsi dalam namespace global tidak boleh dipanggil random_int
atau random_bytes
.
RFC: CSPRNG lahan pengguna yang mudah
define()
Kemampuan untuk mendefinisikan konstanta array diperkenalkan di PHP 5.6 menggunakan kata kunci const
. Kemampuan ini kini telah diterapkan pada fungsi define()
juga:
mendefinisikan('ALLOWED_IMAGE_EXTENSIONS', ['jpg', 'jpeg', 'gif', 'png']);
RFC: tidak ada RFC yang tersedia
Dua kelas refleksi baru telah diperkenalkan di PHP 7. Yang pertama adalah ReflectionGenerator
, yang digunakan untuk introspeksi pada generator:
kelas ReflectionGenerator { publik __construct(Generator $gen) array publik getTrace($options = DEBUG_BACKTRACE_PROVIDE_OBJECT) publik int getExecutingLine (batal) string publik getExecutingFile (batal) Fungsi Refleksi publikAbstrak getFunction(batal) Objek publik getThis (batal) Generator publik getExecutingGenerator (batal) }
Yang kedua adalah ReflectionType
untuk lebih mendukung fitur deklarasi skalar dan tipe kembalian:
kelas Tipe Refleksi { bool publik memungkinkanNull(void) bool publik isBuiltin(void) string publik __toString(void) }
Selain itu, dua metode baru telah diperkenalkan ke dalam ReflectionParameter
:
kelas ReflectionParameter { // ... public bool hasType(void) public ReflectionType getType(void) }
Serta dua metode baru di ReflectionFunctionAbstract
:
kelas ReflectionFunctionAbstract { // ... public bool hasReturnType(void) public ReflectionType getReturnType(void) }
Istirahat SM
Kelas dalam namespace global tidak boleh disebut ReflectionGenerator
atau ReflectionType
.
RFC: tidak ada RFC yang tersedia
Kata-kata yang dicadangkan secara global sebagai nama properti, konstanta, dan metode dalam kelas, antarmuka, dan sifat kini diperbolehkan. Hal ini mengurangi munculnya jeda BC ketika kata kunci baru diperkenalkan dan menghindari pembatasan penamaan pada API.
Hal ini sangat berguna ketika membuat DSL internal dengan antarmuka yang lancar:
// 'baru', 'pribadi', dan 'untuk' sebelumnya tidak dapat digunakanProyek::baru('Nama Proyek')->pribadi()->untuk('tujuan di sini')->dengan('nama pengguna di sini');
Satu-satunya batasan adalah bahwa kata kunci class
masih tidak dapat digunakan sebagai nama konstan, jika tidak maka akan bertentangan dengan sintaks resolusi nama kelas ( ClassName::class
).
RFC: Lexer Sensitif Konteks
Perubahan ini membawa ortogonalitas yang jauh lebih besar pada operator variabel di PHP. Hal ini memungkinkan sejumlah kombinasi operator baru yang sebelumnya tidak diizinkan, sehingga memperkenalkan cara baru untuk mencapai operasi lama dalam kode terser.
// nesting ::$foo::$bar::$baz // mengakses properti $baz dari properti $foo::$bar// nesting ()foo()() // memanggil kembalinya foo() // operator pada ekspresi yang diapit dalam ()(function () {})() // Sintaks IIFE dari JS
Kemampuan untuk menggabungkan operator variabel secara sewenang-wenang berasal dari membalikkan semantik evaluasi referensi variabel, properti, dan metode tidak langsung. Perilaku baru ini lebih intuitif dan selalu mengikuti urutan evaluasi dari kiri ke kanan:
// arti lama // arti baru$$foo['bar']['baz'] ${$foo['bar']['baz']} ($$foo)['bar']['baz' ]$foo->$bar['baz'] $foo->{$bar['baz']} ($foo->$bar)['baz']$foo->$bar['baz']( ) $foo->{$bar['baz']}() ($foo->$bar)['baz']() Foo::$bar['baz']() Foo::{$bar['baz']}() (Foo::$bar)['baz']()
Istirahat SM
Kode yang mengandalkan urutan evaluasi lama harus ditulis ulang agar secara eksplisit menggunakan urutan evaluasi tersebut dengan kurung kurawal (lihat kolom tengah di atas). Ini akan membuat kode tersebut kompatibel ke depan dengan PHP 7.x dan kompatibel ke belakang dengan PHP 5.x
RFC: Sintaks Variabel Seragam
Pengecualian di mesin mengubah banyak kesalahan fatal yang fatal dan dapat dipulihkan menjadi pengecualian. Hal ini memungkinkan degradasi aplikasi secara baik melalui prosedur penanganan kesalahan khusus. Ini juga berarti bahwa fitur-fitur yang didorong oleh pembersihan seperti klausa finally
dan destruktor objek sekarang akan dieksekusi. Selanjutnya, dengan menggunakan pengecualian untuk kesalahan aplikasi, pelacakan tumpukan akan dihasilkan untuk informasi debug tambahan.
fungsi jumlah(float ...$angka) : float{ return array_sum($angka); }coba { $total = jumlah(3, 4, null); } catch (TypeError $typeErr) {// menangani kesalahan tipe di sini}
Hierarki pengecualian baru adalah sebagai berikut:
interface Throwable |- Exception implements Throwable |- ... |- Error implements Throwable |- TypeError extends Error |- ParseError extends Error |- AssertionError extends Error |- ArithmeticError extends Error |- DivisionByZeroError extends ArithmeticError
Lihat subbagian Antarmuka yang Dapat Dilempar di bagian Perubahan untuk informasi selengkapnya tentang hierarki pengecualian baru ini.
Istirahat SM
Penangan kesalahan khusus yang digunakan untuk menangani (dan biasanya mengabaikan) kesalahan fatal yang dapat dipulihkan tidak akan berfungsi lagi karena pengecualian sekarang akan diberikan
Kesalahan penguraian yang terjadi dalam kode ed eval()
sekarang akan menjadi pengecualian, mengharuskannya dibungkus dalam blok try...catch
RFC: Pengecualian pada Mesin
Perubahan ini mempengaruhi hierarki pengecualian PHP karena diperkenalkannya pengecualian di mesin. Daripada menempatkan kesalahan fatal yang fatal dan dapat dipulihkan di bawah hierarki kelas Exception
yang sudah ada sebelumnya, diputuskan untuk menerapkan hierarki pengecualian baru untuk mencegah kode PHP 5.x menangkap pengecualian baru ini dengan catch-all ( catch (Exception $e)
) klausa.
Hierarki pengecualian baru adalah sebagai berikut:
interface Throwable |- Exception implements Throwable |- ... |- Error implements Throwable |- TypeError extends Error |- ParseError extends Error |- AssertionError extends Error |- ArithmeticError extends Error |- DivisionByZeroError extends ArithmeticError
Antarmuka Throwable
diimplementasikan oleh hierarki kelas dasar Exception
dan Error
dan mendefinisikan kontrak berikut:
interface Throwable { final public string getMessage ( void ) final public mixed getCode ( void ) final public string getFile ( void ) final public int getLine ( void ) final public array getTrace ( void ) final public string getTraceAsString ( void ) public string __toString ( void ) }
Throwable
tidak dapat diimplementasikan oleh kelas yang ditentukan pengguna - sebagai gantinya, kelas pengecualian khusus harus memperluas salah satu kelas pengecualian yang sudah ada sebelumnya di PHP.
RFC: Antarmuka yang Dapat Dilempar
Semantik untuk beberapa perilaku berbasis bilangan bulat telah diubah dalam upaya menjadikannya lebih intuitif dan tidak bergantung pada platform. Berikut daftar perubahan tersebut:
Mentransmisikan NAN
dan INF
ke bilangan bulat akan selalu menghasilkan 0
Pergeseran bitwise dengan jumlah bit negatif sekarang tidak diperbolehkan (menyebabkan bool(false) kembali dan mengeluarkan E_WARNING)
Pergeseran bit ke kiri sebanyak beberapa bit melebihi lebar bit bilangan bulat akan selalu menghasilkan 0
Pergeseran bitwise ke kanan sejumlah bit melebihi lebar bit bilangan bulat akan selalu menghasilkan 0 atau -1 (tergantung tanda)
Istirahat SM
Ketergantungan pada semantik lama untuk hal di atas tidak akan berfungsi lagi
RFC: Semantik Integer
Lisensi ekstensi JSON lama dianggap tidak gratis, sehingga menyebabkan masalah bagi banyak distribusi berbasis Linux. Ekstensi tersebut telah diganti dengan JSOND dan hadir dengan beberapa peningkatan kinerja dan gangguan kompatibilitas ke belakang.
Istirahat SM
Angka tidak boleh diakhiri dengan koma (yaitu 34.
harus diubah menjadi 34.0
atau hanya 34
)
Eksponen e
tidak boleh langsung mengikuti koma (yaitu 3.e3
harus diubah menjadi 3.0e3
atau hanya 3e3
)
RFC: Ganti ekstensi json saat ini dengan jsond
Pemaksaan antara float ke integer dapat terjadi ketika float diteruskan ke fungsi internal yang mengharapkan integer. Jika float terlalu besar untuk direpresentasikan sebagai bilangan bulat, maka nilainya akan terpotong secara diam-diam (yang dapat mengakibatkan hilangnya besaran dan tanda). Hal ini dapat menimbulkan bug yang sulit ditemukan. Oleh karena itu, perubahan ini berupaya memberi tahu pengembang ketika konversi implisit dari float ke integer telah terjadi dan gagal dengan mengembalikan null
dan mengeluarkan E_WARNING.
Istirahat SM
Kode yang dulunya bekerja secara diam-diam sekarang akan mengeluarkan E_WARNING dan mungkin gagal jika hasil pemanggilan fungsi diteruskan langsung ke fungsi lain (karena null
sekarang akan diteruskan).
RFC: Kegagalan ZPP pada Overflow
foreach()
Perulangan foreach()
PHP memiliki sejumlah kasus tepi yang aneh. Ini semua didorong oleh implementasi dan menyebabkan banyak perilaku tidak terdefinisi dan tidak konsisten saat melakukan iterasi antara salinan dan referensi array, saat menggunakan manipulator iterator seperti current()
dan reset()
, saat memodifikasi array yang sedang diiterasi, dan seterusnya.
Perubahan ini menghilangkan perilaku tidak terdefinisi dari kasus-kasus tepi ini dan membuat semantik lebih dapat diprediksi dan intuitif.
foreach()
berdasarkan nilai pada array
$array = [1,2,3];$array2 = &$array;foreach($array sebagai $val) { tidak disetel($array[1]); // memodifikasi array yang diiterasi melalui echo "{$val} - ", current($array), PHP_EOL; }// Pra PHP 7 hasil1 - 33 -// PHP 7+ hasil1 - 12 - 13 - 1
Ketika semantik berdasarkan nilai digunakan, array yang diiterasi sekarang tidak diubah pada tempatnya. current()
sekarang juga memiliki perilaku yang ditentukan, yang akan selalu dimulai di awal array.
foreach()
dengan referensi pada array dan objek dan berdasarkan nilai pada objek
$array = [1,2,3];foreach($array sebagai &$val) { echo "{$val} - ", saat ini($array), PHP_EOL; }// Pra PHP 7 hasil1 - 22 - 33 -// PHP 7+ hasil1 - 12 - 13 - 1
Fungsi current()
tidak lagi terpengaruh oleh iterasi foreach()
pada array. Selain itu, semantik referensi by-reference yang digunakan oleh foreach()
kini bekerja secara independen satu sama lain:
$array = [1,2,3];foreach($array sebagai &$val) { echo $val, PHP_EOL; foreach ($array sebagai &$val2) { tidak disetel($array[1]); gema $val, PHP_EOL; } }// Pra PHP 7 hasil111// PHP 7+ hasil111333
Istirahat SM
Ketergantungan pada semantik lama (unik dan tidak terdokumentasi) tidak akan berfungsi lagi.
RFC: Memperbaiki perilaku "foreach".
list()
Fungsi list()
didokumentasikan tidak mendukung string, namun dalam beberapa kasus string dapat digunakan:
// dereferensi array$str[0] = 'ab';list($a, $b) = $str[0];echo $a; // aecho $b; // b// dereferensi objek$obj = new StdClass();$obj->prop = 'ab';list($a, $b) = $obj->prop;echo $a; // aecho $b; // b// fungsi pengembalian fungsi fungsi() { kembalikan 'ab'; }daftar($a, $b) = func();var_dump($a, $b);echo $a; // aecho $b; // B
Ini sekarang telah diubah sehingga penggunaan string dengan list()
dilarang di semua kasus.
Selain itu, list()
yang kosong kini menjadi kesalahan fatal, dan urutan penetapan variabel telah diubah menjadi kiri ke kanan:
$a = [1, 2];list($a, $b) = $a;// LAMA: $a = 1, $b = 2// BARU: $a = 1, $b = null + "Tidak terdefinisi indeks 1"$b = [1, 2];list($a, $b) = $b;// LAMA: $a = null + "Indeks 0 tidak terdefinisi", $b = 2// BARU: $a = 1, $b = 2
Istirahat SM
Membuat list()
sama dengan nilai string tidak langsung tidak mungkin lagi. null
sekarang akan menjadi nilai untuk variabel $a
dan $b
pada contoh di atas
Memanggil list()
tanpa variabel apa pun akan menyebabkan kesalahan fatal
Ketergantungan pada urutan penetapan kanan-ke-kiri yang lama tidak akan berfungsi lagi
RFC: Memperbaiki inkonsistensi perilaku list()
RFC: Pohon sintaksis abstrak
Sebelum PHP 7, ketika pembagi adalah 0 untuk operator pembagian (/) atau modulus (%), E_WARNING akan dikeluarkan dan false
akan dikembalikan. Ini tidak masuk akal untuk operasi aritmatika untuk mengembalikan boolean dalam beberapa kasus, sehingga perilaku tersebut telah diperbaiki di PHP 7.
Perilaku baru ini menyebabkan operator pembagi mengembalikan float sebagai +INF, -INF, atau NAN. Operator modulus E_WARNING telah dihapus dan (bersama dengan fungsi intdiv()
baru) akan memunculkan pengecualian DivisionByZeroError
. Selain itu, fungsi intdiv()
juga dapat memunculkan ArithmeticError
ketika argumen integer yang valid diberikan dan menyebabkan hasil yang salah (karena integer overflow).
var_dump(3/0); // mengapung(INF) + E_WARNINGvar_dump(0/0); // mengapung(NAN) + E_WARNINGvar_dump(0%0); // DivisionByZeroErrorintdiv(PHP_INT_MIN, -1); // Kesalahan Aritmatika
Istirahat SM
Operator pembagian tidak akan lagi mengembalikan false
(yang bisa saja dipaksa secara diam-diam ke 0 dalam operasi aritmatika)
Operator modulus sekarang akan memunculkan pengecualian dengan pembagi 0 alih-alih mengembalikan false
RFC: Tidak ada RFC yang tersedia
Saat mengimplementasikan penangan sesi khusus, fungsi predikat dari SessionHandlerInterface
yang mengharapkan nilai pengembalian true
atau false
tidak berperilaku seperti yang diharapkan. Karena kesalahan dalam implementasi sebelumnya, hanya nilai pengembalian -1
yang dianggap salah - artinya meskipun boolean false
digunakan untuk menunjukkan kegagalan, nilai tersebut dianggap sukses:
<?phpclass FileSessionHandler mengimplementasikan SessionHandlerInterface { pribadi $savePath; fungsi terbuka($savePath, $sessionName) { kembali salah; // selalu gagal } fungsi close(){return true;} fungsi baca($id){} fungsi tulis($id, $data){} fungsi penghancuran($id){} fungsi gc($maxlifetime){} }session_set_save_handler(FileSessionHandler());session_start(); // tidak menyebabkan kesalahan pada kode pra PHP 7
Sekarang, cara di atas akan gagal dengan kesalahan fatal. Memiliki nilai kembalian -1
juga akan terus gagal, sedangkan 0
dan true
akan terus berarti sukses. Nilai lain apa pun yang dikembalikan sekarang akan menyebabkan kegagalan dan mengeluarkan E_WARNING.
Istirahat SM
Jika boolean false
dikembalikan, sekarang akan gagal
Jika selain boolean, 0
, atau -1
dikembalikan, maka akan gagal dan menyebabkan peringatan dikeluarkan
RFC: Memperbaiki penanganan nilai pengembalian pengendali sesi khusus
Konstruktor PHP 4 dipertahankan di PHP 5 bersama dengan __construct()
yang baru. Sekarang, konstruktor gaya PHP 4 tidak lagi digunakan karena hanya memiliki satu metode ( __construct()
) untuk dipanggil pada pembuatan objek. Hal ini karena kondisi saat konstruktor gaya PHP 4 dipanggil menyebabkan beban kognitif tambahan bagi pengembang yang juga dapat membingungkan bagi yang tidak berpengalaman.
Misalnya, jika kelas didefinisikan dalam namespace atau jika ada metode __construct()
, maka konstruktor gaya PHP 4 diakui sebagai metode biasa. Jika didefinisikan di atas metode __construct()
, maka pemberitahuan E_STRICT akan dipancarkan, tetapi masih diakui sebagai metode biasa.
Sekarang di PHP 7, jika kelas tidak ada dalam namespace dan tidak ada metode __construct()
yang ada, konstruktor PHP 4-style akan digunakan sebagai konstruktor tetapi E_Deprecated akan dipancarkan. Dalam PHP 8, konstruktor PHP 4-style akan selalu diakui sebagai metode biasa dan pemberitahuan E_Deprecated akan hilang.
BC istirahat
Penangan kesalahan khusus dapat dipengaruhi oleh peningkatan peringatan E_Deprecated. Untuk memperbaikinya, cukup perbarui nama konstruktor kelas ke __construct
.
RFC: Hapus konstruktor PHP 4
Ketika fungsi berbasis tanggal atau waktu ada yang dipanggil dan zona waktu default belum ditetapkan, peringatan dipancarkan. Perbaikannya adalah hanya mengatur pengaturan date.timezone
. Karena ini adalah satu -satunya pengaturan yang memiliki peringatan yang melekat padanya, dan tetap default ke UTC, peringatan itu sekarang telah dihapus.
RFC: Hapus tanggal.
Tag PHP alternatif <%
(dan <%=
), %>
, <script language="php">
, dan </script>
sekarang telah dihapus.
BC istirahat
Kode yang mengandalkan tag alternatif ini perlu diperbarui ke tag pembukaan dan penutupan yang normal atau pendek. Ini dapat dilakukan secara manual atau otomatis dengan skrip porting ini.
RFC: Hapus tag PHP alternatif
Sebelumnya, dimungkinkan untuk menentukan beberapa pernyataan blok default
dalam pernyataan sakelar (di mana blok default
terakhir hanya dieksekusi). Kemampuan (tidak berguna) ini sekarang telah dihapus dan menyebabkan kesalahan fatal.
BC istirahat
Kode apa pun yang ditulis (atau lebih mungkin dihasilkan) yang membuat pernyataan sakelar dengan beberapa blok default
sekarang akan menjadi kesalahan fatal.
RFC: buat mendefinisikan beberapa kasus default dalam sakelar kesalahan sintaksis
Sebelumnya, dimungkinkan untuk menentukan parameter dengan nama duplikat dalam definisi fungsi. Kemampuan ini sekarang telah dihapus dan menyebabkan kesalahan fatal.
function foo ($ versi, $ versi) {return $ version; } echo foo (5, 7); // pra php 7 result7 // php 7+ kesalahan hasil fatal: redefinisi parameter $ versi di /redefinition-of-parameters.php
BC istirahat
Parameter fungsi dengan nama duplikat sekarang akan menjadi kesalahan fatal.
SAPI berikut telah dihapus dari inti (yang sebagian besar telah dipindahkan ke PECL):
SAPI/AOLSERVER
sapi/apache
sapi/apache_hooks
sapi/apache2filter
Sapi/Kaudium
sapi/kontinuitas
sapi/isapi
sapi/milter
SAPI/NSAPI
SAPI/PHTTPD
SAPI/PI3Web
sapi/roxen
SAPI/THTTPD
Sapi/Tux
sapi/webjames
ext/mssql
ext/mysql
ext/sybase_ct
ext/ereg
RFC: Penghapusan Mati atau Belum PHP7 Porting SAPIS dan Ekstensi
Angka heksadesimal berserat tidak lagi diakui sebagai numerik.
var_dump (is_numeric ('0x123')); var_dump ('0x123' == '291'); echo '0x123' + '0x123'; // pra php 7 hasil bool (true) (true) 582 // php 7+ HasilBool (false) bool (false) 0
Alasan perubahan ini adalah untuk mempromosikan konsistensi yang lebih baik antara penanganan angka hex string di seluruh bahasa. Misalnya, gips eksplisit tidak mengenali angka hex stringy:
var_dump ((int) '0x123'); // int (0)
Sebaliknya, nomor hex stringy harus divalidasi dan dikonversi menggunakan fungsi filter_var()
:
var_dump (filter_var ('0x123', filter_validate_int, filter_flag_allow_hex)); // int (291)
BC istirahat
Perubahan ini mempengaruhi fungsi is_numeric()
dan berbagai operator, termasuk ==
, +
, -
, *
, /
, %
, **
, ++
, dan --
RFC: Hapus dukungan hex di string numerik
Semua fungsionalitas yang sudah usang telah dihapus, terutama:
Ekstensi MySQL Asli (EXT/MYSQL)
Ekstensi EREG (EXT/EREG)
Menetapkan Referensi new
Panggilan tersingkir dari metode non-statis dari suatu konteks $this
yang tidak kompatibel (seperti Foo::bar()
dari luar kelas, di mana bar()
bukan metode statis)
BC istirahat
Kode apa pun yang dikeluarkan dengan peringatan penyusutan di Php 5 tidak akan lagi berfungsi (Anda diperingatkan!)
RFC: Hapus fungsionalitas yang sudah usang dalam php 7
Pemberitahuan E_STRICT selalu sedikit merupakan area abu -abu dalam artinya. Perubahan ini menghilangkan kategori kesalahan ini sama sekali dan baik: menghapus pemberitahuan e_strict, mengubahnya menjadi e_deprecated jika fungsionalitas akan dihapus di masa depan, mengubahnya menjadi e_notice, atau mempromosikannya menjadi peringatan E_.
BC istirahat
Karena E_STRICT berada dalam kategori kesalahan keparahan terendah, promosi kesalahan apa pun ke E_Warning dapat merusak penangan kesalahan khusus
RFC: reklasifikasi pemberitahuan e_strict
password_hash()
Dengan diperkenalkannya Kata Sandi Baru Hashing API di PHP 5.5, banyak yang mulai menerapkannya dan menghasilkan garam mereka sendiri. Sayangnya, banyak dari garam ini dihasilkan dari fungsi kriptografis yang tidak aman seperti mt_rand (), membuat garam jauh lebih lemah daripada yang dihasilkan secara default. (Ya, garam selalu digunakan saat hashing kata sandi dengan API baru ini!) Oleh karena itu menghasilkan garam telah digunakan untuk mencegah pengembang membuat garam yang tidak aman.
RFC: Tidak ada RFC yang tersedia
Literal oktal yang tidak valid sekarang akan menyebabkan kesalahan parse daripada dipotong dan diabaikan secara diam -diam.
Echo 0678; // Kesalahan Parse: numerik tidak valid di ...
BC istirahat
Literal oktal yang tidak valid dalam kode sekarang akan menyebabkan kesalahan parse
RFC: Tidak ada RFC yang tersedia
substr()
perubahan nilai pengembalian substr()
sekarang akan mengembalikan string kosong alih -alih false
ketika posisi awal pemotongan sama dengan panjang string:
var_dump (substr ('a', 1)); // pra php 7 resultBool (false) // php 7+ resultstring (0) ""
Namun, substr()
masih dapat mengembalikan false
dalam kasus lain.
BC istirahat
Kode yang secara ketat memeriksa nilai pengembalian bool(false)
sekarang mungkin tidak valid secara semantik
RFC: Tidak ada RFC yang tersedia
PHP 6 adalah versi PHP utama yang tidak pernah terungkap. Itu seharusnya menampilkan dukungan penuh untuk Unicode di inti, tetapi upaya ini terlalu ambisius dengan terlalu banyak komplikasi yang timbul. Alasan utama mengapa versi 6 dilewati untuk versi utama baru ini adalah sebagai berikut:
Untuk mencegah kebingungan . Banyak sumber daya ditulis tentang PHP 6 dan sebagian besar masyarakat tahu apa yang ditampilkan di dalamnya. PHP 7 adalah binatang yang sama sekali berbeda dengan fokus yang sama sekali berbeda (khususnya pada kinerja) dan set fitur yang sama sekali berbeda. Dengan demikian, sebuah versi telah dilewati untuk mencegah kebingungan atau kesalahpahaman seputar apa itu PHP 7.
Membiarkan anjing tidur berbohong . PHP 6 dipandang sebagai kegagalan dan sejumlah besar kode PHP 6 masih ada di repositori PHP. Oleh karena itu terlihat sebagai yang terbaik untuk bergerak melewati versi 6 dan memulai kembali pada versi utama berikutnya, versi
RFC: Nama rilis PHP berikutnya