1. 程式人生 > >2018 PHP面試題

2018 PHP面試題

2018 PHP面試題

題目來自《PHP程式設計師面試筆試寶典》,裡面涵蓋了近三年了各大型企業常考的PHP面試題,針對面試題提取出來各種面試知識也涵蓋在了本書。

1、PHP常考基礎

1、PHP與ASP、JSP有什麼區別?

ASP全名Active Server Pages,是一個基於Windows平臺的Web伺服器端的開發環境,利用它可以產生和執行動態的、互動的、高效能的Web服務應用程式,它只能在微軟平臺上使用,移植性不好。ASP採用指令碼語言VB ScriptJScriptJavaScript)作為自己的開發語言。國內早期大部分網站都用它來開發。但因微軟全面轉向,ASP.NET放棄了

ASPWeb開發模式,所以現在已經被淘汰使用。

PHP是一種跨平臺的伺服器端的嵌入式指令碼語言。它大量地借用CJavaPerl語言的語法,並耦合PHP自己的特性,使Web開發者能夠快速地寫出動態生成頁面。它可嵌入HTML中,非常適合Web開發,而且它支援目前絕大多數資料庫。除此以外,PHP是完全免費的,不用花錢,開發人員就可以從PHP官方站點(http://www.php.net)自由下載。而且開發人員可以不受限制地獲得原始碼,甚至可以從中加入自己需要的特色,開發效率高,成本低。

JSPSun公司推出的一種網路程式語言,跨平臺執行,安全性高,執行效率也高。它的開發語言主要基於Java

ASPJSPPHP三者都提供在 HTML 程式碼中混合某種程式程式碼、由語言引擎解釋執行,但JSP程式碼被編譯成 Servlet並由Java虛擬機器解釋執行,這種編譯操作僅在對JSP頁面的第一次請求時發生。在ASPPHPJSP環境下,HTML程式碼主要負責描述資訊的顯示樣式,而程式程式碼則用來描述處理邏輯。普通的HTML頁面只依賴於Web伺服器,而ASPPHPJSP頁面需要附加的語言引擎分析和執行程式程式碼。程式程式碼的執行結果被重新嵌入HTML程式碼中,然後一起傳送給瀏覽器。ASPPHPJSP三者都是面向 Web 伺服器的技術,客戶端瀏覽器不需要任何附加的軟體支援。

 

2PHP中,單引號和雙引號所包圍的字串的區別是(    

A.單引號解析其中\r\t等轉義字元,而雙引號不解析

B.雙引號速度快,單引號速度慢

C.單引號速度快,雙引號速度慢

D.雙引號解析其中以$開頭的變數,而單引號不解析

參考答案:D

分析:雙引號是可以解析$符開頭的變數和轉義字元的,而單引號不解析也不轉義字元。所以,選項A錯誤,選項D正確。

對於選項B和選項C,由於題目中明確說了引號內包含的是字串,因此不需要對變數進行解析,在這種情況下雙引號和單引號的效率是相同的。選項B和選項C都是錯誤的。

 

3、面向物件與面向過程有什麼區別?

面向物件是當今軟體開發方法的主流方法之一,它是把資料及對資料的操作方法放在一起,作為一個相互依存的整體,即物件。對同類物件抽象出其共性,即類,類中的大多數資料,只能被本類的方法進行處理。類通過一個簡單的外部介面與外界發生關係,物件與物件之間通過訊息進行通訊。程式流程由使用者在使用中決定。例如,站在抽象的角度,人類具有身高、體重、年齡、血型等一些特稱,人類會勞動、會直立行走、會吃飯、會用自己的頭腦去創造工具等這些方法,人類僅僅只是一個抽象的概念,它是不存在的實體,但是所有具備人類這個群體的屬性與方法的物件都稱為人,這個物件人是實際存在的實體每個人都是人這個群體的一個物件。

而面向過程是一種以事件為中心的開發方法,就是自頂向下順序執行,逐步求精,其程式結構是按功能劃分為若干個基本模組,這些模組形成一個樹狀結構,各模組之間的關係也比較簡單,在功能上相對獨立,每一模組內部一般都是由順序、選擇和迴圈三種基本結構組成,其模組化實現的具體方法是使用子程式,而程式流程在寫程式時就已經決定。例如五子棋,面向過程的設計思路就是首先分析問題的步驟:第一步,開始遊戲;第二步,黑子先走;第三步,繪製畫面;第四步,判斷輸贏;第五步,輪到白子;第六步,繪製畫面;第七步,判斷輸贏;第八步,返回步驟;第九步,輸出最後結果。把上面每個步驟用分別的函式來實現,就是一個面向過程的開發方法。

具體而言,二者主要有以下幾個方面的不同之處。

1出發點不同面向物件是用符合常規思維方式來處理客觀世界的問題,強調把問題域的要領直接對映到物件及物件之間的介面上。而面向過程方法則不然,它強調的是過程的抽象化與模組化,它是以過程為中心構造或處理客觀世界問題的。

2層次邏輯關係不同面向物件方法則是用計算機邏輯來模擬客觀世界中的物理存在,以物件的集合類作為處理問題的基本單位,儘可能地使計算機世界向客觀世界靠攏,以使問題的處理更清晰直接,面向物件方法是用類的層次結構來體現類之間的繼承和發展。面向過程方法處理問題的基本單位是能清晰準確地表達過程的模組,用模組的層次結構概括模組或模組間的關係與功能,把客觀世界的問題抽象成計算機可以處理的過程。

3資料處理方式與控制程式方式不同面向物件方法將資料與對應的程式碼封裝成一個整體,原則上其他物件不能直接修改其資料,即物件的修改只能由自身的成員函式完成,控制程式方式上是通過事件驅動來啟用和執行程式。而面向過程方法是直接通過程式來處理資料,處理完畢後即可顯示處理結果,在控制程式方式上是按照設計呼叫或返回程式,不能自由導航,各模組之間存在著控制與被控制、呼叫與被呼叫。

4分析設計與編碼轉換方式不同面向物件方法貫穿軟體生命週期的分析、設計及編碼之間是一種平滑過程,從分析到設計再到編碼是採用一致性的模型表示,即實現的是一種無縫連線。而面向過程方法強調分析、設計及編碼之間按規則進行轉換,貫穿軟體生命週期的分析、設計及編碼之間實現的是一種有縫的連線。

 

4PHP中,自定義一個類的方式是(    

A.<?php default class Class_Name(){ //...... } ?>

B.<?php class Class_Name{ //......} ?>

C.<?php public function Class_Name(){//......}?>

D.<?php function Class_Name{//......}?>

參考答案:B

分析:定義一個類是使用class關鍵字加類名來定義的,定義格式為:class 類名{}例項化一個類的格式為:$object=new 類名();

【真題11獲得例項化物件所屬類名字的函式是(    

A.get_class() B.get_object_vars()

C.get_class_methods() D.get_classname()

參考答案:A

分析:對於選項Aget_class()函式用於返回一個物件的類的名稱。所以,選項A正確。

對於選項Bget_object_vars()函式用於得到給定物件的屬性。所以,選項B錯誤。

對於選項Cget_class_methods()函式用於獲取類方法的名字。所以,選項C錯誤。

對於選項DPHP中沒有該方法。所以,選項D錯誤。

 

5以下有關PHP面向物件的說法中,不正確的是(    )

A.要實現一個介面,使用 implements操作符,類中必須實現介面中定義的所有方法,否則會報一個致命錯誤

B.類名可以是任何非 PHP保留字的合法標籤,漢字也可以作為PHP的類名

C.如果PHP的子類中定義了建構函式,則建立子類的物件時,會隱式呼叫其父類的建構函式

D.序列化一個物件將會儲存物件的所有變數,但是不會儲存物件的方法,只會儲存類的名字

參考答案:C

分析:子類定義的建構函式會覆蓋父類的建構函式,如果要子類的建構函式執行,同時也執行父類的建構函式,那麼必須顯式地使用parent::__construct();去呼叫。所以,選項C錯誤。

 

6下面關於PHP抽象類的描述中,錯誤的是(    )

A.PHP中抽象類使用abstract關鍵字定義

B.沒有方法體的方法叫抽象方法,包含抽象方法的類必須是抽象類

C.抽象類中必須有抽象方法,否則不叫抽象類

D.抽象類不能例項化,也就是不可以new成物件

參考答案:C

分析:抽象類可以是個空類,也就是不一定需要有抽象方法。但抽象方法只能存在抽象類中。所以,選項C錯誤。

 

7、什麼是多型?

多型是面向物件程式設計中程式碼重用的一個重要機制,它表示當同一個操作作用在不同的物件的時候,會有不同的語義,從而會產生不同的結果。例如同樣是“+”操作,3+4用來實現整數相加,而“3”+“4”卻實現了字串的連線。一般而言,多型有兩種實現方式:覆蓋過載。

 

8includerequire有什麼區別?

requireinclude有著相似的功能:將指定檔案中的所有程式碼/文字/標記複製到使用requireinclude語句的檔案中。通常被用在資料、檔案或程式碼需要被共享的場景。通過把需要被共享的程式碼或資料放到一個單獨PHP檔案中,在需要使用的檔案中通過requireinclude來引用。require()include()也不是真正的函式,因此,require()include()語句也可以不加圓括號而直接加引數。

 

9下列程式碼的輸出是(    

<?php

    define("x","5");

    $x=x+10;

    echo x;

?>

 

A.Error B.5 C.10 D.15

參考答案:B

分析:在PHP中,define函式用於定義一個常量,而常量的值在設定以後,是無法更改的。本題中,x的值始終為5。所以,選項B正確。

 

10、如何對變數進行引用?

可以在變數的前面加&符號對變數進行引用,變數的引用相當於給變數起了個別名,通過不同的名字訪問同一個變數內容,所以改變其中一個變數的值,另一個變數也會跟著改變。

【真題54有如下程式碼:

<?php

    $a="hello";

    $b= &$a;

    unset($b);

    $b="world";

    echo $a;

?>

 

程式的執行結果為(    

A.hello B.world C.NULL D.unset

參考答案:A

分析:這個程式碼的執行過程如下圖所示

 

1首先執行$b= &$a後,ab引用同一個字串變數“hello”。

2接著執行unset($b),這個函式可以斷開這個引用關係。此時由於a仍然指向字串“hello”,也就是說這個字串仍然被a使用,因此這個字串不會被回收。

3接著執行$b="world",此時,b指向一個新的字串“world”,這並不會影響a的值。因此輸出結果為hello

 

2、PHP常考進階

11請寫一個函式驗證電子郵件的格式是否正確。

參考答案:

function checkEmail($email)

{

    $pregEmail= "/^([0-9A-Za-z\\-_\\.]+)@([0-9a-z]+\\.[a-z]{2,3}(\\.[a-z]{2})?)$/i";

    return preg_match($pregEmail,$email);  

}

 

分析:首尾兩個斜槓/是正則表示式的限定符,這是Perl正則的標準,而PHPPerl有相同的正則的規範。兩個斜槓之間表示的是正則內容,後面的i表示忽略大小寫。

這個正則表示式表示的含義如下:

1必須以([0-9A-Za-z\\-_\\.]+)開頭,也就是說郵件地址以多個字母、陣列、“-”“.”開頭。

2緊接著是字元“@”

3然後接著是多個字母或數字的字串,接著是一個字元“.”,接著是兩個或三個字母;然後接下來一部分可有可無的:一個“.”後面跟著兩個字母。

4郵件的結束符是滿足3)的字串。

 

12以下可以匹配中國居民身份證號碼的正則表示式是(    

A\d{15} B\d{18}

C\d D(^\d{15}$)|(^\d{18}$)|(^\d{17}(\d|X|x)$)

參考答案:D

分析:\d表示0~9任意數字。

 

13【真題96一個函式的引數不能是對變數的引用,除非在php.ini中把    設為on

參考答案:allow_call_time_pass_reference

分析:在PHP函式呼叫的時候,基本資料型別預設會使用值傳遞,而不是引用傳遞。allow_call_time_pass_reference 選項的作用為是否啟用在函式呼叫時強制引數被按照引用傳遞。如果把allow_call_time_pass_reference 配置為on,那麼在函式呼叫的時候會預設使用引用傳值。但是不推薦使用這種方法,原因是該方法在未來的版本中很可能不再支援。如果想使用引用傳遞,那麼推薦在函式呼叫的時候顯式地使用&進行引用傳遞。

 

14檔案讀操作

讀取檔案前,通常會判斷檔案能否讀取,例如是否有讀許可權,可以使用is_readable函式;示例程式碼如下:

<?php

    $file = "test.txt";

    if(is_readable($file) == false) {

        echo "can not read\n";

    }

    else{

        echo "can read \n";

    }

?>

 

當然也需要判斷檔案是否存在,可以使用file_exists()函式。示例程式碼如下:

<?php

    $file = "test.txt";

    if(file_exists($file) == false) {

        echo "file not exist\n";

    }

    else{

    }

    echo "file is exists \n";

?>

 

讀取檔案的方法有很多種,此處列舉最常用的按行讀取方法,示例程式碼如下:

<?php

    $file = "test.txt";

    $fp = fopen($file,"r");

    while(!feof($fp)){

        echo fgets($fp,1024);

    }    

    fclose($fp);

?>

 

需要注意的是,讀取檔案的length引數是可選項,如果忽略,則將繼續從流中讀取資料直到行結束。指定最大行的長度在利用資源上更為有效。此外,還有freadfile_get_contents等讀取檔案的方法,此處不再贅述。

 

15、什麼是異常處理與錯誤處理?

當執行的程式發生異常被丟擲時,程式不會繼續執行異常處後面的程式碼,PHP 會嘗試查詢匹配的“catch”程式碼塊。如果異常沒有被捕獲,那麼將會發生嚴重的錯誤,程式會終止或者不受控制執行。示例程式碼如下:

<?php

    function GetNum($num)

    {

        if($num > 10)

        {

            throw new Exception("Exception ocur");

        }

        return true;

    }

    GetNum(100);

?>

 

程式的執行結果為

Uncaught exception 'Exception' with message 'Exception ocur'

 

從這個例子可以看出,如果不對異常進行處理,那麼當程式有異常丟擲的時候就會結束執行。而對於物件方法的異常處理,還有另外一種處理方法,下面介紹在PHP呼叫一些不存在的物件方法時的異常處理,從而保證程式正常執行。主要是通過__call方法來實現的。

方法宣告為__call($funname,$arr_value),當被呼叫方法不存在的時候會預設呼叫這個方法。

示例程式碼如下:

class My {

    function __call($n,$v) {

        echo "錯誤的方法名:".$n;

        echo "錯誤的引數:".$v;

    }

}

 

 

16、什麼是記憶體管理?

記憶體管理主要指程式執行時對計算機記憶體資源的分配、使用和釋放等技術,記憶體管理的目標是高效、快速分配記憶體同時及時釋放和回收記憶體資源。記憶體管理主要包括是否有足夠的記憶體供程式使用,從記憶體池中獲取可用記憶體,使用後及時銷燬並重新分配給其他程式使用。

PHP開發過程中,如果遇到大陣列等操作,那麼可能會造成記憶體溢位等問題。一些常見的處理方法如下:

1)通過ini_set('memory_limit','64M')方法重置php可以使用的記憶體大小,一般在遠端主機上是不能修改php.ini檔案的,只能通過程式設定。注:在safe_mode(安全模式)下,ini_set會失效。

2)另一方面可以對陣列進行分批處理,及時銷燬無用的變數,儘量減少靜態變數的使用,在需要資料重用時,可以考慮使用引用(&)。同時對於資料庫、檔案操作完要及時關閉,物件使用完要及時呼叫解構函式等。

3)及時使用unset()函式釋放變數,使用時需要注意以下兩點:

① unset()函式只能在變數值佔用記憶體空間超過256位元組時才會釋放記憶體空間。

只有當指向該變數的所有變數都銷燬後,才能成功釋放記憶體。

 

17MySQL一樣,Redis在使用過程中,也會碰到很多的問題,適當的技巧和優化將大大提高Redis的使用效能,提高服務的質量。現將常見的一些問題總結如下:

1停止使用keys *操作

keys*操作執行速度將會變慢。因為keys命令的時間複雜度是O(n),其中n是要返回的keys的個數,由此可見這個命令的複雜度就取決於資料量的大小了。當資料量比較大時,在這個操作執行期間,其他任何命令在例項中都無法執行嚴重影響了效能。

可以使用scan命令來代替,scan命令通過增量迭代的方式來掃描資料庫。

2定位Redis速度降低的原因

使用INFO commandstats命令來檢視所有命令的統計情況,如命令執行了多少次,執行命令所耗費的毫秒數等資訊。

 

18Memcache的特徵和特性

Memcache的特徵如下:

1)協議簡單

2)基於libevent的事件處理

3)內建記憶體儲存方式

4Memcached不互相通訊的分散式。

Memcache的特性如下:

1)單個item 最大的資料為1MB

2)單程序最大的使用記憶體為2GB,需要更多記憶體時可開多個埠

3Memcached是多執行緒,非阻塞io複用的網路模型,Redis是單執行緒

4)鍵長最大為250位元組。

 

19下面可以用於伺服器共享session的方式有(    )

A.利用NFS共享Session資料 B.基於資料庫的Session共享

C.基於CookieSession共享 D.使用類似BIG-IP的負載裝置來實現資源共享

參考答案:ABCD

分析:共享Session的方式主要有以下幾種:

1)基於NFSSession共享。NFSNetwork  File System)最早由Sun公司為解決Unix網路主機間的目錄共享而研發。僅需將共享目錄伺服器mount到其他伺服器的本地session目錄即可。

