php大數(shù)據(jù)高并發(fā)處理 當(dāng)數(shù)據(jù)庫(kù)扼住系統(tǒng)性能咽喉,直接分庫(kù)分表能解決嗎?
當(dāng)數(shù)據(jù)庫(kù)扼住系統(tǒng)性能咽喉,直接分庫(kù)分表能解決嗎?子庫(kù)和子表是一種相對(duì)落后的優(yōu)化方法,因?yàn)槌杀鞠鄬?duì)較高。遇到數(shù)據(jù)庫(kù)瓶頸:-首先考慮SQL優(yōu)化,這是最簡(jiǎn)單的方法。對(duì)現(xiàn)有系統(tǒng)沒(méi)有影響。-第二個(gè)是考慮數(shù)據(jù)庫(kù)讀
當(dāng)數(shù)據(jù)庫(kù)扼住系統(tǒng)性能咽喉,直接分庫(kù)分表能解決嗎?
子庫(kù)和子表是一種相對(duì)落后的優(yōu)化方法,因?yàn)槌杀鞠鄬?duì)較高。
遇到數(shù)據(jù)庫(kù)瓶頸:
-首先考慮SQL優(yōu)化,這是最簡(jiǎn)單的方法。對(duì)現(xiàn)有系統(tǒng)沒(méi)有影響。
-第二個(gè)是考慮數(shù)據(jù)庫(kù)讀寫(xiě)分離,這也是一個(gè)相對(duì)簡(jiǎn)單的方法。在數(shù)據(jù)庫(kù)級(jí)配置中,系統(tǒng)級(jí)只需要調(diào)整獲取數(shù)據(jù)庫(kù)連接的邏輯即可。讀取數(shù)據(jù)時(shí),可以同時(shí)獲得主庫(kù)和從庫(kù)連接。寫(xiě)入數(shù)據(jù)時(shí),僅獲取主庫(kù)連接。
-考慮添加緩存層。數(shù)據(jù)緩存在緩存中,再次訪問(wèn)時(shí)不再?gòu)臄?shù)據(jù)庫(kù)檢索。通常,緩存層對(duì)系統(tǒng)是透明的,對(duì)系統(tǒng)本身沒(méi)有影響。但是,cache的引入也引入了相應(yīng)的需要考慮的問(wèn)題,如雪崩、命中率、分布式cache等]-還有一種非技術(shù)手段,就是改變需求。性能問(wèn)題的原因是否不合理?還是要求太復(fù)雜?需求可以簡(jiǎn)化嗎?這種方法對(duì)系統(tǒng)的影響相對(duì)較小。
-最后,考慮子數(shù)據(jù)庫(kù)和子表。優(yōu)先考慮子數(shù)據(jù)庫(kù),因?yàn)樗茸颖砗?jiǎn)單。將相應(yīng)的表移動(dòng)到新的數(shù)據(jù)庫(kù)中,并調(diào)整系統(tǒng)的邏輯以獲得數(shù)據(jù)庫(kù)連接。在這里,我們需要考慮移動(dòng)哪些表。在提高性能的前提下,我們首先嘗試避免分布式事務(wù)。
-最后,考慮子表。子表的主要原因是單個(gè)表中的數(shù)據(jù)量很大。子表分為縱斷面和橫斷面。垂直剪切是按列剪切的,例如用戶(hù)表。常用信息為基本信息表,其他信息為明細(xì)表。橫切是按行切割。例如,一個(gè)有1億數(shù)據(jù)的表被分成10個(gè)有1000萬(wàn)數(shù)據(jù)的表。這涉及到數(shù)據(jù)應(yīng)該存儲(chǔ)在哪個(gè)表中或從哪個(gè)表中獲取。在表被劃分之后,可以對(duì)數(shù)據(jù)庫(kù)進(jìn)行進(jìn)一步的優(yōu)化。
-如果涉及分布式事務(wù),應(yīng)考慮如何保證分布式事務(wù)。理論上,2個(gè),3個(gè),帕克斯,帽子,底座。相應(yīng)中間件的使用。
系統(tǒng)的設(shè)計(jì)和優(yōu)化不是模仿的問(wèn)題,而是需要根據(jù)實(shí)際場(chǎng)景進(jìn)行處理。
mysql表數(shù)據(jù)量太大,達(dá)到了1億多條數(shù)據(jù),除了分庫(kù)分表之外,還有沒(méi)有其他的解決方式?
在正常配置下,MySQL只能承載2000萬(wàn)數(shù)據(jù)(同時(shí)讀寫(xiě),表中有大文本字段,單服務(wù)器)?,F(xiàn)在已經(jīng)超過(guò)1億,而且還在增加,建議按以下方式處理:
1子表。它可以按時(shí)間或一定的規(guī)則進(jìn)行拆分,以便盡可能地查詢(xún)子表中的數(shù)據(jù)庫(kù)。這是最有效的方法。特別是寫(xiě),放入一個(gè)新表,并定期同步。如果記錄不斷更新,最好將寫(xiě)入的數(shù)據(jù)放在redis中,并定期同步表3的大文本字段,將它們分隔成一個(gè)新的獨(dú)立表。對(duì)于較大的文本字段,可以使用NoSQL數(shù)據(jù)庫(kù)
4優(yōu)化體系結(jié)構(gòu),或者優(yōu)化SQL查詢(xún),避免聯(lián)合表查詢(xún),盡量不要使用count(*)、in、recursion等性能消耗語(yǔ)句
5使用內(nèi)存緩存,或者在前端讀取時(shí)增加緩存數(shù)據(jù)庫(kù)。重復(fù)讀取時(shí),直接從緩存中讀取。
以上是一種低成本的管理方法,基本上幾個(gè)服務(wù)器就可以做到,但是管理起來(lái)有點(diǎn)麻煩。
當(dāng)然,如果總體數(shù)據(jù)量特別大,我不關(guān)心投資成本。讓我們使用集群和tidb
我將從子數(shù)據(jù)庫(kù)和子表存在的問(wèn)題以及如何做到這一點(diǎn)來(lái)回答這個(gè)問(wèn)題。。
沒(méi)有辦法避免這個(gè)問(wèn)題,通常拆分SQL,使用多個(gè)查詢(xún),然后使用結(jié)果分別檢查結(jié)果
!我們可以使用TCC編程模型來(lái)確保兩個(gè)事務(wù)可以正確提交,但這種代碼入侵方式相對(duì)較重!您還可以使用基于消息的數(shù)據(jù)一致性保證
!1. 使用多線程分別查詢(xún)多個(gè)節(jié)點(diǎn),然后匯總
MySQL分庫(kù)分表之后,id主鍵如何處理?
由于數(shù)據(jù)庫(kù)中的數(shù)據(jù)量不一定是可控的,沒(méi)有子數(shù)據(jù)庫(kù)和子表,隨著時(shí)間和業(yè)務(wù)的發(fā)展,數(shù)據(jù)庫(kù)中的表數(shù)會(huì)越來(lái)越多,表中的數(shù)據(jù)量也會(huì)越來(lái)越大。相應(yīng)地,數(shù)據(jù)操作、添加、刪除和修改的成本也將越來(lái)越大。另外,由于無(wú)法進(jìn)行分布式部署,服務(wù)器的資源(CP)會(huì)減少(U盤(pán)、內(nèi)存、IO等)有限,最終數(shù)據(jù)庫(kù)所能承載的數(shù)據(jù)量,數(shù)據(jù)處理能力會(huì)遇到瓶頸。
數(shù)據(jù)庫(kù)為什么要分庫(kù)分表?
以MySQL為列:
1:要支持高并發(fā)系統(tǒng),必須涉及事務(wù),所以數(shù)據(jù)庫(kù)引擎必須選擇InnoDB。InnoDB支持事務(wù),事務(wù)級(jí)別取決于業(yè)務(wù)。如果業(yè)務(wù)數(shù)據(jù)一致性要求非常高,事務(wù)將開(kāi)啟序列化級(jí)別,這將完全隔離事務(wù),但會(huì)導(dǎo)致對(duì)鎖資源的競(jìng)爭(zhēng)加劇。MySQL的性能在一定程度上降低了。
2:數(shù)據(jù)庫(kù)分為主數(shù)據(jù)庫(kù)和從數(shù)據(jù)庫(kù)。主數(shù)據(jù)庫(kù)負(fù)責(zé)寫(xiě)入數(shù)據(jù),集群數(shù)據(jù)庫(kù)負(fù)責(zé)讀取數(shù)據(jù)。注意主從數(shù)據(jù)庫(kù)的數(shù)據(jù)一致性。
3:冷熱數(shù)據(jù)分離,美團(tuán)、饑餓部分設(shè)計(jì)采用冷熱數(shù)據(jù)分離。以訂單為例,出庫(kù)單的主要業(yè)務(wù)場(chǎng)景是查詢(xún)。數(shù)據(jù)查詢(xún)?cè)较蚯?,概率越低。這是冷數(shù)據(jù)。正在交易的訂單是熱點(diǎn)數(shù)據(jù),需要隨時(shí)查詢(xún)和更新。冷數(shù)據(jù)可以放入redis緩存。這將提高查詢(xún)效率。
4:數(shù)據(jù)表設(shè)計(jì),充分利用索引查詢(xún)。businesssql避免返回?zé)o用的行和列,禁止使用select*query,在查詢(xún)時(shí)增加限制,并盡可能返回滿(mǎn)足要求的行。對(duì)于復(fù)雜的SQL,請(qǐng)考慮拆分SQL。拆分SQL有一個(gè)優(yōu)點(diǎn)。對(duì)于重復(fù)查詢(xún)SQL,將第二次查詢(xún)放入MySQL緩沖區(qū),避免重復(fù)磁盤(pán)操作,提高訪問(wèn)性能。
5:子數(shù)據(jù)庫(kù)和子表。例如,業(yè)務(wù)數(shù)據(jù)按月份分類(lèi)。在一定程度上,增加、刪除、修改和檢查的壓力將得到緩解。
希望對(duì)您有所幫助。謝謝您。