Spring常見面試題

1.spring由那幾個模塊組成?
Spring Core:核心類庫,提供IOC服務;
Spring Context:提供框架式的Bean訪問方式,以及企業級的功能;
Spring AOP:提供AOP服務;
Spring DAO :對JDBC的抽象,簡化了數據訪問異常的處理;
Spring ORM:對象有ORM框架的支持;
Spring Web:提供基本的面向Web的合特性,例如多方文件上傳;
Spring MVC:提供面向Web應用的Model-View-Controller實現

2.spring中Bean的作用域
singleton:Spring IOC容器中只會存在一個共享的Bean實例,無論有多少個Bean引用它,始終指向同一個對象。單例的模式由BeanFactory自身來維護;
prototype:每次通過spring容器獲取prototype定義的Bean時,容器都將創建一個新的Bean的實例,每個Bean實例都有自己的屬性和狀態,而singleton全局只有一個對象;
request:在一次http請求中,容器會返回該Bean的同一實例。而對不同的http請求,則會產生新的 Bean,而且該bean僅在當前Http Request內有效;
session:與request範圍類似,確保每個session都有一個Bean’實例,在session失效之後,Bean隨之失效;
global-session:全局作用域,global-session和portlet應用相關,當你的應用部署zaiportlet容器中工作時,它包含很多portlet,如果你想聲明所有的portlet共用全局的儲存變量的話,那麼這個全局變量需要儲存在global-session中,全局作用域與Servlet中的session作用域效果相同;

3.Spring中Bean的聲明週期
在這裏插入圖片描述
(1)實例化Bean
對於BeanFactory容器,當客戶向容器請求一個尚未初始化的bean時,或初始化bean的時候需要注入另一個尚未初始化的依賴時,容器會調用createBean進行實例化。對於ApplicationContext容器,當容器啓動結束後,通過獲取beanDefintion對象中的信息,實例化所有的bean。
(2).依賴注入,設置對象屬性
實例化後的對象封裝在BeanWrapper對象中,緊接着,spring根據BeanDfinfintion中的信息以及通過BeanWrapper提供的設置的接口完成依賴注入;
(3)處理Aware接口:
spring會檢測對象是否實現了 **Aware接口,並將相關的 xxxAware實例注入給Bean
a.如果這個bean已經實現了BeanNameAware接口,會調用他實現的setBeanName(BeanId)方法,此處傳遞的就是Spring配置文件中Bean的id值;
b.如果這個bean已經實現了BeanFactoryAware接口,會調用它實現的
setBeanFactory(),傳遞的是Spring工廠本身;
c.如果這個bean已經實現了ApplicationContextAware接口,會調用它實現的
setApplicationContext方法,傳入spring上下文;
4)BeanPostProcessor
如果相對bean進行一些自定義的處理,那麼可以讓bean實現了BeanPostProcessor接口,會調用postProcessorBeforeInitialization(Object obj,String s)方法;
(5)InitializingBean和init-method
如果Bean在Spring配置文件中配置了init-method屬性,則會自動調用其配置的初始化方法
(6)Bean關聯BeanPostProcess接口
如果這個Bean實現了BeanPostProcess接口,就會調用postProcessAfterInitialization方法,這個方法是在Bean初始化結束時調用的(此時Bean已經被正確創建了)
(7)DisposableBean
當bean不在被需要時,會經歷清理階段,如果實現了DisposableBean這個接口,會調用其實現的destory()方法;
(8)destory-method
最後,如果這個Bean的Spring配置中配置了destroy-method屬性,會自動調用其配置的銷燬方法。

4.自動裝配有哪些方式
在spring中,對象無需自己查找或創建與其關聯的其他對象,由容器負責把需要相互協作的對象引用賦予各個對象,使用autowire來配置自動裝載模式:
* no:默認的方式不進行自動裝配,通過手動設置ref屬性來進行裝配bean
* byType:通過參數的類型進行自動裝配
* byName:通過bean 的名稱進行自動裝配
* constructor:利用構造函數進行裝配,並且構造函數的參數通過byType進行裝配
* autodetect:自動探測,如果有構造方法,通過construtor方式自動裝配,否則使用byType的方式自動裝配