2基於資料庫的Session共享

3)基於CookieSession共享原理是將全站使用者的Session資訊加密、序列化後以Cookie的方式,統一種植在根域名下(如:.host.com),利用瀏覽器訪問該根域名下的所有二級域名站點時,會傳遞與之域名對應的所有Cookie內容的特性,從而實現使用者的CookieSession 在多服務間的共享訪問。

4基於快取(Memcache)的Session共享Memcache是一款基於Libevent多路非同步I/O技術的記憶體共享系統,簡單的key + value資料儲存模式使得程式碼邏輯小巧高效,因此在併發處理能力上佔據了絕對優勢,目前達到2000/s平均查詢,並且伺服器CPU消耗依然不到10%

所以,本題的答案為ABCD

 

20、如何預防各類安全性問題?

常見的安全性問題主要包括以下方面:

1SQL注入攻擊。所謂SQL注入式攻擊,就是攻擊者把SQL命令插入Web表單的域或頁面請求的查詢字串中,欺騙伺服器執行惡意的SQL命令。在某些表單中,使用者輸入的內容直接用來構造動態SQL命令,或作為儲存過程的輸入引數,這類表單特別容易受到SQL注入式攻擊。例如,對於一個站點http://www.shuaiqi100.com/News/details.jsp?id=2頁面,id是查詢引數,通過id獲取顯示某條資訊,在JSP程式中,用SQL語句來讀取該條新聞:“select * from news where id =”+ id,正常執行的話,只需要將id替換為引數2即可,沒有任何問題,但是當非法使用者將id的引數變為id=2;drop database news時,則執行的SQL語句除了讀取對應的新聞資訊外,還會執行drop database news資訊,可是後面這條語句是非法的。

