技術思考框架:抽象-思路-考量-優化-細節

如何思考問題與思考具體問題同等重要。html


引子

如何思考一個技術問題?如何高效地理解某個技術 ?如何快速學習一個新的技術點 ? 這都須要一個好的技術思考框架。缺少思考框架,知識和技術就變成一堆細節的堆砌,缺少關聯,難以理解和記憶,也就難以掌握和應用。程序員

本文來探索一種好的技術思考框架。

redis

技術思考框架

在多年的開發生涯及閱讀和理解源碼的過程當中,我逐漸造成了一種我的以爲比較可行的技術思考框架:「抽象-思路-考量-優化-細節」 五步曲。算法

  • 抽象:給用戶提供怎樣的抽象。
  • 思路:如何去實現它,基本的依據、結構、算法與實現;
  • 考量:工程應用上須要考慮哪些因素,作到安全可靠高質量;
  • 優化:在考量的基礎上,從多個層面去優化和完善;
  • 細節:在優化的基礎上,打磨細節,精益求精。

抽象數據庫

抽象很是重要。一個典型的例子是刪除操做。刪除操做提供的是「用戶不可見」的抽象。能夠採用兩種思路:緩存

  • 物理刪除:直接抹掉數據的全部痕跡,再也找不到了。
  • 邏輯刪除:沒有抹掉數據,只是提供了一個標記,在用戶查詢時根據標記過濾掉這個數據。邏輯刪除爲數據恢復提供了前提。

能夠看到,提供良好的抽象,而不是直覺上按照用戶的要求去作,每每會帶來更靈活的設計空間。安全

抽象最好能用一句話歸納。好比,文字編輯器(UI界面)提供的是「所見即所得」的抽象;理財產品提供的是符合利率模型的計算抽象。

服務器

思路網絡

思路是如何去基本實現的問題。在問題討論初期,提出儘量多種思路,應對不一樣的場景。好比排序,就有插入排序、冒泡排序、快速排序、合併排序、希爾排序、桶排序、外部排序、多關鍵字排序等。不一樣的排序具備不一樣的特性,在不一樣的場景下使用。挖掘儘量多的思路,有助於拓展對問題的思考。好的思路是成功的一半。架構


考量和優化

考量和優化每每須要豐富的開發實踐經驗。知道往哪一個方向使力,如何使力,須要解決什麼技術難點等。

細節

在掌握宏觀視角後,細節的打磨尤其重要。細節處理不當,可能會致使總體工做前功盡棄。程序員或工程師的一大特質,便是體如今細節的考慮和思惟的縝密上。

考慮各類錯誤和異常,考慮依賴服務、服務器、網絡等的不可靠,是作好細節工做的必要前提。


Redis 持久化示例

抽象

持久化,便是給用戶提供一個「數據保存了、即便掉電或重啓也能從某處找回數據」的抽象。

思路

如何實現 Redis 持久化 ? 持久化就是將 Redis 內存數據庫的數據集狀態保存在某個磁盤文件裏。能夠基於兩種思路:

  • 基於數據。直接將數據存儲在(壓縮過的)二進制磁盤文件裏,恢復的時候讀取數據文件便可,好比 RDB 機制。
  • 基於命令。將 Redis 命令存儲在磁盤文件裏,恢復的時候執行文件裏的命令便可,好比 AOF 機制。

考量

實際工程中要考慮什麼因素呢 ?

  • 避免數據丟失: 持久化過程若被中斷,已持久化的數據不丟失;持久化期間,盡力保證不丟數據,或者丟數據在可接受範圍內。
  • 性能:持久化能更高效地完成。
  • 穩定性:持久化的過程當中,不能影響到 Redis 的正常服務。
  • 存儲空間: 持久化文件佔用的空間應當儘量少。
  • 同步: 新增的數據及已持久化後的數據更新也要持久化。
  • 恢復速度: 服務器啓動或緊急狀況須要恢復數據狀態時,應當儘量高效、便捷、減小沒必要要的坑。
  • 可讀性: 持久化文件可讀,可以爲人所理解;可解析,可以爲機器高效讀取。
  • 可追溯: 當數據出現不一致時,或者不對勁時,能夠經過追溯持久化文件來定位緣由。

優化

針對上述考量因素,可制定相應優化措施:

  • 異步:新起子進程在後臺去作持久化的事情,而不佔用服務進程,不阻塞服務的正常運行。好比 BGSAVE 命令。
  • 緩衝區:在持久化的過程當中,若是新增命令都直接寫到持久化文件,勢必會影響正常服務的性能。所以經常使用作法是,在持久化開啓以後,新增的命令或數據會先寫入到緩衝區,而後以某種策略來同步到持久化文件裏。能夠配置相應的策略,來實現服務性能和避免數據丟失的權衡。
  • AOF 重寫:將多條命令重寫爲一條命令,從而減小可執行命令數,減小 AOF 文件體積,提高恢復速度。讀取鍵值的數據庫當前數據狀態,生成一條新的命令寫入 AOF。爲何不直接寫入鍵值呢 ? 由於要知足可追溯的需求。 AOF 重寫後的文件用於恢復數據庫狀態, 而 AOF 的原文件能夠考慮歸檔,便於在急需的時候定位緣由。
  • 二進制與文本文件:二進制文件機器解析更高效,兼容性更強,但人類可讀性差; 文本文件可讀,解析時可能會有坑,須要經過統一協議來避免。

細節