基於註解的方式:
使用@autowired註解自動來裝配製定的bean,在使用@Autowired註解之前需要在Spring配置文件
進行配置,<context:annotation-config />。在啓動spring IoC時,容器自動裝載了一個
AutowiredAnnotationBeanPostProcessor後置處理器,當容器掃描到@Autowied、
@Resource或@Inject時,就會在IoC容器自動查找需要的bean,並裝配給該對象的屬性。在使用
@Autowired時,首先在容器中查詢對應類型的bean:
	如果查詢結果爲一個,就將該bean裝配給@autowired指定的數據
	如果查詢的結果不止一個,@autowiredautowired會根據名稱來查找
	若果上述的查找爲空,那麼會拋出異常,解決方法時;使用required=false
@autowired可用於:構造函數,成員變量,Setter方法

5.spring框架中都用到了哪些設計模式
a.工廠模式:BeanFactory就是簡單的工廠模式,用來創建對象的實例;
b.單例模式:Bean默認爲單利模式
c代理模式:Spring的AOP功能使用到的jdk的動態代理cglib動態代理
d.模板模式:用來解決代碼重複的問題。比如RestTemplate,JmsTemplate
e.觀察者模式:定義對象一種一對多的依賴關係,當一個對象的狀態發生改變時,所有依賴於它的對象都會得到通知自動更新,如spring中listener的實現(ApplicationListener)

6.對Spring的AOP的理解
OOP:面向對象,允許開發者定義縱向的關係,但並適用於定義橫向的關係,導致大量代碼的重複,二不利於各個模塊的重用;
AOP:一般稱爲面向切面,用於將那些於業務無關,但是卻能對多個對象產生影響的公共行爲和邏輯,抽取並封裝爲一個可重用的模塊,這個模塊被命名爲切面(aspect),減少系統中的重複代碼,降低模塊間的耦合度,提高系統的可維護性。可用於權限認證,日誌打印,事務代理
AOP實現的關鍵在於代理模式,AOP代理主要分爲靜態代理和動態代理。靜態代理的代表爲Aspect;動態代理則以Spring AOP爲代表

Spring AOP中的動態代理主要有兩種,JDK動態代理和CGLIB動態代理:
	1.JDK動態代理只提供接口的代理,不支持類的代理。核心類是invocationHandler接口和
	Proxy類invocationHandler通過invoke()方法反射來調用目標類中的代碼,動態的將
	橫切邏輯和業務編制在一起;接着,proxy利用invocationHandler動態創建一個符合某一
	接口的實例,生成目標類的代理對象
	2.如果代理類沒有發現invocationHandler接口,那麼Spring AOP會選擇使用CGLIB來
	動態代理目標類,CGLIB是一個代碼生類庫,可在運行時動態的生成指定類的一個子類對象
	並覆蓋其中特定方法,並添加增強代碼,從而實現AOP,CGLIB通過繼承的方式做的動態代理
	因此如果某個類被標記爲final,那麼它是無法使用CGLIB
	3.靜態代理和動態代理區別在於AOP代理對象的時機不同,相對來說AspectJ的靜態代理方式
	具有更好的性能,但是AspectJ需要特定的編譯器進行處理,而Spring AOP則無需特定的編
	譯器處理。

InvocationHandler 的 invoke(Object proxy,Method method,Object[] args):
proxy是最終生成的代理實例;
method 是被代理目標實例的某個具體方法; a
rgs 是被代理目標實例某個方法的具體入參, 在方法反射調用時使用。