由於SQL注入攻擊利用的是合法的SQL語句,使得這種攻擊不能被防火牆檢查,而且由於對任何基於SQL語言標準的資料庫都適用,所以危害特別大。儘管如此,目前防止SQL注入攻擊的方法也非常多,具體而言,有以下一些方法:使用預處理語句和引數分別傳送到資料庫伺服器進行解析,引數將會被當作普通字元處理。使用這種方式後,攻擊者無法注入惡意的SQL。那麼如何防止SQL注入攻擊呢,下面介紹常用的一些方法:

預處理語句和引數分別傳送到資料庫伺服器進行解析

使用函式addslashes()轉義提交的內容。

③ PHP配置檔案中開啟magic_quotes_gpc=on;將自動轉換使用者查詢的SQL語句,對防止SQL注入有重大作用。

PHP配置檔案中,將register_globals設定為off,關閉全域性變數註冊。

PHP配置檔案中,開啟安全模式safe_mode=on;

⑥ SQL語句的書寫儘量不要省略小引號與單引號。

提高資料庫表和欄位的命名技巧,對一些重要的欄位根據程式的特點命名,取不易被猜到的名字。

控制錯誤資訊,關閉錯誤資訊的輸出,將錯誤資訊寫到日誌檔案中,不要在網站暴露錯誤資訊。