RDB 機制的細節:

  • SAVE 會阻塞主服務進程,通常用於業務量低峯期; BGSAVE 會建立子進程去作持久化工做,不會阻塞。
  • BGSAVE 執行期間,新的 SAVE, BGSAVE 會被拒絕;BGREWRITEOF 會在 BGSAVE 完成以後執行。避免併發操做磁盤引發性能波動或下降。
  • save 命令能夠配置多久執行一次 BGSAVE ; 能夠配置多個 save 命令,任一知足都會執行 BGSAVE(或關係)。默認 [900, 1], [300, 10], [60, 10000]。實際配置值須要根據業務狀態調優。
  • save 的實現:[ dirty & lastsave ] 。dirty 記錄了距離最近一次建立 RDB 文件快照以後的數據庫狀態修改次數; lastsave 記錄了最近一次建立 RDB 文件快照的時間戳。 每隔 100ms 都會檢測一次,save 條件是否知足。

AOF 機制的細節:

  • appendfsync: 同步持久化文件的策略。 always 每次寫緩衝區都同步到持久化文件,不會丟數據,但性能會受影響; everysec 每秒同步,可能會丟失最近 1s 內的數據,性能能夠; no 性能最優,但會有較大的丟數據風險。 默認策略是 everysec。
  • AOF 重寫集合: 爲了不緩衝區溢出,重寫集合時,可根據 REDIS_AOF_REWRITE_ITEMS_PER_CMD 配置,一個數量爲 N 的很大的集合,會拆分爲 ( N / REDIS_AOF_REWRITE_ITEMS_PER_CMD +1 ) 個重寫命令。
  • 應用啓動時,默認加載 RDB 文件;恢復數據庫狀態時,優先使用 AOF 機制,若 AOF 關閉,則採用 RDB 機制。

高併發處理

再來思考一個問題:如何應對高併發流量呢?這是互聯網應用必然面對的一個重大挑戰。

抽象

高併發流量問題,本質是資源有限的問題。便是用有限的資源去應對不肯定性的巨大流量的矛盾。假設有足夠的資源,加以適當的水平擴展,高併發也不算什麼事。難在用現有的架構、現有的資源來應對巨大流量,並且不管預留多少資源,老是不必定能承載將來可能降臨的超過負載能力的峯值流量。

思路

既然是資源有限的問題,那麼思路也就三條:

  • 用更少資源作更多的事情,提高服務能力,提高 QPS;
  • 加資源;
  • 限流。

考量

  • 穩定性:高併發流量下,首先要考慮的是保證應用不會被超出負荷能力的流量壓垮;
  • 保障正常服務:對於負荷範圍內的正常流量,可以正常服務,正常響應,正常的服務體驗。不會由於高負荷致使服務處理能力變差,連正常流量的請求都沒法有效應對,或者用戶體驗變差。

優化

提高服務能力:

  • 用好緩存:能夠提高 QPS ,但依然沒法阻擋高併發流量;

  • 熔斷降級:高併發狀況下,自動熔斷次要的鏈路,提高 QPS;

  • 讀寫分離: 將高併發流量中的讀寫部分分開,讀寫分別處理;

  • 分庫分表: 提高 DB 的併發處理能力;

  • 彈性擴容:要求應用可以彈性部署和啓動。在大促活動以前,能夠提早擴容。目前難以應對瞬時峯值。


加資源(在不一樣層面):

  • 加資源的同時作好負載均衡(分流做用)。經過負載均衡進行分流,一部分流量直接進入服務器,一部分流量走消息隊列再走服務。負載均衡可採用七層的 ngnix 和 四層的 LVS 或 F5。負載均衡能抗住大流量;

  • 多機房 + CDN:多機房 + CDN + 負載均衡,分別抗住來自不一樣地區的大流量。


限流: 仍然沒法承載的流量,採用限流處理掉。


細節

  • 資源消耗:一個請求會消耗多少資源?CPU、內存、磁盤空間、網絡鏈接及帶寬、DB 鏈接等。
  • 如何將緩存用到極致?須要對業務數據有敏感度,採起適當的策略,不斷調優,密切注意監控;
  • 熔斷降級的策略?熔斷值的設定與調優;
  • 如何部署負載均衡和多機房?須要網絡運維能力;
  • 在哪些層面限流?限流值如何肯定?
  • 讀庫的複製時延如何解決?
  • 分庫分表的切換過程當中的新數據如何作到不丟失?

高併發其實是一個實操性很強的事情。沒有通過高併發流量的洗禮,只談理論終究仍是隔着點。不過,至少要了解相關理論,才能在實戰中積極運用並積累經驗。

技術體系結構

從上述示例能夠看到:

  • 抽象能夠提供更靈活的設計空間和思路。
  • 考量因素每每會決定優化的大方向。
  • 優化每每須要通盤綜合考慮,且要有實操經驗。
  • 細節在優化的過程當中產生和解決。

抽象、考量和優化,須要建基於一個比較豐富的技術體系結構。爲何考慮這個問題而不考慮那個問題?爲何選擇優化這個而不是優化那個?技術知識點是很是繁雜瑣碎的,缺少技術體系結構來有效地組織起來,極可能會腦中一團漿糊,分不清東南西北,對着各類新技術望洋興嘆。

所以,打造一個適合本身的技術體系結構很是重要,這也是將來的核心競爭力之一。好比 「互聯網應用服務端的經常使用技術思想與機制綱要」 便是圍繞「數據處理」這個中心主題,從靈活性、高性能、高可用、高可靠、一致性、海量、安全、自動化、智能化八個方面打造的技術體系結構。這個體系結構幾乎能夠容納各類技術流派和技術優化手段。

小結

本文探討了一種技術思考框架:基於技術體系結構的「抽象-思路-考量-優化-細節」五步曲。

合適的抽象會帶來更靈活的設計空間和思路,而考量則會決定優化的大方向,在優化的過程當中解決細節問題。在學習技術的過程當中,要逐步打造適合本身的技術體系結構,不斷充實這個體系結構,從而具有更強的系統思考力和技術吸取力。

參考資料

相關文章
相關標籤/搜索