7.對Spring的Ioc理解
1.IOC就是控制反轉,是指創建對象的控制權的轉移,以前創建對象的主動權是自己把控的,現在對象的創建權交給了spring容器,並由容器根據配置文件去創建實例和管理實例之間的依賴關係,對象與對象之間鬆散耦合,利於功能的複用。DI依賴注入,應用程序在運行依賴Ioc容器來動態注入對象需要的外部資源
2.最直觀的表達是:Ioc讓對象的創建不用去new了,可以由spring自由生產,使用java的反射機制,根據配置文件在運行時動態的去創建對象以及管咯對象,並且調用對象的方法。
3.spring IOC由三種注入方式:根據註解注入,構造器注入,setter方法注入
4.Ioc讓相互協作的組件保持鬆散的耦合,而AOP變成允許你把遍佈於各個應用各層的功能分離出來形成可重用的功能組件

8.BeanFactory和ApplicationContext有什麼區別?

BeanFactory和ApplicationContext是Spring的兩大核心接口,都可以當做Spring的容器。其中ApplicationContext是BeanFactory的子接口。
(1)BeanFactory:是Spring裏面最底層的接口,包含了各種Bean的定義,讀取bean配置文檔,管理bean的加載,初始化。實例化,管理bean的生命週期,維護bean之間的依賴關係。ApplicationContext接口作爲BeanFactory的派生,除了提供BeanFactory所具有的的功能外,還維護了更完整的框架功能:
1.集成MessageSource,因此支持國際化
2. 統一的資源訪問方式
3.提供在監聽器中註冊bean的時間
4.同時加載多個配置文件
(2)1.BeanFactory採用的是延遲加載的形式來注入Bean的,只有在使用到某個Bean,才能對Bean進行實例化加載,這樣,我們就不能發現一些存在的Spring的配置問題。如果Bean的某一個屬性沒有注入,BeanFactory加載後,直至第一次使用調用getBean方法纔會拋出異常
2.ApplicationContext,它在容器一起動的時候,一次性創建了所有的bean,這樣,容器一啓動時,就能發現spring中存在的配置錯誤,有利於檢查所依賴的屬性是否注入
3.ApplicationContext 唯一的不足是佔用內存空間。當應用程序配置Bean較多時,程序啓動較慢。
(3)BeanFactory和ApplicationContext都支持BeanPostProcessor、BeanFactoryPostProcessor的使用,但兩者之間的區別是:BeanFactory需要手動註冊,而ApplicationContext則是自動註冊。

9.spring事務的實現方式和實現原理
spring事務的本質其實就是數據庫對事物的支持,沒有數據庫的事務支持,spring是無法提供事務的,真正的數據庫層的事務提交和回滾通過binlog或者redo log實現的
spring事務的種類:
1.編程時事務: TransactionTemplate
2.聲明式事務:建立在AOP之上,本質是通過AOP功能,對方法前後進行攔截,將事務的功能便知道攔截的方法中,在目標方法開始之前加入一個事務,在目標方法執行完成之後進行提交或者回滾事務。

聲明式事務最大的優點是不需要再業務邏輯代碼中摻雜事務管理代碼,只需要在配置文件中做相關的
事務規則或通過@Transaction註解的方式,便可以將事務規則應用到業務邏輯中
聲明式事務福安裏要優於編程式事務,這正是spring飛侵入式的開發方式,是業務代碼不受污染,只
要加上註解可獲得完全的事務支持。只能應用到方法級別,不能像編程式事務一樣作用到代碼塊級別

10.spring的事務傳播行爲
傳播行爲說的是,當多個事務同時存在的時候,spring如何這個事務的行爲?

 PROPAGATION_REQUIRED:如果當前沒有事務,就創建一個新事務,如果當前存在事務,就加入該事務,該設置是最常用的設置。

 PROPAGATION_SUPPORTS:支持當前事務,如果當前存在事務,就加入該事務,如果當前不存在事務,就以非事務執行。‘

 PROPAGATION_MANDATORY:支持當前事務,如果當前存在事務,就加入該事務,如果當前不存在事務,就拋出異常。

 PROPAGATION_REQUIRES_NEW:創建新事務,無論當前存不存在事務,都創建新事務。

 PROPAGATION_NOT_SUPPORTED:以非事務方式執行操作,如果當前存在事務,就把當前事務掛起。

 PROPAGATION_NEVER:以非事務方式執行,如果當前存在事務,則拋出異常。

 PROPAGATION_NESTED:如果當前存在事務,則在嵌套事務內執行。如果當前沒有事務,則按REQUIRED屬性執行。