2)資料庫操作安全問題。例如未對使用者的許可權進行限制,updatedeleteinsert等誤操作造成系統安全性問題。

解決方法為給不同的使用者授不同的許可權,這樣能夠保證只有有許可權的使用者才能進行特定的操作。

3)沒有驗證使用者http請求方式。惡意的使用者可以模擬http對網站進行請求產生惡意攻擊,為了防止這種攻擊需要檢查使用者的http請求中的訪問來源是否可信,對http頭中的referer進行過濾,只允許本域站點訪問。

4沒有驗證表單來源的唯一性,不能識別是合法的表單提交還是黑客偽造的表單提交。

為了防止黑客偽造表單提交,可以使用一次性令牌Token。通過伺服器端以某種策略生成隨機字串作為令牌儲存在Session裡,然後發出請求的頁面時,把該令牌以隱藏域一類的形式,與其他資訊一併發出,在接收頁面中把接收到的資訊中的令牌與Session中的令牌比較,一致才處理請求,否則拒絕請以此保證表單的來源唯一,防止黑客偽造的表單提交。

 

21、PHP的開發框架有哪些?

CodeIgniter是一個輕量級的PHP開發框架,具有快速開發、靈活性高等優點,它特別適合網際網路公司的快速迭代場景,因此很受歡迎,據說騰訊、去哪兒網等應用場景都使用了這個框架CodeIgniter具有動態例項化、鬆耦合、元件單一性等很多優點。動態例項化是指元件的匯入和函式在執行時才會生效。鬆耦合是指系統模組之間的關聯依賴很少,確保系統具有很好的重用性和靈活性。框架內的類和功能都是高度自治的,具有非常好的元件單一性。

