Sudah lama dahulu, kami menggunakan React dengan kelas, ingat?
Pada masa itu, kami mempunyai konsep kaedah kitaran hayat, kaedah pada kelas yang menerima panggilan balik yang akan dilaksanakan pada saat tertentu. Tiga besar: pada lekap, pada kemas kini dan pada nyahlekap.
Itu penting, pada komponen kelas, JSX yang dikembalikan dibuat pada kaedah pemaparan, keadaan yang dilampirkan pada komponen ini dan pembangun apl memerlukan cara untuk mengetahui melakukan tindakan pada saat tertentu. Kami mempunyai idea tentang masa pada hayat komponen:
Dan sudah tentu, anda mempunyai API penting seperti forceUpdate, yang membolehkan anda mencetuskan pemarahan semula secara manual jika anda menggunakan data luaran yang tidak akan berhubung dengan kemas kini keadaan React.
Pada peringkat konsep, kami mempunyai cara yang lebih langsung untuk menjalankan aliran apl. Kaedah kitar hayat mengikuti kitaran hayat yang serupa bagi elemen DOM, anda boleh melakukan memo dan forceUpdates sendiri, keadaan penyegerakan ialah cara lalai untuk melakukan logik.
Keterusterangan ini dilihat sebagai kesederhanaan, dan untuk mempelajari konsep ini adalah lebih mudah berbanding dengan model reaktif. Tetapi kemudian, cangkuk tiba dan mengubah segala-galanya.
Peralihan itu mengelirukan. Pertama, dalam pencarian untuk memudahkan, dan semacam, mengekalkan visi konsep model React yang dimiliki oleh pembangun, banyak komunikasi cuba menunjukkan persamaan pada model cangkuk. Untuk mempunyai 3 kaedah kitaran hayat utama, mereka menunjukkan penyelesaian dengan useEffect.
// componentDidMount useEffect(() => { // code... // componentWillUnmount: return function cleanup() { // code... }; }, []); // componentDidUpdate useEffect(() => { // code... }, [dependencyState, dependencyProp]);
Jadi, kebanyakan kod React baharu yang dibuat dengan cangkuk mengikuti idea ini dan mula menyegerakkan keadaan adalah proses semula jadi. Untuk mengekalkan idea kaedah kitaran hayat yang sama, ia adalah tempat untuk memanggil setState dan mencetuskan proses pemaparan semula.
Apakah masalahnya?
Keadaan penyegerakan menjadi masalah, penggunaan useEffect yang salah menjadi masalah, pemaparan semula berganda menjadi masalah, pemaparan semula terlalu banyak menjadi masalah, prestasi menjadi masalah.
Agak mengelirukan langkah ini daripada React, sekurang-kurangnya untuk saya. Kerana, perpindahan ke cangkuk adalah perpindahan kepada model reaktif, walaupun model itu berbutir kasar. Tetapi komunikasi adalah bahawa tiada apa yang benar-benar berubah. Tiada kandungan tentang konsep dan teori kereaktifan, malah bekerja selama bertahun-tahun dengan React, saya baru mula benar-benar memahami kereaktifan membaca catatan blog Ryan Carniato tentang kereaktifan dan pepejal.
Walaupun mengetahui bahawa useEffect mempunyai penyalahgunaan, saya benar-benar tidak faham mengapa, dan kekurangan teori konseptual tentang kereaktifan ini menjadikan melakukan kesilapan dengan cangkuk begitu mudah. useEffect menjadi cangkuk yang paling dibenci, dipanggil “useFootgun” bagi sesetengah orang. Intinya ialah, terdapat kekeliruan konsep dalam React yang menyatakan dirinya sebagai semua isu dengan useEffect yang kita lihat hari ini.
Isu useEffect bukanlah punca masalah, tetapi akibatnya.
Jadi, inilah perkaranya. Tiada kitaran hayat dalam konsep kereaktifan.
Anda mempunyai perubahan, anda bertindak balas terhadapnya menghasilkan dan melakukan kesan sampingan. Kesan adalah akibat, bukan sebab. Tiada penyegerakan keadaan dan tiada konsep lekap dan nyahlekap.
Tidak kira sama ada ia yang pertama, yang ke-10 atau yang terakhir sebelum menyahlekap, dan cangkuk tidak mengambil kiranya, malah useEffect.
Cubalah:
// componentDidMount useEffect(() => { // code... // componentWillUnmount: return function cleanup() { // code... }; }, []); // componentDidUpdate useEffect(() => { // code... }, [dependencyState, dependencyProp]);
Anda akan melihat pada konsol anda kedua-dua fungsi dilaksanakan pada setiap kemas kini keadaan. Mula-mula pembersihan, dan kemudian kesan panggilan balik. Jika anda menggunakan useEffect dengan beberapa keadaan atau prop untuk melakukan langganan, setiap kali kebergantungan berubah, fungsi pembersihan akan dipanggil, dan kemudian panggil balik baharu, melakukan langganan semula, tetapi dengan nilai baharu.
Anda harus melihat kod apl anda sebagai model React yang dipermudahkan:
function EffectExample() { const [count, setCount] = useState(0); useEffect(() => { console.log('effect', count); return () => { console.log('clean up', count); } }, [count]); return ( <button onClick={() => setCount((state) => state + 1)}> {count} </button> ) }
Jika anda mempunyai komponen seperti ini:
UI = fn(state)
apa yang anda ada, apabila anda mengklik butang dan menambah 1 pada kiraan, secara konseptual, adalah seperti ini:
function Example() { const [count, setCount] = useState(0); return ( <button onClick={() => setCount((state) => state + 1)}> {count} </button> ) }
Setiap klik memanggil sekali lagi fn, dengan keadaan baharu, menjana versi UI baharu. Keadaan harus berubah mengikut tindakan pengguna atau oleh nilai asinkron yang harus dibuat dengan terbitan tak segerak.
Dengan cara ini anda mengekalkan idea yang bersih:
penyampai perlu mengambil berat dengan menambah, mengemas kini dan mengalih keluar elemen daripada skrin. Di peringkat komponen, apa yang penting ialah:
Hooks dan model reaktifnya menjadikan React memisahkan diri daripada penyemak imbas, menjadikan kod apl kurang mengambil berat tentang masa proses pemaparan skrin anda. Anda tidak lagi memaksa kemas kini malah mengendalikan memo mengikut peraturan anda sendiri, ia kurang tepat untuk pembangun apl, tetapi lebih langsung dari segi model.
Setiap paparan semula menjana struktur, React mengurus yang lain.
Atas ialah kandungan terperinci Kitaran hayat tidak wujud dalam React with hooks. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!