12.spring的隔離級別

 ISOLATION_DEFAULT:這是個 PlatfromTransactionManager 默認的隔離級別,使用數據庫默認的事務隔離級別。

 ISOLATION_READ_UNCOMMITTED:讀未提交,允許另外一個事務可以看到這個事務未提交的數據。

 ISOLATION_READ_COMMITTED:讀已提交,保證一個事務修改的數據提交後才能被另一事務讀取,而且能看到該事務對已有記錄的更新。

 ISOLATION_REPEATABLE_READ:可重複讀,保證一個事務修改的數據提交後才能被另一事務讀取,但是不能看到該事務對已有記錄的更新。

 ISOLATION_SERIALIZABLE:一個事務在執行的過程中完全看不到其他事務對數據庫所做的更新。

13.spring AOP裏面的名詞解釋
切面:被抽取的公共模塊,可能會回橫切多個對象在Spring AOP中,在AOP中切面就是與業務邏輯獨立,但又垂直存在於業務邏輯的代碼結構中的通用功能組合;
切點(join point):切面與業務邏輯相交的點就是切點;連接點就是把業務邏輯離散化後的關鍵節點;切點屬於連接點,是連接點的子集,一個連接點代表一個方法的執行
通知(advice):在切面的某個特定的連接點上執行的操作,其中包括 “before”,“after”,“around”等通知
切入點(Pointcut):切入點是指我們要對哪些joint point進行攔截的定義,通過切入點表達式,指定攔截的方法,比如指定攔截add*、search*。
目標對象: 被一個或者多個切面(aspect)所通知(advise)的對象。也有人把它叫做 被通知(adviced) 對象。 既然Spring AOP是通過運行時代理實現的,這個對象永遠是一個 被代理(proxied) 對象。
織入(Weaving):在切點上可以把要完成增強操作的目標對象(Target)連接到切面裏,這個連接的方式就叫織入。

13.spring的通知類型

**前置通知**(Before advice):在某連接點(join point)之前執行的通知,但這個通知不能阻止
連接點前的執行
返回後通知(After returning advice):在某連接點(join point)正常完成後執行的通知:例如,一個方法沒有拋出任何異常,正常返回。 
拋出異常後通知(After throwing advice):在方法拋出異常退出時執行的通知。 
後通知(After (finally) advice):當某連接點退出的時候執行的通知(不論是正常返回還是異
常退出)
環繞通知(Around Advice):包圍一個連接點(join point)的通知,如方法調用。這是最強大
的一種通知類型。 環繞通知可以在方法調用前後完成自定義的行爲。它也會選擇是否繼續執行連接點
或直接返回它們自己的返回值或拋出異常來結束執行。 環繞通知是最常用的一種通知類型

14.spring框架中單例Beans是線程安全的嗎?
Spring框架並沒有對單例bean進行任何多線程的封裝處理,,大部分的Spring bean並沒有可變的狀態(比如Serview類和DAO類),所以在某種程度上說Spring的單例bean是線程安全的。如果你的bean有多種狀態的話(比如 View Model 對象),就需要自行保證線程安全。最淺顯的解決辦法就是將多態bean的作用域由“singleton”變更爲“prototype”。

15.spring如何解決線程併發問題?
在一般情況下,只有無狀態的Bean纔可以在多線程環境下共享,在Spring中,絕大多數的Bean都可以聲明爲 singleton作用域,spring對一些bean中非線程安全狀態採用Threadlocal進行處理,解決線程安全問題
Threadlocal和線程同步機制都是爲了解決線程中相同變量的訪問衝突問題,同步機制採用“時間換空間”發方式,僅提供一份變量,不同線程訪問前需要鎖,沒獲得鎖的需要排隊。給每個線程提供獨立的變量副本,隔離多個線程對數據的 訪問衝突。Threadlocal提供了線程安全的共享對象,在編寫多線程代碼時,可以把不安全的變量封裝進Threadlocal。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章