CodeIgniter中,模型代表資料結構,包含取出、插入、更新資料庫的這些功能。檢視通常是一個網頁,但是在CodeIgniter中,一個檢視也可以是一個頁面片段,如頭部、頂部HTML程式碼片段。它還可以是一個RSS頁面,或其他任一頁面。控制器相當於一個指揮者,或者說是一個中介,它負責聯絡檢視和模型,以及其他任何處理HTTP請求和產生網頁的資源。

Zend Framework是完全基於PHP語言的針對Web應用開發的框架,與眾多的其他PHP開發框架相比,Zend Framework是一個PHP官方的框架,它由Zend公司負責開發和維護。Zend Framework同樣基於MVC模式,Zend Framework採用了ORMObject Relational Mapping,物件關係對映)思路,這是一種為了解決面向物件程式設計與關係資料庫存在的互不匹配現象的技術。簡單地說,這種技術將資料庫中的一個表對映為程式中的一個物件,表中的欄位對映為物件的屬性,然後通過提供的方法完成對資料庫的操作。就這一點而言,Zend Framework很相似於現在流行的非PHP的開發框架Ruby on Rails

ThinkPHP是一個快速、相容而且簡單的輕量級國產PHP開發框架,誕生於2006年初,原名FCS2007年元旦正式更名為ThinkPHP遵循Apache2開源協議釋出,從Struts結構移植過來並做了改進和完善,同時也借鑑了國外很多優秀的框架和模式,使用面向物件的開發結構和MVC模式,融合了Struts的思想和TagLib(標籤庫)、RoRORM對映和ActiveRecord模式。

