42、PHP緩存技術有哪些?1)、全頁面靜態(tài)化緩存2)、頁面部分緩存3)、數(shù)據(jù)緩存4)、查詢緩存5)、按內容變更進行緩存6)、內存式緩存7)、apache緩存模塊8)、php APC緩存擴展9)、Opcode緩存43、PHP7的新特性有哪些?1),PHP 標量類型與返回值類型聲明2),PHP NULL 合并運算符3),PHP 太空船運算符(組合比較符)4),PHP 常量數(shù)組5),PHP 匿名類6),PHP Closure::call()7),PHP 過濾 unserialize()8),PHP IntlChar()9),PHP CSPRNG10),PHP 7 異常11),PHP 7 use 語句12),PHP 7 錯誤處理13),PHP intdiv() 函數(shù)14),PHP 7 Session 選項15),PHP 7 廢棄特性16),PHP 7 移除的擴展17),PHP 7 移除的 SAPI18),0成本斷言44、如何實現(xiàn)商品的無限分類?遞歸函數(shù)的編寫。45、什么是匿名函數(shù)?匿名函數(shù)也叫什么函數(shù)?通常在什么情況下使用?php中的匿名函數(shù)(Anonymous functions), 也叫閉包函數(shù)(closures), 允許指定一個沒有名稱的函數(shù)。最常用的就是回調函數(shù)的參數(shù)值。46、PHP 命名空間是為了解決什么問題? 在PHP中,命名空間用來解決在編寫類庫或應用程序時創(chuàng)建可重用的代碼如類或函數(shù)時碰到的兩類問題: 用戶編寫的代碼與PHP內部的類/函數(shù)/常量或第三方類/函數(shù)/常量之間的名字沖突。 為很長的標識符名稱(通常是為了緩解第一類問題而定義的)創(chuàng)建一個別名(或簡短)的名稱,提高源代碼的可讀性。47、說出幾個PHP常用加密碼方法?md5,sha1,base64_encode,rsa48、請寫一段PHP代碼,確保多個進程同時寫入同一個文件成功function writeData($filepath, $data) { $fp = fopen($filepath,'a'); do{ usleep(100); }while (!flock($fp, LOCK_EX)); //LOCK_EX 取得獨占鎖定(寫入的程序)進行排它型鎖定 獲取鎖 有鎖就寫入,沒鎖就得 $res = fwrite($fp, $data."\n"); flock($fp, LOCK_UN); //LOCK_UN 釋放鎖定(無論共享或獨占)。 fclose($fp); return $res; } 方案二可以借助Redis setnx49、使用兩種方法獲取一個文件的擴展名。pathinfoparse_url50、寫一個函數(shù),能夠遍歷一個文件夾下的所有文件和子文件夾。function my_scandir($dir) { $files = array(); if ( $handle = opendir($dir) ) { while ( ($file = readdir($handle)) !== false ) { if ( $file != ".." && $file != "." ) { if ( is_dir($dir . "/" . $file) ) { $files[$file] = scandir($dir . "/" . $file); }else { $files[] = $file; } } } closedir($handle); return $files; } }51、寫出一個能創(chuàng)建多級目錄的PHP函數(shù) function createDir($path,$mode) { , if (is_dir($path)) echo "路徑已經(jīng)存在"! else { $re = mkdir($path,$mode,true); if ($re) echo "目錄創(chuàng)建成功"; else echo "目錄創(chuàng)建失敗"; }}$path = /a/b/c/d; $mode = 0777;createDir($path,$mode);52、寫出一個正則表達式,過慮網(wǎng)頁上的所有JS/VBS腳本(即把script標記及其內容都去掉)
$script=” 以下內容不顯示:alert(‘cc’);”;
echo preg_replace(“/].*?>.*?<\/script>/si”, “替換內容”, $script);七、mysql 部分1、優(yōu)化mysql數(shù)據(jù)庫的方法(至少5種)。1). 為查詢緩存優(yōu)化你的查詢2). EXPLAIN 你的 SELECT 查詢3). 當只要一行數(shù)據(jù)時使用 LIMIT 14). 為搜索字段建索引5). 在Join表的時候使用相當類型的例,并將其索引6). 千萬不要 ORDER BY RAND()7). 避免 SELECT *8). 永遠為每張表設置一個ID9). 使用 ENUM 而不是 VARCHAR10). 從 PROCEDURE ANALYSE() 取得建議11). 盡可能的使用 NOT NULL12). Prepared Statements13). 無緩沖的查詢14). 把IP地址存成 UNSIGNED INT15). 固定長度的表會更快16). 垂直分割17). 拆分大的 DELETE 或 INSERT 語句18). 越小的列會越快19). 選擇正確的存儲引擎20). 使用一個對象關系映射器(Object Relational Mapper)21). 小心“永久鏈接”2、簡單描述mysql中,索引,主鍵,唯一索引,聯(lián)合索引的區(qū)別,對數(shù)據(jù)庫的性能有什么影響(從讀寫兩方面)。索引是一種特殊的文件(InnoDB數(shù)據(jù)表上的索引是表空間的一個組成部分),它們包含著對數(shù)據(jù)表里所有記錄的引用指針。普通索引(由關鍵字KEY或INDEX定義的索引)的唯一任務是加快對數(shù)據(jù)的訪問速度。普通索引允許被索引的數(shù)據(jù)列包含重復的值。如果能確定某個數(shù)據(jù)列將只包含彼此各不相同的值,在為這個數(shù)據(jù)列創(chuàng)建索引的時候就應該用關鍵字UNIQUE把它定義為一個唯一索引。也就是說,唯一索引可以保證數(shù)據(jù)記錄的唯一性。主鍵,是一種特殊的唯一索引,在一張表中只能定義一個主鍵索引,主鍵用于唯一標識一條記錄,使用關鍵字 PRIMARY KEY 來創(chuàng)建。索引可以覆蓋多個數(shù)據(jù)列,如像INDEX(columnA, columnB)索引,這就是聯(lián)合索引。索引可以極大的提高數(shù)據(jù)的查詢速度,但是會降低插入、刪除、更新表的速度,因為在執(zhí)行這些寫操作時,還要操作索引文件。3、數(shù)據(jù)庫中的事務是什么?事務(transaction)是作為一個單元的一組有序的數(shù)據(jù)庫操作。如果組中的所有操作都成功,則認為事務成功,即使只有一個操作失敗,事務也不成功。如果所有操作完成,事務則提交,其修改將作用于所有其他數(shù)據(jù)庫進程。如果一個操作失敗,則事務將回滾,該事務所有操作的影響都將取消。ACID 四大特性,原子性、隔離性、一致性、持久性。4、對于關系型數(shù)據(jù)庫而言,索引是相當重要的概念,請回答有關索引的幾個問題:a)、索引的目的是什么?? 1. 快速訪問數(shù)據(jù)表中的特定信息,提高檢索速度? 2. 創(chuàng)建唯一性索引,保證數(shù)據(jù)庫表中每一行數(shù)據(jù)的唯一性。? 3. 加速表和表之間的連接? 4. 使用分組和排序子句進行數(shù)據(jù)檢索時,可以顯著減少查詢中分組和排序的時間b)、索引對數(shù)據(jù)庫系統(tǒng)的負面影響是什么?創(chuàng)建索引和維護索引需要耗費時間,這個時間隨著數(shù)據(jù)量的增加而增加;索引需要占用物理空間,不光是表需要占用數(shù)據(jù)空間,每個索引也需要占用物理空間;當對表進行增、刪、改、的時候索引也要動態(tài)維護,這樣就降低了數(shù)據(jù)的維護速度。c)、為數(shù)據(jù)表建立索引的原則有哪些?? 1. 在最頻繁使用的、用以縮小查詢范圍的字段上建立索引。? 2. 在頻繁使用的、需要排序的字段上建立索引d)、什么情況下不宜建立索引?? 1. 對于查詢中很少涉及的列或者重復值比較多的列,不宜建立索引。? 2. 對于一些特殊的數(shù)據(jù)類型,不宜建立索引,比如文本字段(text)等。5、簡述在MySQL數(shù)據(jù)庫中MyISAM和InnoDB的區(qū)別。區(qū)別于其他數(shù)據(jù)庫的最重要的特點就是其插件式的表存儲引擎。切記:存儲引擎是基于表的,而不是數(shù)據(jù)庫。InnoDB與MyISAM的區(qū)別:InnoDB存儲引擎: 主要面向OLTP(Online Transaction Processing,在線事務處理)方面的應用,是第一個完整支持ACID事務的存儲引擎(BDB第一個支持事務的存儲引擎,已經(jīng)停止開發(fā))。特點:? ● 行鎖設計、支持外鍵;? ● 支持類似于Oracle風格的一致性非鎖定讀(即:默認情況下讀取操作不會產(chǎn)生鎖);? ● InnoDB將數(shù)據(jù)放在一個邏輯的表空間中,由InnoDB自身進行管理。從MySQL4.1版本開始,可以將每個InnoDB存儲引擎的表單獨存放到一個獨立的ibd文件中;? ● InnoDB通過使用MVCC(多版本并發(fā)控制:讀不會阻塞寫,寫也不會阻塞讀)來獲得高并發(fā)性,并且實現(xiàn)了SQL標準的4種隔離級別(默認為REPEATABLE級別);? ● InnoDB還提供了插入緩沖(insert buffer)、二次寫(double write)、自適應哈希索引(adaptive hash index)、預讀(read ahead)等高性能和高可用的功能;? ● InnoDB采用了聚集(clustered)的方式來存儲表中的數(shù)據(jù),每張標的存儲都按主鍵的順序存放(如果沒有顯式的在建表時指定主鍵,InnoDB會為每一行生成一個6字節(jié)的ROWID,并以此作為主鍵);? ● InnoDB表會有三個隱藏字段:除了上面提到了6字節(jié)的DB_ROW_ID外,還有6字節(jié)的DB_TX_ID(事務ID)和7字節(jié)的DB_ROLL_PTR(指向對應回滾段的地址)。這個可以通過innodb monitor看到;MyISAM存儲引擎: 是MySQL官方提供的存儲引擎,主要面向OLAP(Online Analytical Processing,在線分析處理)方面的應用。特點:? ● 不支持事務,支持表所和全文索引。操作速度快;? ● MyISAM存儲引擎表由MYD和MYI組成,MYD用來存放數(shù)據(jù)文件,MYI用來存放索引文件。MySQL數(shù)據(jù)庫只緩存其索引文件,數(shù)據(jù)文件的緩存交給操作系統(tǒng)本身來完成;MySQL5.0版本開始,MyISAM默認支持256T的單表數(shù)據(jù);6、解釋MySQL外連接、內連接與自連接的區(qū)別。先說什么是交叉連接: 交叉連接又叫笛卡爾積,它是指不使用任何條件,直接將一個表的所有記錄和另一個表中的所有記錄一一匹配。內連接 則是只有條件的交叉連接,根據(jù)某個條件篩選出符合條件的記錄,不符合條件的記錄不會出現(xiàn)在結果集中,即內連接只連接匹配的行。外連接 其結果集中不僅包含符合連接條件的行,而且還會包括左表、右表或兩個表中的所有數(shù)據(jù)行,這三種情況依次稱之為左外連接,右外連接,和全外連接。左外連接,也稱左連接,左表為主表,左表中的所有記錄都會出現(xiàn)在結果集中,對于那些在右表中并沒有匹配的記錄,仍然要顯示,右邊對應的那些字段值以NULL來填充。右外連接,也稱右連接,右表為主表,右表中的所有記錄都會出現(xiàn)在結果集中。左連接和右連接可以互換,MySQL目前還不支持全外連接。7、寫出三種以上MySQL數(shù)據(jù)庫存儲引擎的名稱。MyISAM、InnoDB、BDB(BerkeleyDB)、Merge、Memory(Heap)、Example、Federated、Archive、CSV、Blackhole、MaxDB 等等十幾個引擎8、Myql中的事務回滾機制概述。事務是用戶定義的一個數(shù)據(jù)庫操作序列,這些操作要么全做要么全不做,是一個不可分割的工作單位,事務回滾是指將該事務已經(jīng)完成的對數(shù)據(jù)庫的更新操作撤銷。要同時修改數(shù)據(jù)庫中兩個不同表時,如果它們不是一個事務的話,當?shù)谝粋€表修改完,可能第二個表修改過程中出現(xiàn)了異常而沒能修改,此時就只有第二個表依舊是未修改之前的狀態(tài),而第一個表已經(jīng)被修改完畢。而當你把它們設定為一個事務的時候,當?shù)谝粋€表修改完,第二表修改出現(xiàn)異常而沒能修改,第一個表和第二個表都要回到未修改的狀態(tài),這就是所謂的事務回滾。9、MySQL的復制原理以及流程。1)在Slave 服務器上執(zhí)行sart slave命令開啟主從復制開關,開始進行主從復制。2)此時,Slave服務器的IO線程會通過在master上已經(jīng)授權的復制用戶權限請求連接master服務器,并請求從執(zhí)行binlog日志文件的指定位置(日志文件名和位置就是在配置主從復制服務時執(zhí)行change master命令指定的)之后開始發(fā)送binlog日志內容3)Master服務器接收到來自Slave服務器的IO線程的請求后,二進制轉儲IO線程會根據(jù)Slave服務器的IO線程請求的信息分批讀取指定binlog日志文件指定位置之后的binlog日志信息,然后返回給Slave端的IO線程。返回的信息中除了binlog日志內容外,還有在master服務器端記錄的新的binlog文件名稱,以及在新的binlog中的下一個指定更新位置。4)當Slave服務器的IO線程獲取到Master服務器上IO線程發(fā)送的日志內容、日志文件及位置點后,會將binlog日志內容依次寫到Slave端自身的Relay Log(即中繼日志)文件(MySQL-relay-bin.xxx)的最末端,并將新的binlog文件名和位置記錄到master-info文件中,以便下一次讀取master端新binlog日志時能告訴Master服務器從新binlog日志的指定文件及位置開始讀取新的binlog日志內容5)Slave服務器端的SQL線程會實時檢測本地Relay Log 中IO線程新增的日志內容,然后及時把Relay LOG 文件中的內容解析成sql語句,并在自身Slave服務器上按解析SQL語句的位置順序執(zhí)行應用這樣sql語句,并在relay-log.info中記錄當前應用中繼日志的文件名和位置點10、drop, delete truncate的區(qū)別。三者都是刪除的意思,但是三者個有些區(qū)別? ● delete和truncate只刪除表的數(shù)據(jù)不刪除表的結構? ● 速度 drop > truncate > delete? ● 想刪除部分數(shù)據(jù)時, delete 刪除時要帶上where語句? ● 保留表而想刪除所有的數(shù)據(jù)時用truncate11、寫出數(shù)據(jù)庫的三大范式。第一范式? 字段具有原子性,不可再分第二范式? 表中的每列都和主鍵相關第三范式? 每列都和主鍵列直接相關,而不是間接相關12、數(shù)據(jù)庫中的樂觀鎖和悲觀鎖。根據(jù)不同類型可以對數(shù)據(jù)設置不同的鎖權限** 樂觀 悲觀 鎖 主要是作用在并發(fā)訪問控制**? ● 悲觀鎖 假定會發(fā)生并發(fā)沖突,屏蔽任何違反數(shù)據(jù)完整的操作? ● 樂觀鎖 假定不會發(fā)生沖突,只有在提交操作時檢查是否違反數(shù)據(jù)的完整性13、什么是存儲過程,及其優(yōu)缺點。存儲過程是一些編譯好的SQL語句因為系統(tǒng)在調用SQL的時候比較浪費時間,所以之前先將一些基本的額SQL語句代碼進行編譯(對單表或多表的增刪改查),然后再給代碼取一個名字,在需要這個功能時去調用它就可以了。優(yōu)點:1. 運行速度:對于很簡單的sql,存儲過程沒有什么優(yōu)勢。對于復雜的業(yè)務邏輯,因為在存儲過程創(chuàng)建的時候,數(shù)據(jù)庫已經(jīng)對其進行了一次解析和優(yōu)化。存儲過程一旦執(zhí)行,在內存中就會保留一份這個存儲過程,這樣下次再執(zhí)行同樣的存儲過程時,可以從內存中直接調用,所以執(zhí)行速度會比普通sql快。? ? 2.? 減少網(wǎng)絡傳輸:存儲過程直接就在數(shù)據(jù)庫服務器上跑,所有的數(shù)據(jù)訪問都在數(shù)據(jù)庫服務器內部進行,不需要傳輸數(shù)據(jù)到其它服務器,所以會減少一定的網(wǎng)絡傳輸。但是在存儲過程中沒有多次數(shù)據(jù)交互,那么實際上網(wǎng)絡傳輸量和直接sql是一樣的。而且我們的應用服務器通常與數(shù)據(jù)庫是在同一內網(wǎng),大數(shù)據(jù)的訪問的瓶頸會是硬盤的速度,而不是網(wǎng)速?! ?. 可維護性:的存儲過程有些時候比程序更容易維護,這是因為可以實時更新DB端的存儲過程。? 有些bug,直接改存儲過程里的業(yè)務邏輯,就搞定了。 4. 增強安全性:提高代碼安全,防止 SQL注入。這一點sql語句也可以做到?! ?. 可擴展性:應用程序和數(shù)據(jù)庫操作分開,獨立進行,而不是相互在一起。方便以后的擴展和DBA維護優(yōu)化。缺點:1. SQL本身是一種結構化查詢語言,但不是面向對象的的,本質上還是過程化的語言,面對復雜的業(yè)務邏輯,過程化的處理會很吃力。同時SQL擅長的是數(shù)據(jù)查詢而非業(yè)務邏輯的處理,如果如果把業(yè)務邏輯全放在存儲過程里面,違背了這一原則。2. 如果需要對輸入存儲過程的參數(shù)進行更改,或者要更改由其返回的數(shù)據(jù),則您仍需要更新程序集中的代碼以添加參數(shù)、更新調用,等等,這時候估計會比較繁瑣了。3. 開發(fā)調試復雜,由于IDE的問題,存儲過程的開發(fā)調試要比一般程序困難。? ? 4. 沒辦法應用緩存。雖然有全局臨時表之類的方法可以做緩存,但同樣加重了數(shù)據(jù)庫的負擔。如果緩存并發(fā)嚴重,經(jīng)常要加鎖,那效率實在堪憂。5. 不支持群集,數(shù)據(jù)庫服務器無法水平擴展,或者數(shù)據(jù)庫的切割(水平或垂直切割)。數(shù)據(jù)庫切割之后,存儲過程并不清楚數(shù)據(jù)存儲在哪個數(shù)據(jù)庫中??偨Y:1. 適當?shù)氖褂么鎯^程,能夠提高我們SQL查詢的性能,2. 存儲過程不應該大規(guī)模使用,濫用。3. 隨著眾多ORM 的出現(xiàn),存儲過程很多優(yōu)勢已經(jīng)不明顯。4. SQL最大的缺點還是SQL語言本身的局限性——SQL本身是一種結構化查詢語言,我們不應該用存儲過程處理復雜的業(yè)務邏輯——讓SQL回歸它“結構化查詢語言”的功用。復雜的業(yè)務邏輯,還是交給代碼去處理吧。14、Innodb是行鎖,那什么時候會產(chǎn)生行鎖,什么情況下會變成表鎖?一般情況下,innodb只對指定的行進行鎖定,其他進程還是可以對表中的其他行進行操作的,因此,這時候innodb加的就是行鎖;但是,如果在執(zhí)行一個SQL語句時MySQL不能確定要掃描的范圍,InnoDB表同樣會鎖全表,例如update table set num=1 where name like “%aaa%”。 15、大批量插入數(shù)據(jù),如何提高insert的性能?有如下方法:1)合并多條 insert 為一條,即: insert into t values(a,b,c),? (d,e,f) ,,,原因分析:主要原因是多條insert合并后日志量(MySQL的binlog和innodb的事務讓日志) 減少了,降低日志刷盤的數(shù)據(jù)量和頻率,從而提高效率。通過合并SQL語句,同時也能減少SQL語句解析的次數(shù),減少網(wǎng)絡傳輸?shù)腎O。2)修改參數(shù) bulk_insert_buffer_size, 調大批量插入的緩存;3)設置 innodb_flush_log_at_trx_commit = 0 ,相對于 innodb_flush_log_at_trx_commit = 1 可以十分明顯的提升導入速度;? ? ? (備注:innodb_flush_log_at_trx_commit 參數(shù)對 InnoDB Log 的寫入性能有非常關鍵的影響。該參數(shù)可以設置為0,1,2,解釋如下: ? 0:log buffer中的數(shù)據(jù)將以每秒一次的頻率寫入到log file中,且同時會進行文件系統(tǒng)到磁盤的同步操作,但是每個事務的commit并不會觸發(fā)任何log buffer 到log file? 的刷新或者文件系統(tǒng)到磁盤的刷新操作; ? 1:在每次事務提交的時候將log buffer 中的數(shù)據(jù)都會寫入到log file,同時也會觸發(fā)文件系統(tǒng)到磁盤的同步; ? 2:事務提交會觸發(fā)log buffer 到log file的刷新,但并不會觸發(fā)磁盤文件系統(tǒng)到磁盤的同步。此外,每秒會有一次文件系統(tǒng)到磁盤同步操作。? ? ? ? )4)手動使用事務? 因為mysql默認是autocommit的,這樣每插入一條數(shù)據(jù),都會進行一次commit;所以,為了減少創(chuàng)建事務的消耗,我們可用手工使用事務,即START TRANSACTION;insert 。。,insert。。 commit;即執(zhí)行多個insert后再一起提交;一般1000條insert 提交一次。 16、如果發(fā)現(xiàn)CPU,或者IO壓力很大,怎么定位問題?? 1)、首先我會用top命令和iostat命令,定位是什么進程在占用cpu和磁盤io;? ? 2)、如果是mysql的問題,我會登錄到數(shù)據(jù)庫,通過show full processlist命令,看現(xiàn)在數(shù)據(jù)庫在執(zhí)行什么sql語句,是否有語句長時間執(zhí)行使數(shù)據(jù)庫卡?。? 3)、執(zhí)行show innodb engine status命令,查看數(shù)據(jù)庫是否有鎖資源爭用;? 4)、查看mysql慢查詢日志,看是否有慢sql;? 5)、找到引起數(shù)據(jù)庫占用資源高的語句,進行優(yōu)化,該建索引的建索引,索引不合適的刪索引,或者根據(jù)情況kill掉耗費資源的sql語句等17、innodb有多少種日志?分別是什么。錯誤日志(error log): log-err查詢日志(general? query log): log慢查詢日志: -log-slow-queries? ? ? 二進制日志 (binary log): log-bin中繼日志( relay log)18、請列舉除mysql外,PHP可以連接的其它關系數(shù)據(jù)庫(至少2個)。sqlserver,postgresql,oracle,db219、寫出常用5種數(shù)據(jù)庫函數(shù)。concat(),find_in_set(),now(),from_unixtime(),unix_timestamp()20、編寫SQL語句:(1)創(chuàng)建一張學生表student,包含學號student_id,姓名studen_name,性別sex,年齡age,家庭住址address,聯(lián)系電話tel信息?(2)修改學生表結構,增加學歷字段?(3)隨機插入3條學生信息?(4)查詢出年齡小于20歲,學歷為本科的所有學員信息?(5)統(tǒng)計所有學生的男女人數(shù)?(6)統(tǒng)計學生年齡在15-20,20-25,25-30三個區(qū)間的人數(shù)分別為多少?八、nosql部分1、使用redis有哪些好處?(1) 速度快,因為數(shù)據(jù)存在內存中,類似于HashMap,HashMap的優(yōu)勢就是查找和操作的時間復雜度都是O(1)(2) 支持豐富數(shù)據(jù)類型,支持string,list,set,sorted set,hash(3) 支持事務,操作都是原子性,所謂的原子性就是對數(shù)據(jù)的更改要么全部執(zhí)行,要么全部不執(zhí)行(4) 豐富的特性:可用于緩存,消息,按key設置過期時間,過期后將會自動刪除2. redis相比memcached有哪些優(yōu)勢?(1) memcached所有的值均是簡單的字符串,redis作為其替代者,支持更為豐富的數(shù)據(jù)類型(2) redis的速度比memcached快很多,因為數(shù)據(jù)存在內存中,類似于HashMap,HashMap的優(yōu)勢就是查找和操作的時間復雜度都是O(1)(3) redis可以持久化其數(shù)據(jù)3、redis常見性能問題和解決方案?(1) Master最好不要做任何持久化工作,如RDB內存快照和AOF日志文件(2) 如果數(shù)據(jù)比較重要,某個Slave開啟AOF備份數(shù)據(jù),策略設置為每秒同步一次(3) 為了主從復制的速度和連接的穩(wěn)定性,Master和Slave最好在同一個局域網(wǎng)內(4) 盡量避免在壓力很大的主庫上增加從庫(5) 主從復制不要用圖狀結構,用單向鏈表結構更為穩(wěn)定,即:Master <- Slave1 <- Slave2 <- Slave3...這樣的結構方便解決單點故障問題,實現(xiàn)Slave對Master的替換。如果Master掛了,可以立刻啟用Slave1做Master,其他不變。4、redis的并發(fā)競爭問題如何解決?Redis為單進程單線程模式,采用隊列模式將并發(fā)訪問變?yōu)榇性L問。Redis本身沒有鎖的概念,Redis對于多個客戶端連接并不存在競爭,但是在Jedis客戶端對Redis進行并發(fā)訪問時會發(fā)生連接超時、數(shù)據(jù)轉換錯誤、阻塞、客戶端關閉連接等問題,這些問題均是由于客戶端連接混亂造成。對此有2種解決方法: 1.客戶端角度,為保證每個客戶端間正常有序與Redis進行通信,對連接進行池化,同時對客戶端讀寫Redis操作采用內部鎖synchronized。 2.服務器角度,利用setnx實現(xiàn)鎖?! τ诘谝环N,需要應用程序自己處理資源的同步,可以使用的方法比較通俗,可以使用synchronized也可以使用lock;第二種需要用到Redis的setnx命令,但是需要注意一些問題。5、redis持久化有幾種方式,各有什么優(yōu)缺點? 1)、快照(snapshots)優(yōu)點:? ? RDB 是一個非常緊湊(compact)的文件,它保存了 Redis 在某個時間點上的數(shù)據(jù)集。 這種文件非常適合用于進行備份: 比如說,你可以在最近的 24 小時內,每小時備份一次 RDB 文件,并且在每個月的每一天,也備份一個 RDB 文件。 這樣的話,即使遇上問題,也可以隨時將數(shù)據(jù)集還原到不同的版本。? ? RDB 非常適用于災難恢復(disaster recovery):它只有一個文件,并且內容都非常緊湊,可以(在加密后)將它傳送到別的數(shù)據(jù)中心,或者亞馬遜 S3 中。? ? RDB 可以最大化 Redis 的性能:父進程在保存 RDB 文件時唯一要做的就是 fork 出一個子進程,然后這個子進程就會處理接下來的所有保存工作,父進程無須執(zhí)行任何磁盤 I/O 操作。? ? RDB 在恢復大數(shù)據(jù)集時的速度比 AOF 的恢復速度要快缺點:? ? 如果你需要盡量避免在服務器故障時丟失數(shù)據(jù),那么 RDB 不適合你。 雖然 Redis 允許你設置不同的保存點(save point)來控制保存 RDB 文件的頻率, 但是, 因為RDB 文件需要保存整個數(shù)據(jù)集的狀態(tài), 所以它并不是一個輕松的操作。 因此你可能會至少 5 分鐘才保存一次 RDB 文件。 在這種情況下, 一旦發(fā)生故障停機, 你就可能會丟失好幾分鐘的數(shù)據(jù)。? ? 每次保存 RDB 的時候,Redis 都要 fork() 出一個子進程,并由子進程來進行實際的持久化工作。 在數(shù)據(jù)集比較龐大時, fork()可能會非常耗時,造成服務器在某某毫秒內停止處理客戶端; 如果數(shù)據(jù)集非常巨大,并且 CPU 時間非常緊張的話,那么這種停止時間甚至可能會長達整整一秒。 雖然 AOF 重寫也需要進行 fork() ,但無論 AOF 重寫的執(zhí)行間隔有多長,數(shù)據(jù)的耐久性都不會有任何損失?!?)、AOF優(yōu)點:? ? 使用 AOF 持久化會讓 Redis 變得非常耐久(much more durable):你可以設置不同的 fsync 策略,比如無 fsync ,每秒鐘一次 fsync ,或者每次執(zhí)行寫入命令時 fsync 。 AOF 的默認策略為每秒鐘 fsync 一次,在這種配置下,Redis 仍然可以保持良好的性能,并且就算發(fā)生故障停機,也最多只會丟失一秒鐘的數(shù)據(jù)( fsync 會在后臺線程執(zhí)行,所以主線程可以繼續(xù)努力地處理命令請求)。? ? AOF 文件是一個只進行追加操作的日志文件(append only log), 因此對 AOF 文件的寫入不需要進行 seek , 即使日志因為某些原因而包含了未寫入完整的命令(比如寫入時磁盤已滿,寫入中途停機,等等), redis-check-aof 工具也可以輕易地修復這種問題。? ? Redis 可以在 AOF 文件體積變得過大時,自動地在后臺對 AOF 進行重寫: 重寫后的新 AOF 文件包含了恢復當前數(shù)據(jù)集所需的最小命令集合。 整個重寫操作是絕對安全的,因為 Redis 在創(chuàng)建新 AOF 文件的過程中,會繼續(xù)將命令追加到現(xiàn)有的 AOF 文件里面,即使重寫過程中發(fā)生停機,現(xiàn)有的 AOF 文件也不會丟失。 而一旦新 AOF 文件創(chuàng)建完畢,Redis 就會從舊 AOF 文件切換到新 AOF 文件,并開始對新 AOF 文件進行追加操作。? ? AOF 文件有序地保存了對數(shù)據(jù)庫執(zhí)行的所有寫入操作, 這些寫入操作以 Redis 協(xié)議的格式保存, 因此 AOF 文件的內容非常容易被人讀懂, 對文件進行分析(parse)也很輕松。 導出(export) AOF 文件也非常簡單: 舉個例子, 如果你不小心執(zhí)行了 FLUSHALL 命令, 但只要 AOF 文件未被重寫, 那么只要停止服務器, 移除 AOF 文件末尾的 FLUSHALL 命令, 并重啟 Redis , 就可以將數(shù)據(jù)集恢復到 FLUSHALL 執(zhí)行之前的狀態(tài)。缺點:? ? 對于相同的數(shù)據(jù)集來說,AOF 文件的體積通常要大于 RDB 文件的體積。? ? 根據(jù)所使用的 fsync 策略,AOF 的速度可能會慢于 RDB 。 在一般情況下, 每秒 fsync 的性能依然非常高, 而關閉 fsync 可以讓 AOF 的速度和 RDB 一樣快, 即使在高負荷之下也是如此。 不過在處理巨大的寫入載入時,RDB 可以提供更有保證的最大延遲時間(latency)。? ? AOF 在過去曾經(jīng)發(fā)生過這樣的 bug : 因為個別命令的原因,導致 AOF 文件在重新載入時,無法將數(shù)據(jù)集恢復成保存時的原樣。 (舉個例子,阻塞命令 BRPOPLPUSH 就曾經(jīng)引起過這樣的 bug 。) 測試套件里為這種情況添加了測試: 它們會自動生成隨機的、復雜的數(shù)據(jù)集, 并通過重新載入這些數(shù)據(jù)來確保一切正常。 雖然這種 bug 在 AOF 文件中并不常見, 但是對比來說, RDB 幾乎是不可能出現(xiàn)這種 bug 的6、mySQL里有2000w數(shù)據(jù),redis中只存20w的數(shù)據(jù),如何保證redis中的數(shù)據(jù)都是熱點數(shù)據(jù)? redis 內存數(shù)據(jù)集大小上升到一定大小的時候,就會施行數(shù)據(jù)淘汰策略。redis 提供 6種數(shù)據(jù)淘汰策略:voltile-lru:從已設置過期時間的數(shù)據(jù)集(server.db[i].expires)中挑選最近最少使用的數(shù)據(jù)淘汰volatile-ttl:從已設置過期時間的數(shù)據(jù)集(server.db[i].expires)中挑選將要過期的數(shù)據(jù)淘汰volatile-random:從已設置過期時間的數(shù)據(jù)集(server.db[i].expires)中任意選擇數(shù)據(jù)淘汰allkeys-lru:從數(shù)據(jù)集(server.db[i].dict)中挑選最近最少使用的數(shù)據(jù)淘汰allkeys-random:從數(shù)據(jù)集(server.db[i].dict)中任意選擇數(shù)據(jù)淘汰no-enviction(驅逐):禁止驅逐數(shù)據(jù)7、請列舉5種以上redis 最適合的場景。(1)、會話緩存(Session Cache)(2)、全頁緩存(FPC)(3)、隊列(4),排行榜/計數(shù)器(5)、發(fā)布/訂閱8、Memcache與Redis的區(qū)別都有哪些?1)、存儲方式Memecache把數(shù)據(jù)全部存在內存之中,斷電后會掛掉,數(shù)據(jù)不能超過內存大小。Redis有部份存在硬盤上,這樣能保證數(shù)據(jù)的持久性。2)、數(shù)據(jù)支持類型Memcache對數(shù)據(jù)類型支持相對簡單。Redis有復雜的數(shù)據(jù)類型。3)、使用底層模型不同它們之間底層實現(xiàn)方式 以及與客戶端之間通信的應用協(xié)議不一樣。Redis直接自己構建了VM 機制 ,因為一般的系統(tǒng)調用系統(tǒng)函數(shù)的話,會浪費一定的時間去移動和請求。4),value大小redis最大可以達到1GB,而memcache只有1MB9、簡單的描述一下Memcache的工作原理。Memcached的神奇來自兩階段哈希(two-stage hash)。Memcached就像一個巨大的、存儲了很多對的哈希表。通過key,可以存儲或查詢任意的數(shù)據(jù)。
客戶端可以把數(shù)據(jù)存儲在多臺memcached上。當查詢數(shù)據(jù)時,客戶端首先參考節(jié)點列表計算出key的哈希值(階段一哈希),進而選中一個節(jié)點;客戶端將請求發(fā)送給選中的節(jié)點,然后memcached節(jié)點通過一個內部的哈希算法(階段二哈希),查找真正的數(shù)據(jù)(item)。
舉個列子,假設有3個客戶端1, 2, 3,3臺memcached A, B, C:
Client 1想把數(shù)據(jù)”barbaz”以key “foo”存儲。Client 1首先參考節(jié)點列表(A, B, C),計算key “foo”的哈希值,假設memcached B被選中。接著,Client 1直接connect到memcached B,通過key “foo”把數(shù)據(jù)”barbaz”存儲進去?! lient 2使用與Client 1相同的客戶端庫(意味著階段一的哈希算法相同),也擁有同樣的memcached列表(A, B, C)。
于是,經(jīng)過相同的哈希計算(階段一),Client 2計算出key “foo”在memcached B上,然后它直接請求memcached B,得到數(shù)據(jù)”barbaz”。
各種客戶端在memcached中數(shù)據(jù)的存儲形式是不同的(perl Storable, php serialize, java hibernate, JSON等)。一些客戶端實現(xiàn)的哈希算法也不一樣。但是,memcached服務器端的行為總是一致的。
最后,從實現(xiàn)的角度看,memcached是一個非阻塞的、基于事件的服務器程序。這種架構可以很好地解決C10K problem ,并具有極佳的可擴展性。
可以參考A Story of Caching ,這篇文章簡單解釋了客戶端與memcached是如何交互的。
10、memcached的cache機制是怎樣的?
Memcached主要的cache機制是LRU(最近最少用)算法+超時失效。
當您存數(shù)據(jù)到memcached中,可以指定該數(shù)據(jù)在緩存中可以呆多久Which is forever, or some time in the future。
如果memcached的內存不夠用了,過期的slabs會優(yōu)先被替換,接著就輪到最老的未被使用的slabs。
11、memcached最大能存儲多大的單個item,為什么?
1MB。如果你的數(shù)據(jù)大于1MB,可以考慮在客戶端壓縮或拆分到多個key中。
12、memcached最大的優(yōu)勢是什么?
Memcached最大的好處就是它帶來了極佳的水平可擴展性,特別是在一個巨大的系統(tǒng)中。由于客戶端自己做了一次哈希,那么我們很容易增加大量memcached到集群中。memcached之間沒有相互通信,因此不會增加 memcached的負載;沒有多播協(xié)議,不會網(wǎng)絡通信量爆炸(implode)。memcached的集群很好用。內存不夠了?增加幾臺 memcached吧;CPU不夠用了?再增加幾臺吧;有多余的內存?在增加幾臺吧,不要浪費了。
基于memcached的基本原則,可以相當輕松地構建出不同類型的緩存架構。除了這篇FAQ,在其他地方很容易找到詳細資料的。
看看下面的幾個問題吧,它們在memcached、服務器的local cache和MySQL的query cache之間做了比較。這幾個問題會讓您有更全面的認識。
13、memcached能接受的key的最大長度是多少?
key的最大長度是250個字符。
需要注意的是,250是memcached服務器端內部的限制,如果您使用的客戶端支持”key的前綴”或類似特性,
那么key(前綴+原始key)的最大長度是可以超過250個字符的。
我們推薦使用使用較短的key,因為可以節(jié)省內存和帶寬。
14、memcached對item的過期時間有什么限制?為什么?
過期時間最大可以達到30天。
memcached把傳入的過期時間(時間段)解釋成時間點后,一旦到了這個時間點,memcached就把item置為失效狀態(tài)。
這是一個簡單但obscure的機制。
九、服務器架構
1,假設給你5臺服務器,請大致的描述一下,如何使用你所熟悉的開源軟件,搭建一個日PV300萬左右的中型網(wǎng)站?
1臺做負載,2臺做應用,2臺做數(shù)據(jù)庫主從
十、其它
1:git的使用命令,例如:寫出版本回退命令。
git reset --hard head^
2:git與svn的區(qū)別。
1) 最核心的區(qū)別Git是分布式的,而Svn不是分布的。
2) Git把內容按元數(shù)據(jù)方式存儲,而SVN是按文件:
3) Git沒有一個全局版本號,而SVN有:
4) Git的內容的完整性要優(yōu)于SVN:
5) Git下載下來后,在OffLine狀態(tài)下可以看到所有的Log,SVN不可以。
6) 分支合并git比svn列少出現(xiàn)錯誤。
3:如何進行多分支開發(fā),包括多人開發(fā)協(xié)同,分段測試,上線。
參考:GIT版本管理:Git Flow模型