面試基礎
-
談談一致hash算法?
按照hash算法來將對應的key哈希到一個具有232次方個桶的空間中,即0~(232)-1的數字空間。將這些數字頭尾相連,想象成一個閉合的環形。如果集群中加入新的機器,采用它的IP或者唯一別名計算哈希值,也映射到環中。新增key值以順時針的方向,存儲到離自己最近的機器中。
參考:https://blog.csdn.net/cb_lcl/article/details/81448570 -
說說樂觀鎖和悲觀鎖?
樂觀鎖:假設每次操作別人不會修改數據,當更新的時候根據版本號判斷數據是否變化,適合讀多寫少的場景。
悲觀鎖:假設每次操作別人會修改數據,操作前先加上鎖,后面的操作被阻塞,直至操作完畢釋放鎖。 -
說說對MySQL的了解,和Oracle的區別?
MySQL是一種開源關系型數據庫,支持標准的SQL語言,支持多種數據引擎、事務、主從配置。廣泛用於中小型互聯網公司。與Oracle的區別:- 定位:Oracle是大型數據庫,Mysql是中小型數據庫。Oracle是付費的商業數據庫,MySQL是免費開源數據庫。
- 性能:Oracle有更強的並發性能,更豐富的數據管理工具。
-
說說事務四大特性?
- A(原子性):事務是一個不可分割的工作單位,事務中的操作要么都發生,要么都不發生。
- C(一致性):事務前后數據的完整性必須保持一致,符合邏輯運算。
- I(隔離性):多個用戶並發訪問數據庫時,數據庫為每一個用戶開啟的事務,不能被其他事務的操作數據所干擾,多個並發事務之間要相互隔離。
- D(持久性):事務一旦被提交,它對數據的改變是永久性的,即使數據庫發生故障也不應該對其有影響。
-
說說事務的兩階段提交機制?
分布式事務有兩個角色:事務協調者和事務參與者,兩階段提交協議是協調所有事務參與者決定提交或取消(回滾)的方式。- prepare階段:協調者詢問各個參與者是否正常執行,通知事務參與者准備提交或取消事務,然后進入表決過程。在表決過程中,參與者將告知協調者自己的決策:同意(事務參與者本地作業執行成功)或取消(本地作業執行故障)。
- commit階段:協調者利用准備階段的結果進行決策,當且僅當所有的參與者同意提交事務協調者才通知所有的參與者提交事務,否則協調者將通知所有的參與者取消事務
-
說說數據庫的索引原理,聚簇索引和非聚簇索引?
索引本質上是一種數據結構(存儲結構+算法),目的是為了加快數據檢索的速度。
https://www.jianshu.com/p/e1dce41a6b2b -
舉例說一下索引的使用場景?
- 主鍵索引:給表設置主鍵,這個表就擁有主鍵索引。
- 普通索引:增加某個字段的索引,比如用戶表根據用戶名查詢。
- 復合索引:多個字段增加索引,遵循最左原則,比如創建索引(col1 + col2 + col3),相當於創建了(col1)、(col1,col2)、(col,col2,col3)三個索引。
-
說說數據庫當前讀和快照讀?
- 快照讀:簡單的
select
是快照讀。 - 當前讀:
select for update,insert,update,delete
是當前讀。 - 原 理:在repeat read級別下,快照讀是通過MVVC(多版本控制)和undo log來實現的,當前讀是通過加record lock(記錄鎖)和gap lock(間隙鎖)來實現的。
- 快照讀:簡單的
-
HashTable & HashMap & ConcurrentHashMap區別及優缺點?
相比HashMap,HashTable和ConcurrentHashMap都是線程安全的。HashTable在put和get操作上加上synchronize實現同步控制。而ConcurrentHashMap通過分段鎖,避免鎖住全哈希表,提高了同步效率。
參考:https://www.cnblogs.com/sunshinekevin/p/10625516.html -
Synchronize是可重入鎖嗎,實現原理?
可重入鎖,
參考:https://blog.csdn.net/zc19921215/article/details/84780335 -
說說JVM類加載過程?
加載(Loading)、驗證(Verification)、准備(Preparation)、解析(Resolution)、初始化(Initialization)、使用(Using)和卸載(Unloading)7個階段。
裝載:查找和導入Class文件。
鏈接:把類的二進制數據合並到JRE中。
校驗:檢查載入Class文件數據的正確性。
准備:給類的靜態變量分配存儲空間。
解析:將符號引用轉成直接引用。
初始化:對類的靜態變量,靜態代碼塊執行初始化操作。 -
JVM雙親委派機制及使用原因?
- 機制:將當前類的加載任務轉給它的父類加載器,如果它的父類還有父類,就繼續向上傳遞,如果父類加載器加載失敗則自己加載。
- 意義:避免重復加載以及核心類的修改風險。
-
說說Java的GC機制,有哪幾種GC算法?
C/C++申請內存時都要malloc進行系統調用,使用完畢后通過free釋放內存。Java虛擬機是先一次性分配一塊較大的空間,然后在該空間上自動進行分配和釋放,一般情況下程序員不需要手動操作。GC機制就是解決自動回收,面臨三個問題:怎么確定垃圾,怎么回收垃圾,什么時候回收。-
怎么確定垃圾:
- 引用計數算法:給對象添加一個引用計數器,當有一個地方引用它時,計數器值就加1;當引用失效時,計數器值就減1;任何時刻計數器為0的對象就是死亡的。引用計數算法很簡單,判斷效率也很高,但是JVM沒有選用它來管理內存。原因是什么呢?主要是因為它很難解決循環引用的問題。
- 可達性分析算法:通過一系列名為GC Roots的對象作為起始點,從這些節點開始向下搜索,搜索所有走過的路徑稱為“引用鏈”,當一個對象到GC Roots沒有任何引用鏈相連時,則證明此對象是不可用的。
-
怎么回收垃圾:
- 分代收集法:它根據對象的生存周期,將堆分為新生代和老年代。在新生代中,由於對象生存期短,每次回收都會有大量對象死去,那么這時就采用復制算法。老年代里的對象存活率較高,沒有額外的空間進行分配擔保,所以可以使用標記整理或者標記清除。
- 標記清除法:將需要回收的對象標記出來,批量清除。缺點是效率低,產生碎片。
- 標記整理法:將需要回收的對象標記出來,移動到一端再清除,避免了碎片的產生。
- 復制法:將新生代內存划分為8:1:1三部分,較大的叫Eden區,其余是兩塊較小的Survior區。每次都會優先使用Eden區,若Eden區滿,就將對象復制到第二塊內存區上,然后清除Eden區,如果此時存活的對象太多,以至於Survivor不夠時,會將這些對象通過分配擔保機制復制到老年代中。
-
什么時候回收:
GC有兩種類型:Scavenge GC和Full GC。- Scavenge GC:一般情況下,當新對象生成,並且在Eden申請空間失敗時,就會觸發Scavenge GC,對Eden區域進行GC,清除非存活對象,並且把尚且存活的對象移動到Survivor區。然后整理Survivor的兩個區。這種方式的GC是對年輕代的Eden區進行,不會影響到年老代。因為大部分對象都是從Eden區開始的,同時Eden區不會分配的很大,所以Eden區的GC會頻繁進行。因而,一般在這里需要使用速度快、效率高的算法,使Eden去能盡快空閑出來。
- Full GC:對整個堆進行整理,包括Young、Tenured和Perm。Full GC因為需要對整個堆進行回收,所以比Scavenge GC要慢,因此應該盡可能減少Full GC的次數。在對JVM調優的過程中,很大一部分工作就是對於Full GC的調節。有如下原因可能導致Full GC:
- 年老代(Tenured)被寫滿
- 持久代(Perm)被寫
- System.gc()被顯示調用
- 上一次GC之后Heap的各域分配策略動態變化
參考:https://blog.csdn.net/u011983531/article/details/79479972
-
-
說說線程池的核心參數和基本原理、調優策略?
- 核心參數:
corePoolSize:線程池中核心線程數量。
maximumPoolSize:線程池同時允許存在的最大線程數量。
RejectedExecutionHandler:拒絕服務策略。
keepAliveTime:當線程池中工作線程數大於corePoolSize,並且線程空閑時間超過keepAliveTime,這些線程將被終止。 - 基本原理:
參考:https://www.jianshu.com/p/896b8e18501b - 調優策略
要想合理的配置線程池,就必須首先分析任務特性,從以下幾個角度來進行分析:
任務的性質:CPU密集型任務,IO密集型任務和混合型任務。
任務的優先級:高,中和低。
任務的執行時間:長,中和短。
任務的依賴性:是否依賴其他系統資源,如數據庫連接。
參考:https://blog.csdn.net/chenpeng19910926/article/details/78142187
- 核心參數:
-
Collections.sort底層排序方式?排序穩定性?具體場景的排序策略?
Arrays.sort和Collections.sort最終使用的都是TimSort的算法。
Timsort的核心過程:
1、數組個數小於32的情況使用二分插入排序。
2、數組大於32時,先算出一個合適的大小,在將輸入按其升序和降序特點進行了分區。排序的輸入的單位不是一個個單獨的數字,而是一個個的塊-分區。其中每一個分區叫一個run。針對這些 run 序列,每次拿一個run出來按規則進行合並。每次合並會將兩個run合並成一個 run。合並的結果保存到棧中。合並直到消耗掉所有的run,這時將棧上剩余的 run合並到只剩一個 run 為止。這時這個僅剩的 run 便是排好序的結果。
3、Timsort是穩定的算法,當待排序的數組中已經有排序好的數,它的時間復雜度會小於nlogn。與其他合並排序一樣,Timesort是穩定的排序算法,最壞時間復雜度是O(n log n)。在最壞情況下,Timsort算法需要的臨時空間是n/2,在最好情況下,它只需要一個很小的臨時存儲空間 -
頻繁老年代回收怎么分析解決?
參考:
https://www.cnblogs.com/justdojava/p/11198106.html
http://www.codersui.com/198.html
年輕代中經歷了N次垃圾回收后仍然存活的對象,會被放到年老代中,老年代占滿后觸發FULL GC,一般是有對象無法回收會導致老年代頻繁回收,排查步驟如下:- ps命令拿到pid:
ps -ef|grep your_application
- jstat命令查詢gc情況:
jstat -gcutil 172046 1000
- 使用jmap分析對象占用內存情況,並導出到jmap.txt中:
jmap -histo 172046 > jmap.txt
- ps命令拿到pid:
-
說說Spring IOC、AOP的原理?
- IOC是控制反轉的意思,用於降低代碼之間的耦合度。工廠模式的升華,可以把IOC容器看作是一個工廠,這個工廠里要生產的對象都在配置文件中給出定義,然后利用編程語言的的反射編程,根據配置文件中給出的類名生成相應的對象。 (對象A獲得依賴對象B的過程,由主動行為變為了被動行為,控制權顛倒過來了,這就是“控制反轉”這個名稱的由來).
- AOP意為面向切面編程,基於代理思想。對原來目標對象創建代理對象,在不修改原對象代碼情況下,通過代理對象增加增強功能的代碼,從而對原有業務方法進行增強。實現方式有JDK動態代理和動態字節碼Cglib技術。
-
阻塞隊列不用java提供的自己怎么實現,condition和wait不能用?
https://blog.csdn.net/h525483481/article/details/80347485 -
擁塞窗口為什么要用慢啟動?
https://www.cnblogs.com/losbyday/p/5847041.html -
說說負載均衡有幾種算法以及優缺點?
- 輪詢
將所有請求,依次分發到每台服務器上,適合服務器硬件相同的場景。
優點:服務器請求數目相同
缺點:服務器壓力不一樣,不適合服務器配置不同的情況 - 隨機
請求隨機分配到各台服務器上。
優點:使用簡單
缺點:不適合機器配置不同的場景 - 最少鏈接
將請求分配到連接數最少的服務器上(目前處理請求最少的服務器)。
優點:根據服務器當前的請求處理情況動態分配
缺點:算法實現相對復雜,需要監控服務器請求連接數 - Hash(源地址散列)
根據IP地址進行Hash計算,得到IP地址。
優點:將來自同一IP地址的請求,同一會話期內,轉發到相同的服務器,實現會話粘滯
缺點:目標服務器宕機后,會話會丟失 - 加權
在輪詢、隨機、最少鏈接、Hash等算法的基礎上,通過加權的方式,進行負載服務器分配。
優點:根據權重,調節轉發服務器的請求數目
缺點:使用相對復雜
- 輪詢
-
Redis的數據一致性問題(分布式多節點環境 & 單機環境)
https://blog.csdn.net/qq_27384769/article/details/79499373 -
簡述docker容器?
Docker是一個容器化平台,它以容器的形式將您的應用程序及其所有依賴項打包在一起,以確保您的應用程序在任何環境中無縫運行。 -
設計模式的看法和認知,有哪些設計模式?
設計模式就是一套被反復使用,多數人知曉的代碼設計經驗的總結。常用的設計模式如下:
工廠模式:Spring通過工廠模式創建bean
代理模式:Spring AOP通過動態代理增強原對象的功能
責任鏈模式:SpringMVC的過濾器
單例模式:spring構建的對象默認是單例 -
如何實現分布式緩存?
分布式緩存系統要滿足動態擴展和高可用性,通常采用Redis實現。Sentinel模式實現主從,
Cluster模式實現集群。通過key做一致性哈希,實現key對應redis結點的分布。 -
多線程如何避免死鎖?
- 加鎖順序(線程按照一定的順序加鎖)
- 加鎖時限(線程嘗試獲取鎖的時候加上一定的時限,超過時限則放棄對該鎖的請求,並釋放自己占有的鎖)
- 死鎖檢測(jstack -l jvm_pid)
-
簡述對JVM中的Runtime?
Runtime類代表Java程序的運行時環境,每個Java程序都有一個Runtime實例,該類會被自動創建,可以通過Runtime.getRuntime()方法來獲取當前程序的Runtime實例。 -
DNS解析過程?
- 查詢本地hosts文件
- 查詢本次DNS緩存
- 查詢本地DNS服務器
- 本地DNS服務器轉發請求到根DNS服務器
參考:https://www.jianshu.com/p/401f34691dcc
-
簡述Htttp協議,Http和Https的區別,Https的加密方式?
HTTP是一個基於TCP/IP通信協議來傳遞數據(HTML文件、圖片等),屬於客戶端-服務端工作模式,瀏覽器作為HTTP客戶端通過URL向WEB服務器發送請求。https是http和TCP之間加入的SSL層,作用是防止釣魚和數據加密。HTTPS采用非對稱加密算法協商對稱加密算法,處理步驟如下:- 服務器將攜帶的公鑰向數字證書機構申請證書。
- 數字證書機構用自己的私鑰對公鑰簽名頒發證書,並返回給服務器。
- 服務器將申請攜帶公鑰的證書分發給客服端。
- 客戶端驗證證書,證書機構通過驗證,或者用戶接受不受信任的證書(非權威機構頒發的證書)。獲取到公鑰。到這一步,在證書保證下服務器擁有私鑰,客戶端擁有公鑰,可進行非對稱性加密。
- 使用公鑰加密報文發送給服務器,其中攜帶隨機串。其中的隨機串用戶傳輸數據時進行對稱加密。
- 服務器使用私鑰解密。獲取報文信息及隨機串。
- 解密后服務器發送握手消息給客戶端。
- 客戶端接受握手消息,握手結束,雙方確定加密算法(使用隨機串確定的對稱性加密),開始傳輸。
- 數據傳輸過程使用對稱性加密算法。
-
Http請求過程?
- 對網址進行DNS域名解析,得到對應的IP地址。
- 根據IP找到對應的服務器,發起TCP的三次握手。
- 建立TCP連接后發起HTTP請求。
- 服務器響應HTTP請求,瀏覽器得到html代碼。
- 瀏覽器解析html代碼,請求html中包含其他資源地址(如js、css圖片等)。
- 瀏覽器對頁面進行渲染呈現給用戶。
-
說說TCP協議的三次握手四次揮手?
-
三次握手:
- 第一次握手:Client將標志位SYN置為1,隨機產生一個值seq=J,並將該數據包發送給Server,Client進入SYN_SENT狀態,等待Server確認。
- 第二次握手:Server收到數據包后由標志位SYN=1知道Client請求建立連接,Server將標志位SYN和ACK都置為1,ack (number )=J+1,隨機產生一個值seq=K,並將該數據包發送給Client以確認連接請求,Server進入SYN_RCVD狀態。
- 第三次握手:Client收到確認后,檢查ack是否為J+1,ACK是否為1,如果正確則將標志位ACK置為1,ack=K+1,並將該數據包發送給Server,Server檢查ack是否為K+1,ACK是否為1,如果正確則連接建立成功,Client和Server進入ESTABLISHED狀態,完成三次握手,隨后Client與Server之間可以開始傳輸數據了。
-
四次揮手:
- 第一次揮手:Client發送一個FIN,用來關閉Client到Server的數據傳送,Client進入FIN_WAIT_1狀態。
- 第二次揮手:Server收到FIN后,發送一個ACK給Client,確認序號為收到序號+1(與SYN相同,一個FIN占用一個序號),Server進入CLOSE_WAIT狀態。
- 第三次揮手:Server發送一個FIN,用來關閉Server到Client的數據傳送,Server進入LAST_ACK狀態。
- 第四次揮手:Client收到FIN后,Client進入TIME_WAIT狀態,接着發送一個ACK給Server,確認序號為收到序號+1,Server進入CLOSED狀態,完成四次揮手。
項目經驗
-
對你來說影響最大的一個項目?
-
說說自己參與的項目技術難度在哪里?哪一部分最難攻克?如何攻克?
-
為什么會想做這個項目?這個項目的idea是誰提出來的?
-
說說對項目中用到中間件的理解(Dubbo、MQ、Redis、kafka、zookeeper)?
-
服務器雪崩是怎么造成的?之前有這樣的經歷嗎?怎么防備?
-
說說高並發架構的設計思路?
- CDN緩存靜態資源
- 服務拆分和負載均衡
- 分布式緩存
- 消息隊列解耦流量削峰
- 數據庫集群和庫表散列。
-
項目中如何實現的大數據的傳輸和存儲?
-
如何實現何高並發下的削峰和限流?
限流算法:漏桶算法和令牌桶算法(基於Redis的分布式令牌桶實現) -
簡述軟件模塊化的好處?
- 有利於代碼復用
- 有利於分工協作
- 有利於模塊化測試
- 有利於模塊化部署與監控、排錯
生活經歷
- 生活中遇到的最大的挫折,怎么解決的?
- 生活中遇到的最有成就感的事情?
- 你的職業規划是什么?