此外,還有FleaPHPCakePHP等很多優秀的框架,此處就不一一列舉,它們本質上都是基於MVC的架構,下面著重介紹一下在網際網路公司使用比較廣泛的CI框架。

 

3、PHP+mysql

問題:設教務管理系統中有三個基本表:

學生資訊表S(SNO, SNAME, AGE, SEX),其屬性分別表示學號、學生姓名、年齡和性別

選課資訊表SC(SNO, CNO, SCGRADE),其屬性分別表示學號、課程號和成績

課程資訊表C(CNO, CNAME, CTEACHER),其屬性分別表示課程號、課程名稱和任課老師姓名

1SC表中每門課程的平均成績插入另外一個已經存在的表SC_C(CNO, CNAME, AVG_GRADE)中,其中AVG_GRADE表示的是每門課程的平均成績。

INSERT INTO SC_C(CNO, CNAME, AVG_GRADE)

SELECT SC.CNO, C.CNAME, AVG(SCGRADE) FROM SC, C WHERE SC.CNO = C.CNO GROUP BY SC.CNO

 

2規定女同學選修何昊老師的課程成績都應該在80分以上(包含80分)。

ALERT TABLE SC, S, C

ADD CONSTRAINT GRADE CHECK(SCGRADE>=80)

WHERE SC.CNO=C.CNO  AND  SC.SNO=S.SNO AND C.CTEACHER='何昊' AND  S.SEX=

 

""

 

3SC表中把何昊老師的女學生選課記錄刪除。

DELETE FROM SC WHERE CNO=(SELECT CNO FROM C WHERE C.CTEACHER ='何昊') AND SNO IN (SELECT SNO FROM S WHERE SEX='')

 

4)找出沒有選修過何昊老師講授課程的所有學生姓名

SELECT SNAME FROM S

WHERE NOT EXISTS(

SELECT * FROM SC,C WHERE SC.CNO=C.CNO AND CNAME='何昊' AND SC.SNO=S.SNO)

 

