有兩種方法可以使用SQL。
一種是在線交互使用,在這種情況下,SQL實際上是作為一種獨立的語言來使用的。另一種是將其嵌入高級編程語言(如C語言)中使用。前一種模式適合非計算機專業人士,后一種模式適合計算機專業人士。雖然用的方法不對,但所用語言的語法結構基本相同。
更新表名設置列名值
為什么唐你不試試嗎,
字符串列Str
字符串值Str
for(inti0iltcolumns.lengthi){
columnStr
記錄集讀回。打開("select*from聯接表",#SQL語句,)數據庫連接。1.執行SQL("插入到新表(商店標志,愿望信息)值("處理單引號(編輯框商店標志。內容)","處理單引號(客戶)"))數據庫連接。
本文將分析下一條sql語句在Mysql中的執行過程,包括sql的查詢將如何在Mysql內部流動,以及SQL語句的更新是如何完成的。
在分析之前,我先給大家展示一下MySQL的基礎架構,了解一下MySQL由哪些組件組成,可以幫助我們理解和解決這些問題。
MySQL基礎架構分析1.1MySQL基礎架構概述
下圖是MySQL的簡要架構圖,從中可以清楚地看到用戶的SQL語句在MySQL內部執行。
讓下面我們簡單介紹一下下圖中涉及到的一些組件的基本功能,幫助你理解這個圖,這些組件的功能將在1.2節詳細介紹。
連接器:認證與權限相關(登錄MySQL時)。查詢緩存在執行一條查詢語句的時候,會先查詢緩存(MySQL版以后去掉了,因為這個功能不是很實用)。如果解析器不;如果沒有命中緩存,SQL語句將通過解析器。說白了,解析器首先要看你的SQL語句是干什么用的,然后檢查你的SQL語句的語法是否正確。優化器:按照MySQL認為最好的方案實現。執行器執行該語句,然后從存儲引擎返回數據。
簡單來說,MySQL主要分為服務器層和存儲引擎層:
服務器層:主要包括連接器、查詢緩存、分析器、優化器、執行器等。跨存儲引擎的所有功能都在這一層實現,比如存儲過程、觸發器、視圖、函數等。還有一個通用的日志模塊,binglog日志模塊。存儲引擎:主要負責數據存儲和讀取,采用可替換插件架構,支持InnoDB、MyISAM、Memory等多種存儲引擎,其中InnoDB引擎自帶日志模塊redolog模塊。現在最常用的存儲引擎是InnoDB,從MySQL5.5.5版開始就被視為默認的存儲引擎。1.2服務器層基本組件介紹
1)連接器
連接器主要涉及與身份驗證和權限相關的功能,就像高級門衛一樣。
它主要負責用戶登錄數據庫和用戶認證。;的身份,包括檢查賬戶密碼、權限等操作。如果用戶的帳戶密碼已過,連接器將在權限表中查找該用戶的所有權限,然后該連接中權限的邏輯判斷將取決于此時讀取的權限數據,也就是說,只要連接持續打開,即使管理員修改了用戶的權限。
2)查詢緩存(MySQL版后移除)
查詢緩存主要用于緩存我們執行的SELECT語句以及該語句的結果集。
連接建立后,執行查詢語句時,會先查詢緩存。Mysql會先檢查這條sql是否已經執行,并以Key-Value的形式緩存在內存中,其中Key是查詢預期,Value是結果集。如果命中緩存鍵,將直接返回給客戶端。如果未命中,則執行后續操作,完成后緩存結果,方便下次調用。當然,當實際執行緩存查詢時,用戶的權限,以及該表是否有查詢條件。
不建議對MySQL查詢使用緩存,因為在實際的業務場景中,查詢緩存失效可能會非常頻繁。如果更新一個表,該表上的所有查詢緩存都將被清空。對于不經常更新的數據,仍然可以使用緩存。
因此,在大多數情況下,我們一般不不建議使用查詢緩存。
MySQL版之后,刪除了緩存功能,官方認為實際應用場景中該功能較少,所以干脆刪除了。
3)分析儀
如果MySQL不t命中緩存,就會進入解析器,解析器主要用來分析SQL語句是干什么用的,解析器。它還將分為幾個步驟:
第一步,詞法分析,一條SQL語句由多個字符串組成。首先,需要提取關鍵字,如select、要查詢的表、字段名、查詢條件等。完成這些操作后,你將進入第二步。
第二步,語法分析,主要是判斷你輸入的sql是否正確,是否符合MySQL的語法。
完成這兩步,MySQL就準備開始執行了,但是怎么執行,怎么執行才是最好的結果?這時候優化器就需要發揮作用了。
4)優化器
優化器的作用是實現它認為的最優執行方案(有時可能不是最優的,本文涉及到這部分知識的深入講解),比如使用多個索引時如何選擇索引,查詢多個表時如何選擇關聯順序等等。
可以說優化器之后,可以說如何執行這個語句已經決定了。
5)致動器
當執行方案選定后,MySQL就準備開始執行了。首先,在執行之前,它會檢查用戶是否有權限。否則,它將返回一條錯誤消息。如果有權限,它會調用引擎的接口,返回接口執行的結果。
兩句話分析2.1查詢語句
說到這里,一條sql語句到底是怎么執行的呢?其實我們的sql可以分為兩種,一種是查詢,一種是更新(添加、更新、刪除)。讓讓我們首先分析查詢語句。聲明如下:
Select*fromtb_studentAwhere和張三
結合上面的描述,我們分析一下這條語句的執行過程:
首先,檢查語句是否有權限。如果沒有,直接返回錯誤信息。如果有,在Mysql8.0版本之前,先查詢緩存,以此sql語句為關鍵字查詢內存中是否有結果。如果有直接緩存,如果沒有,執行下一步。由分析器進行詞法分析,提取sql語句的關鍵元素,比如提取上面的語句是queryselect,提取要查詢的表名為tb_student,需要查詢所有列,查詢條件為該表的id1。然后判斷這條sql語句是否存在語法錯誤,比如關鍵詞是否正確等。如果沒有問題,執行下一步。接下來,優化器確定執行方案。上面的sql語句可以有兩種執行方案:
A.首先檢查名為"張三"在學生表中,然后判斷年齡是否為18歲。首先找出18歲的學生,然后查詢名字是"張三"。
然后優化器根據自己的優化算法選擇最高效的方案(優化器認為有時候不一定是最好的)。然后確認執行計劃后,就準備開始執行了。是的。
檢查權限。如果沒有權限,將返回一條錯誤消息。如果有權限,會調用數據庫引擎接口,返回引擎的執行結果。
2.2更新聲明
以上是查詢sql的一個執行過程,所以讓讓我們看看update語句是如何執行的。sql語句如下所示:
更新tb_學生一集張三在哪里
讓s修改張三年代。實際數據庫中肯定不會設置年齡字段,否則由技術負責人鍵入。其實這個語句基本會遵循上一次查詢的流程,但是在進行更新的時候必須記錄日志,這就要引入日志模塊。MySQL和的日志模塊binlog(歸檔日志)可以被所有的存儲引擎使用,我們常用的InnoDB引擎也自帶了日志模塊redolog(重做日志),所以我們將在InnoDB模式下討論這條語句的執行過程。流程如下:
先查詢張三的數據。如果有緩存,也會使用它。然后獲取查詢語句,把年齡改成19,然后調用引擎的API接口寫這一行數據。InnoDB引擎將數據保存在內存中,并記錄重做日志。此時重做日志進入準備狀態,然后告訴執行人執行完成,可以隨時提交。收到通知后,執行器記錄binlog,然后調用引擎接口,提交重做日志作為提交狀態。更新完成。這里肯定有同學會問,為什么要用兩個日志模塊,而不是一個日志模塊?
這是因為MySQL沒有t一開始用InnoDBengine(InnoDBengine是其他公司作為插件插入MySQL的),MySQL的引擎是MyISAM,但是我們知道重做日志是InnoDB引擎獨有的,其他存儲引擎都沒有。這樣一來,就不會有崩潰安全的能力(即使數據庫非正常重啟,之前提交的記錄也不會丟失),binlog日志只能用于存檔。
It不是那樣的。;不可能只使用一個日志模塊,但是InnoDB引擎支持通過重做日志處理事務。然后,有些同學會問,我用兩個日志模塊,但是可以不會這么復雜吧?為什么重做日志引入了準備提交前狀態?這里我們用歸謬法來解釋為什么要這樣做。
先寫重做日志直接提交,再寫binlog。假設寫完重做日志后,機器掛起,沒有寫binlog日志,那么機器重啟后,這臺機器會通過重做日志來恢復數據,但是bingog此時并沒有記錄數據。以后備份機器的時候,這塊數據會丟失,主從同步也會丟失這塊數據。首先寫binlog,然后重做log。假設寫完binlog后,機器異常重啟。因為沒有重做日志,所以這臺機器無法恢復這個記錄,但是binlog有一個記錄。然后和上面一樣,會出現數據不一致的情況。如果重做日志分兩個階段提交,會有所不同。編寫binglog后,提交Redlog會防止上述問題,從而保證數據的一致性。那么問題來了。是否存在極端情況?假設重做日志處于提交前狀態,binglog已經完成。如果此時出現異常重啟會怎么樣?這取決于MySQL的處理機制,MySQL的處理過程如下:
判斷重做日志是否完整,如果完整,立即提交。如果重做日志只是預提交,而不是提交狀態,此時會判斷binlog是否完整,如果完整就提交重做日志,如果不完整就回滾事務。這就解決了數據一致性的問題。
第三,MySQL主要分為服務器層和引擎層。服務器層主要包括連接器、查詢緩存、分析器、優化器和執行器,還有一個日志模塊(binlog),所有執行引擎都可以共享,redolog只有InnoDB才有。引擎層是插件,主要包括MyISAM、InnoDB、Memory等等。查詢語句的執行流程如下:權限檢查(如果命中緩存)-查詢緩存-分析器-優化器-權限檢查-執行器。引擎更新語句的執行流程如下:分析器-權限檢查-執行器。