【精講】2022年PHP中高級(jí)面試題(二)
1.Iptolong long2ip 注意轉(zhuǎn)換成整形的時(shí)候負(fù)數(shù)問題
function?IP2Long($ip)?{
$ips?=?explode('.',?$ip);
if(count($ips)?!=?4)?{
return?false;
}
return?($ips[0]?<24)?+?($ips[1]?<16)?+?($ips[2]?<8)?+?$ips[3];
}
function?Long2IP($int)?{
$ip1?=?$ipint?>>?24;
$ip2?=?($ipint?>>?16)?&?255;
$ip3?=?($ipint?>>?8)?&?255;
$ip4?=?$ipint?&?255;
return?$ip1.'.'.$ip2.'.'.$ip3.'.'.$ip4;
}
2.php鏈?zhǔn)秸{(diào)用:
1 使用魔法函數(shù)__call結(jié)合call_user_func來實(shí)現(xiàn)
2 使用魔法函數(shù)__call結(jié)合call_user_func_array來實(shí)現(xiàn)
3 不使用魔法函數(shù)__call來實(shí)現(xiàn),修改 __call() 為 trim重點(diǎn)在于,返回$this指針,方便調(diào)用后者函數(shù)。
3.?不使用第三個(gè)變量來交換兩個(gè)變量的值
兩個(gè)為 數(shù)字時(shí)
/**
*雙方變量為數(shù)字時(shí),可用交換方法,使用加減運(yùn)算符,相當(dāng)于數(shù)學(xué)運(yùn)算了
*/
$a?=?1;?//a變量原始值
$b?=?2;??//b變量原始值
echo?'交換之前?$a?的值:'?.?$a?.?',?$b?的值:'?.?$b,?'
';?//?輸出原始值
$a?=?$a?+?$b;?//?$a?$b和值
$b?=?$a?-?$b;?//?不解釋..
$a?=?$a?-?$b;?//?不解釋..
echo?'交換之后?$a?的值:'?.?$a?.?',?$b?的值:'?.?$b,?'
';?//?輸出結(jié)果值
兩個(gè)為字符串時(shí)
/**
*?雙方變量為字符串或者數(shù)字時(shí),可用交換方法四
*?使用異或運(yùn)算
*/
$a?=?"This?is?A";?//?a變量原始值
$b?=?"This?is?B";?//?b變量原始值
echo?'交換之前?$a?的值:'?.?$a?.?',?$b?的值:'?.?$b,?'
';?//?輸出原始值
/**
*?原始二進(jìn)制:
*?$a:010101000110100001101001011100110010000001101001011100110010000001?000001
*?$b:010101000110100001101001011100110010000001101001011100110010000001?000010
*?下面主要使用按位異或交換,具體請(qǐng)參照下列給出的二進(jìn)制過程,
*/
$a?=?$a?^?$b;?//?此刻?$a:000000000000000000000000000000000000000000000000000000000000000000?000011
$b?=?$b?^?$a;?//?此刻?$b:010101000110100001101001011100110010000001101001011100110010000001?000001
$a?=?$a?^?$b;?//?此刻?$a:010101000110100001101001011100110010000001101001011100110010000001?000010
echo?'交換之后?$a?的值:'?.?$a?.?',?$b?的值:'?.?$b,?'
';?//?輸出結(jié)果值
或者 str_replace 處理
$a?=?"This?is?A";?//?a變量原始值
$b?=?"This?is?B";?//?b變量原始值
echo?'交換之前?$a?的值:'?.?$a?.?',?$b?的值:'?.?$b,?'
';?//?輸出原始值
$a?.=?$b;?//?將$b的值追加到$a中
$b?=?str_replace($b,?"",?$a);?//?在$a(原始$a+$b)中,將$b替換為空,則余下的返回值為$a
$a?=?str_replace($b,?"",?$a);?//?此時(shí),$b為原始$a值,則在$a(原始$a+b)中將$b(原始$a)替換為空,則余下的返回值則為原始$b,交換成功
echo?'交換之后?$a?的值:'?.?$a?.?',?$b?的值:'?.?$b,?'
';?//?輸出結(jié)果值
4.Strtoupper/strtolower 遇到中文會(huì)亂碼
需要手動(dòng)分割字符串,然后 ord 函數(shù)判斷是否是單詞,是則大小寫轉(zhuǎn)換,中文則不處 理
mb_convert_case 函數(shù)中有可選參數(shù),直接能處理這種情況
5.Php-fpm 和 NGINX 通信機(jī)制
CGI:是 Web Server 與 Web Application 之間數(shù)據(jù)交換的一種協(xié)議。
FastCGI:同 CGI,是一種通信協(xié)議,但比 CGI 在效率上做了一些優(yōu)化。
PHP-CGI:是 PHP (Web Application)對(duì) Web Server 提供的 CGI 協(xié)議的接口程 序。
PHP-FPM:是 PHP(Web Application)對(duì) Web Server 提供的 FastCGI 協(xié)議的接口 程序,額外還提供了相對(duì)智能一些任務(wù)管理。
CGI就是規(guī)定要傳哪些數(shù)據(jù),以什么樣的格式傳遞給后方處理這個(gè)請(qǐng)求的協(xié)議,例如 URL、查詢字符串、POST數(shù)據(jù)、HTTP header,缺點(diǎn)是每次請(qǐng)求都有啟動(dòng)和退出操 作,不適合并發(fā)場景
Fastcgi 是常駐類型的,不需要每次去激活了
FastCGI程序會(huì) 先啟動(dòng)一個(gè)master,解析配置環(huán)境,初始化執(zhí)行環(huán)境,然后再啟動(dòng)多個(gè)worker。當(dāng)請(qǐng)求過來時(shí),master會(huì)傳遞給一個(gè)worker,然后立即可以接受下一個(gè)請(qǐng) 求。
首先要說的是:fastcgi是一個(gè)協(xié)議,php-fpm實(shí)現(xiàn)了這個(gè)協(xié)議。
大家都知道,PHP的解釋器是php-cgi。php-cgi只是個(gè)CGI程序,他自己本身只能解析 請(qǐng)求,返回結(jié)果,不會(huì)進(jìn)程管理,所以就出現(xiàn)了一些能夠調(diào)度php-cgi進(jìn)程的程序,php-fpm就是這樣的一個(gè)東西。它克服了php-cgi變更php.ini配置后,需重啟php-cgi才能讓新的php-ini生效,不可以平滑重啟,直接殺死php-cgi進(jìn)程,php就不能運(yùn)行了 的問題。修改php.ini之后,php-cgi進(jìn)程的確沒辦法平滑重啟的。php-fpm對(duì)此的處理 機(jī)制是新的worker用新的配置,已經(jīng)存在的worker處理完手上的活就可以歇著了,通 過這種機(jī)制來平滑過度。
6.Explain 后需要關(guān)注的信息
列名
備注
type
本次查詢表聯(lián)接類型,從這里可以看到本次查詢大概的效率
key
最終選擇的索引,如果沒有索引的話,本次查詢效率通常很差
key_le n
本次查詢用于結(jié)果過濾的索引實(shí)際長度,參見另一篇分享(FAQ系列-解讀EXPLAIN執(zhí)行計(jì)劃中的key_len)
rows
預(yù)計(jì)需要掃描的記錄數(shù),預(yù)計(jì)需要掃描的記錄數(shù)越小越好
Extra
額外附加信息,主要確認(rèn)是否出現(xiàn) Using filesort、Using temporary 這 兩種情況
首先看下 type 有幾種結(jié)果,分別表示什么意思:
類型
備注
ALL
執(zhí)行full table scan,這是最差的一種方式
index
執(zhí)行full index scan,并且可以通過索引完成結(jié)果掃描并且直接從索引中 取的想要的結(jié)果數(shù)據(jù),也就是可以避免回表,比ALL略好,因?yàn)樗饕募?常比全部數(shù)據(jù)要來的小
range
利用索引進(jìn)行范圍查詢,比index略好
index_sub query
子查詢中可以用到索引
unique_su bquery
子查詢中可以用到唯一索引,效率比 index_subquery 更高些
index_mer ge
可以利用index merge特性用到多個(gè)索引,提高查詢效率
ref_or_null
表連接類型是ref,但進(jìn)行掃描的索引列中可能包含NULL值
fulltext
全文檢索
ref
基于索引的等值查詢,或者表間等值連接
eq_ref
表連接時(shí)基于主鍵或非NULL的唯一索引完成掃描,比ref略好
const
基于主鍵或唯一索引唯一值查詢,最多返回一條結(jié)果,比eq_ref略好
system
查詢對(duì)象表只有一行數(shù)據(jù),這是最好的情況
上面幾種情況,從上到下一次是最差到最好。再來看下Extra列中需要注意出現(xiàn)的幾種情況:
關(guān)鍵字
備注
Using filesort
將用外部排序而不是按照索引順序排列結(jié)果,數(shù)據(jù)較少時(shí)從內(nèi)存排序, 否則需要在磁盤完成排序,代價(jià)非常高,需要添加合適的索引
Using temporary
需要?jiǎng)?chuàng)建一個(gè)臨時(shí)表來存儲(chǔ)結(jié)果,這通常發(fā)生在對(duì)沒有索引的列進(jìn)行GROUP BY時(shí),或者ORDER BY里的列不都在索引里,需要添加合適 的索引
Using index
表示MySQL使用覆蓋索引避免全表掃描,不需要再到表中進(jìn)行二次查 找數(shù)據(jù),這是比較好的結(jié)果之一。注意不要和type中的index類型混淆
Using where
通常是進(jìn)行了全表引掃描后再用WHERE子句完成結(jié)果過濾,需要添加 合適的索引
Impossible WHERE
對(duì)Where子句判斷的結(jié)果總是false而不能選擇任何數(shù)據(jù),例如where 1=0,無需過多關(guān)注
Select tables optimized away
使用某些聚合函數(shù)來訪問存在索引的某個(gè)字段時(shí),優(yōu)化器會(huì)通過索引直 接一次定位到所需要的數(shù)據(jù)行完成整個(gè)查詢,例如MIN()\MAX(),這 種也是比較好的結(jié)果之一
7.Php-fpm 運(yùn)行的三種模式:
Static模式最簡單,直接啟動(dòng)配置的固定數(shù)量的進(jìn)程,但是靈活性不夠高
ondemand?模式相對(duì) static 模式比較復(fù)雜,會(huì)根據(jù)請(qǐng)求量的增加動(dòng)態(tài)增加,但是處理完請(qǐng)求后不會(huì)立即釋放,而是由定時(shí)事件定時(shí)的檢測(cè)空閑到一定時(shí)間的進(jìn)程才會(huì)釋放
Dynamic 模式類似于 ondemand 模式,但進(jìn)程的回收機(jī)制不同于 ondemand 模式, 會(huì)根據(jù) idle 數(shù)量進(jìn)行增加和減少worker數(shù)量
8.Php-fpm 運(yùn)行的邏輯:
Fpm 的實(shí)現(xiàn)就是創(chuàng)建一個(gè) master 進(jìn)程,在 master 進(jìn)程中創(chuàng)建 worker pool 并監(jiān)聽 socket,然后 fork出多個(gè)子進(jìn)程(work),這些 worker 在啟動(dòng)后阻塞在 fcgi_accept_request() 上,各自 accept 請(qǐng)求,有請(qǐng)求到達(dá)后 worker 開始讀取請(qǐng)求數(shù) 據(jù),讀取完成后開始處理然后再返回,在這期間是不會(huì)接收其它請(qǐng)求的,也就是說 fpm 的子進(jìn)程同時(shí)只能響應(yīng)一個(gè)請(qǐng)求,只有把這個(gè)請(qǐng)求處理完成后才會(huì) accept 下一個(gè)請(qǐng) 求,所以有多少子進(jìn)程就能同時(shí)處理多少請(qǐng)求。
10.Fpm 工作流程:
FastCGI 進(jìn)程管理器自身初始化,啟動(dòng)多個(gè) CGI 解釋器進(jìn)程,并等待來自 Web Server 的連接。
Web 服務(wù)器與 FastCGI 進(jìn)程管理器進(jìn)行 Socket 通信,通過 FastCGI 協(xié)議發(fā) 送 CGI 環(huán)境變量和標(biāo)準(zhǔn)輸入數(shù)據(jù)給 CGI 解釋器進(jìn)程。
CGI 解釋器進(jìn)程完成處理后將標(biāo)準(zhǔn)輸出和錯(cuò)誤信息從同一連接返回 Web Server。
CGI 解釋器進(jìn)程接著等待并處理來自 Web Server 的下一個(gè)連接。
11.Nginx 與 php-fpm 有兩種通信方式:
tcp socket和 unix socket,unix 不需要經(jīng)過 網(wǎng)絡(luò)協(xié)議棧,不需要打包拆包,計(jì)算校驗(yàn)和,維護(hù)序號(hào)和應(yīng)答,只是將應(yīng)用層數(shù)據(jù)從一 個(gè)進(jìn)程拷貝到另一個(gè)進(jìn)程,減少不必要的 tcp 開銷,高并發(fā)時(shí)性能不穩(wěn)定,tcp 模式可 以保證通信的正確性和完整性,效率可以通過負(fù)載均衡等優(yōu)化。
一段PHP代碼會(huì)經(jīng)過詞法解析、語法解析等階段,會(huì)被翻譯成一個(gè)個(gè)指令 (opcode),然后 zend 虛擬機(jī)會(huì)順序執(zhí)行這些指令。PHP 本身是用C語言實(shí)現(xiàn)的,因 此最終調(diào)用的也是C語言的函數(shù),實(shí)際上我們可以把 PHP 看做一個(gè)C語言開發(fā)的軟 件。Opcode 是php執(zhí)行的最基本單位
12.數(shù)據(jù)庫連接池實(shí)現(xiàn)原理
連接池的作用就是為了提高性能,將已經(jīng)創(chuàng)建好的連接保存在池中,當(dāng)有請(qǐng)求來時(shí),直 接使用已經(jīng)創(chuàng)建好的連接對(duì) Server 端進(jìn)行訪問。這樣 省略了創(chuàng)建連接和銷毀連接的過 程,從而提高性能。
13.Redis 常見應(yīng)用場景
首頁熱點(diǎn)新聞/商品,避免頻繁讀取數(shù)據(jù)庫 bitmap 用來記錄連續(xù)簽到/登錄情況 新 聞閱讀量的計(jì)數(shù)器
最新新聞列表 lpush 就行,然后讀取 簡單的消息發(fā)布系統(tǒng) pubsub sortedset 來做 排行榜
14.負(fù)載均衡的幾種實(shí)現(xiàn)方式及原理
1 ip負(fù)載均衡,相當(dāng)于多一到N次重定向,過程
2 DNS 負(fù)載均衡,DNS支持一個(gè)域名多個(gè)ip地址了
3 反向代理負(fù)載均衡,NGINX 根據(jù)一定規(guī)則進(jìn)行請(qǐng)求分發(fā)
4 F5硬件級(jí)別
6 CDN 對(duì)于靜態(tài)文件的負(fù)載均衡 負(fù)載均衡構(gòu)建在原有網(wǎng)絡(luò)結(jié)構(gòu)之上,它提供了一種透明且廉價(jià)有效的方法擴(kuò)展服務(wù)器和 網(wǎng)絡(luò)設(shè)備的帶寬、加強(qiáng)網(wǎng)絡(luò)數(shù)據(jù)處理能力、增加吞吐量、提高網(wǎng)絡(luò)的可用性和靈活性。
15.數(shù)據(jù)庫主從復(fù)制的原理,會(huì)不會(huì)延遲,會(huì)該怎樣解決
三個(gè)要點(diǎn):網(wǎng)絡(luò)延遲,master 負(fù)載 slave 負(fù)載 slave 對(duì)數(shù)據(jù)安全性的要求
原理
master 將數(shù)據(jù)改變記錄到 binlog 中
slave 啟動(dòng)一個(gè)io線程,從指定位置開 始同步 binlog
讀取到 master 數(shù)據(jù)的更新,slave 寫入到 replaylog 中,然后開始重 放數(shù)據(jù)
Tps 是事務(wù)數(shù)/秒 qps 是每秒查詢率
延遲原因:主庫的 tps 并發(fā)較高時(shí),產(chǎn)生的 ddl 超過 slave 的執(zhí)行,或者網(wǎng)絡(luò)延遲較 大,也有可能是從庫性能很差
解決:減少網(wǎng)絡(luò)延遲,關(guān)閉 slave 的 sync_binlog 設(shè)置成大點(diǎn)就行,累計(jì)多次事務(wù)之后 刷盤 innodb_flush_log_at_trx_commit = 2 事務(wù)提交之后刷盤,slave 上也可以關(guān)閉 這個(gè),缺點(diǎn)是意外斷電了會(huì)丟失數(shù)據(jù)
16.如何保障數(shù)據(jù)的可用性,即使被刪庫了也能恢復(fù)到分鐘級(jí)別。你會(huì)怎么做。
數(shù)據(jù)庫集群方案就行,刪掉主庫了會(huì)自動(dòng)選舉從庫,業(yè)務(wù)保持穩(wěn)定,然后就是精細(xì)化的 備份
2021年最新大廠php+go面試題集(四)
2021年最新大廠php+go面試題集(三)
2021年最新大廠php+go面試題集(二)
2021年最新大廠php+go面試題集(1)
PHP 任務(wù)調(diào)度
版權(quán)聲明:本文內(nèi)容由網(wǎng)絡(luò)用戶投稿,版權(quán)歸原作者所有,本站不擁有其著作權(quán),亦不承擔(dān)相應(yīng)法律責(zé)任。如果您發(fā)現(xiàn)本站中有涉嫌抄襲或描述失實(shí)的內(nèi)容,請(qǐng)聯(lián)系我們jiasou666@gmail.com 處理,核實(shí)后本網(wǎng)站將在24小時(shí)內(nèi)刪除侵權(quán)內(nèi)容。
版權(quán)聲明:本文內(nèi)容由網(wǎng)絡(luò)用戶投稿,版權(quán)歸原作者所有,本站不擁有其著作權(quán),亦不承擔(dān)相應(yīng)法律責(zé)任。如果您發(fā)現(xiàn)本站中有涉嫌抄襲或描述失實(shí)的內(nèi)容,請(qǐng)聯(lián)系我們jiasou666@gmail.com 處理,核實(shí)后本網(wǎng)站將在24小時(shí)內(nèi)刪除侵權(quán)內(nèi)容。