5)列出有門以上含兩門不及格課程(成績小於60)的學生姓名及其平均成績

SELECT S.SNO,S.SNAME,AVG_SCGRADE=AVG(SC.SCGRADE)

FROM S,SC,(

SELECT SNO FROM SC WHERE SCGRADE<60 GROUP BY SNO

HAVING COUNT(DISTINCT CNO)>=2)A WHERE S.SNO=A.SNO AND SC.SNO = A.SNO

GROUP BY S.SNO,S.SNAME

 

6)列出既學過“1”號課程,又學過“2”號課程的所有學生姓名

SELECT S.SNO,S.SNAME

FROM S,(SELECT SC.SNO FROM SC,C

WHERE SC.CNO=C.CNO AND C.CNAME IN('1','2')

GROUP BY SNO

HAVING COUNT(DISTINCT CNO)=2

)SC WHERE S.SNO=SC.SNO

 

7)列出“1”號課成績比“2”號同學該門課成績高的所有學生的學號

SELECT S.SNO,S.SNAME

FROM S,(

SELECT SC1.SNO

FROM SC SC1,C C1,SC SC2,C C2

WHERE SC1.CNO=C1.CNO AND C1.NAME='1'

AND SC2.CNO=C2.CNO AND C2.NAME='2'

AND SC1.SCGRADE>SC2.SCGRADE

)SC WHERE S.SNO=SC.SNO

 

8)列出“1”號課成績比“2”號課成績高的所有學生的學號及其“1”號課和“2”號課的成績

SELECT S.SNO,S.SNAME,SC.[1號課成績],SC.[2號課成績]

FROM S,(

SELECT SC1.SNO,[1號課成績]=SC1.SCGRADE,[2號課成績]=SC2.SCGRADE

FROM SC SC1,C C1,SC SC2,C C2

WHERE SC1.CNO=C1.CNO AND C1.NAME='1'

AND SC2.CNO=C2.CNO AND C2.NAME='2'

 

AND SC1.SCGRADE>SC2.SCGRADE

)SC WHERE S.SNO=SC.SNO

 

UNION和UNION ALL有什麼區別?

UNION在進行表求並集後會去掉重複的元素,所以會對所產生的結果集進行排序運算,刪除重複的記錄再返回結果。

UNION ALL只是簡單將兩個結果合併後就返回。因此,如果返回的兩個結果集中有重複的資料,那麼返回的結果集就會包含重複的資料。

從上面的對比可以看出,在執行查詢操作的時候,UNION ALL要比UNION快很多,所以,如果可以確認合併的兩個結果集中不包含重複的資料,那麼最好使用UNION ALL。例如,如下有兩個學生表Table1Table2

Table1

C1

C2

1

1

2

2

3

3

 

Table2

C1

C2

3

3

4

4

1

1

select * from Table1 union select * from Table2 的查詢結果為

C1

C2

1

1

2

2

3

3

4

4

select * from Table1 union all select * from Table2 的查詢結果為

C1

C2

1

1

2

2

3

3

3

3

4

4

1

1

3、什麼是資料庫三級封鎖協議?

眾所周知,基本的封鎖型別有兩種:排它鎖(X鎖)和共享鎖(S鎖)。所謂X鎖是事務T對資料A加上X鎖時,只允許事務T讀取和修改資料A。所謂S鎖是事務T對資料A加上S鎖時,其他事務只能再對資料AS鎖,而不能加X鎖,直到T釋放A上的S鎖。若事務T對資料物件A加了S鎖,則T就可以對A進行讀取,但不能進行更新(S鎖因此又稱為讀鎖),在T釋放A上的S鎖以前,其他事務可以再對AS鎖,但不能加X鎖,從而可以讀取A,但不能更新A

在運用X鎖和S鎖對資料物件加鎖時,還需要約定一些規則,例如,何時申請X鎖或S鎖、持鎖時間、何時釋放等,稱這些規則為封鎖協議(Locking Protocol)。對封鎖方式規定不同的規則,就形成了各種不同的封鎖協議。一般使用三級封鎖協議,也稱為三級加鎖協議。該協議是為了保證正確的排程事務的併發操作。三級加鎖協議是事務在對資料庫物件加鎖、解鎖時必須遵守的一種規則。下面分別介紹這三級封鎖協議。

一級封鎖協議:事務T在修改資料R之前必須先對其加X鎖,直到事務結束才釋放。事務結束包括正常結束(COMMIT)和非正常結束(ROLLBACK)。一級封鎖協議可以防止丟失修改,並保證事務T是可恢復的。使用一級封鎖協議可以解決丟失修改問題。在一級封鎖協議中,如果僅僅是讀資料不對其進行修改,是不需要加鎖的,它不能保證可重複讀和不讀“髒”資料。

二級封鎖協議:一級封鎖協議加上事務T在讀取資料R之前必須先對其加S鎖,讀完後方可釋放S鎖。二級封鎖協議除防止了丟失修改,還可以進一步防止讀“髒”資料。但在二級封鎖協議中,由於讀完資料後即可釋放S鎖,所以它不能保證可重複讀。

三級封鎖協議:一級封鎖協議加上事務T在讀取資料R之前必須先對其加S鎖,直到事務結束才釋放。三級封鎖協議除防止了丟失修改和不讀“髒”資料外,還進一步防止了不可重複讀。

 

4以下關於mysql_pconnect的說法中,正確的是    )。

A.與資料庫進行多連線 B.與mysql_connect功能相同

C.與@mysql_connect功能相同 D.與資料庫建立持久連線

參考答案:D

分析:mysql_pconnect()函式開啟一個到 MySQL 伺服器的持久連線。

mysql_pconnect()mysql_connect()非常相似,雖然只多了一個p它們有兩個主要區別:當連線的時候本函式將先嚐試尋找一個在同一個主機上用同樣的使用者名稱和密碼已經開啟的(持久)連線,如果找到,則返回此連線標識而不開啟新連線。其次,當指令碼執行完畢後到SQL伺服器的連線不會被關閉,此連線將保持開啟以備以後使用(mysql_close()不會關閉由mysql_pconnect()建立的連線)。所以,選項D正確。

 

 

【真題204PDO通過執行SQL查詢與資料庫進行互動,可以分為多種不同的策略,使用哪一種方法取決於你要做什麼操作。如果向資料庫傳送DML語句,那麼下面最合適的方式是    )。

A.使用PDO物件中的exec()方法

B.使用PDO物件中的query()方法

C.使用PDO物件中的prepare()PDOStatement物件中的execute()兩個方法結合

D.以上方式都可以

參考答案:A

分析:PDO->exec()方法主要是針對沒有結果集合返回的操作,例如INSERTUPDATE、DELETE 等操作,它返回的結果是當前操作影響的列數。所以,選項A正確。

 

5PHPmysql系列函式中常用的遍歷資料的函式是    )。

Amysql_fetch_rowmysql_fetch_assocmysql_affetced_rows

Bmysql_fecth_rowmysql_fecth_assocmysql_affetced_rows

Cmysql_fetch_rowsmysql_fetch_arraymysql_fetch_assoc

Dmysql_fecth_rowmysql_fecth_arraymysql_fecth_assoc

參考答案:D

分析:最常用的mysql系列函式常用的遍歷資料函式有mysql_fetch_row、mysql_fetch_ array和mysql_fetch_assoc等三個函式,但不存在mysql_fetch_rows

所以,本題的答案為D

 

6更改表字段名的標準語法為    )。

Aalter table 表名  add 欄位字型別[first|after]

Balter table 表名  drop  欄位[first|after]

Calter table 表名  change 原名新名新型別[first|after]

Dalter table 表名  modify  原名欄位型別[first|after]

參考答案:C

分析:修改表字段名的語法:alter table 表名change 原欄位名新欄位名型別;

修改欄位型別的語法:alter table 表名modify 欄位名型別;

增加一個欄位:alter table 表名add column 欄位名型別 not null(或default null新增一個欄位預設不為空(預設為空)

刪除一個欄位:alter table 表名drop column 新欄位名;

 

購買連結:京東購買

 

題目來自《PHP程式設計師面試筆試寶典》,裡面涵蓋了近三年了各大型企業常考的PHP面試題,針對面試題提取出來各種面試知識也涵蓋在了本書。

 

更多PHP面試筆試真題可以瀏覽:www.shuaiqi100.com  

 

更多有趣有料的PHP面試筆試資料可以關注:“琉憶程式設計庫”

或者瀏覽:www.shuaiqi100.com 獲取。

PHP程式設計師面試筆試寶典下載:https://pan.baidu.com/s/1-ES2ZI3z5Lhv-zTKFmJDSQ