Java獲取接口的所有實(shí)現(xiàn)類方法總結(jié)示例
業(yè)務(wù)開發(fā)中,有時(shí)需要獲取到某個(gè)接口或抽象類的所有實(shí)現(xiàn)方法,然后再某個(gè)類中集中進(jìn)行處理,都有哪些方法呢?
一、 如果是普通的Java應(yīng)用,可以使用JDK自帶的一個(gè)類加載器ServiceLoader,其實(shí)就是SPI機(jī)制。
ServiceLoaderloader = ServiceLoader.load(IWork.class);
因?yàn)樵赟erviceLoader.load的時(shí)候,是根據(jù)傳入的接口類,遍歷META-INF/services目錄下的以該類命名的文件中的所有類,并實(shí)例化返回。所以,不適用于抽象類。
二、如果在Springboot工程中,接口的實(shí)現(xiàn)可以由IOC容器來托管,就可以非常簡單的從Spring容器中獲取到實(shí)現(xiàn)類集合。具體包括2種渠道。
直接使用Spring注解@Autowired
實(shí)現(xiàn)ApplicationContextAware接口獲取并管理所有實(shí)現(xiàn)類。 就可以很簡單的利用@Autowired來獲取到實(shí)現(xiàn)類的list或map集合。
三、Springboot具體實(shí)現(xiàn)實(shí)例講解
1)接口類
IWorkService.java
public interface IWorkService { String workPlace(); }
2)實(shí)現(xiàn)類
TeacherWorkService.java
@Service public class TeacherWorkService implements IWorkService { @Override public String workPlace() { return "school"; } }
DoctorWorkService.java
@Service public class DoctorWorkService implements IWorkService{ @Override public String workPlace() { return "hospital"; } }
3)Aware實(shí)現(xiàn)類
WorkServiceLocator.java
@Component public class WorkServiceLocator implements ApplicationContextAware { //手動(dòng)獲取,key是bean的name,value是實(shí)現(xiàn)類 private Map<String, IWorkService> workServiceMap; //手動(dòng)獲取,list是所有的實(shí)現(xiàn)類 private List<IWorkService> workServiceList; @Override public void setApplicationContext(ApplicationContext applicationContext) throws BeansException { workServiceMap = applicationContext.getBeansOfType(IWorkService.class); workServiceList = new ArrayList<>(workServiceMap.values()); } public Map<String, IWorkService> getAllMap() { return workServiceMap; } public IWorkService getByName(String beanName) { return workServiceMap.get(beanName); } public List<IWorkService> getAllList() { return workServiceList; } }
3)Test入口類
@SpringBootTest(classes = {Application.class}) @RunWith(SpringRunner.class) public class WorkServiceTest { /** * 方式1:直接使用spring依賴注入注解 */ @Autowired private Map<String, IWorkService> workServiceMap; /** * 方式2:直接使用spring的依賴注入注解 */ @Autowired private List<IWorkService> workServiceList; /** * 方式3:借助spring的ApplicationContextAware */ @Autowired private WorkServiceLocator workServiceLocator; @Test public void testAll() { Map<String, IWorkService> allMap = workServiceLocator.getAllMap(); List<IWorkService> allList = workServiceLocator.getAllList(); IWorkService iWorkService = workServiceLocator.getByName("teacherWorkService"); } }
四、總結(jié)
對(duì)于普通的Java工程實(shí)現(xiàn)獲取接口所有實(shí)現(xiàn)類需要借助SPI機(jī)制,且僅限于接口;對(duì)于Spring工程,則有@Autowired自動(dòng)獲取和實(shí)現(xiàn)ApplicationContextAware手動(dòng)獲取2種,既支持接口實(shí)現(xiàn)類、也支持抽象類的實(shí)現(xiàn)類。
附:java獲取實(shí)現(xiàn)某個(gè)接口的所有實(shí)現(xiàn)類集合
關(guān)鍵在于: applicationContext.getBeansOfType(ChartService.class);
獲得Map對(duì)象的key為實(shí)現(xiàn)類的名稱如:chartSimpleServiceImpl
獲得Map對(duì)象的value為實(shí)現(xiàn)類對(duì)象如: com.read.data.cms.service.impl.ChartExtraServiceImpl@5c85b6e9
applicationContext的獲取方法有很多種,我這里暫列兩種
第一種方式實(shí)現(xiàn)接口所有類集合(注解)
@Autowire private ApplicationContext applicationContext; Map<String,ChartService> res = applicationContext.getBeansOfType(ChartService.class); res.get("實(shí)現(xiàn)類的字符串如:chartSimpleServiceImpl") res.get獲得的結(jié)果,就是當(dāng)前實(shí)現(xiàn)類對(duì)象
第二種方式實(shí)現(xiàn)接口所有類集合(實(shí)現(xiàn)接口)
/** * @author: tianyong * @Time: 2019/6/26 11:17 * @description:服務(wù)工廠(主要用于動(dòng)態(tài)注入接口實(shí)現(xiàn)類) */ @Component public class ServiceFactory implements ApplicationContextAware { //定義成員變量 private static Map<String,ChartService> res; /** * @author: tianyong * @time: 2019/6/27 16:04 * @description:設(shè)置上下文參數(shù) */ @Override public void setApplicationContext(ApplicationContext applicationContext) throws BeansException { res = applicationContext.getBeansOfType(ChartService.class); } /** * @author: tianyong * @time: 2019/6/27 16:05 * @description:根據(jù)標(biāo)記返回當(dāng)前接口實(shí)現(xiàn)類 */ public static <T extends ChartService> T getServices(String flag){ return (T)res.get(flag); } }
到此這篇關(guān)于Java獲取接口的所有實(shí)現(xiàn)類方法的文章就介紹到這了,更多相關(guān)Java獲取接口所有實(shí)現(xiàn)類內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
SpringSecurity 認(rèn)證、注銷、權(quán)限控制功能(注銷、記住密碼、自定義登入頁)
SpringSecurity是一個(gè)強(qiáng)大的Java框架,用于保護(hù)應(yīng)用程序的安全性,它提供了一套全面的安全解決方案,本文給大家介紹SpringSecurity認(rèn)證、注銷、權(quán)限控制和注銷、記住密碼、自定義登入頁等知識(shí)總結(jié),感興趣的朋友一起看看吧2025-03-03springboot的EnvironmentPostProcessor接口方法源碼解析
這篇文章主要介紹了springboot的EnvironmentPostProcessor接口方法源碼解析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-08-08Java找不到或無法加載主類及編碼錯(cuò)誤問題的解決方案
今天小編就為大家分享一篇關(guān)于Java找不到或無法加載主類及編碼錯(cuò)誤問題的解決方案,小編覺得內(nèi)容挺不錯(cuò)的,現(xiàn)在分享給大家,具有很好的參考價(jià)值,需要的朋友一起跟隨小編來看看吧2019-02-02教你用java實(shí)現(xiàn)學(xué)生成績管理系統(tǒng)(附詳細(xì)代碼)
教學(xué)管理系統(tǒng)很適合初學(xué)者對(duì)于所學(xué)語言的練習(xí),下面這篇文章主要給大家介紹了關(guān)于如何用java實(shí)現(xiàn)學(xué)生成績管理系統(tǒng)的相關(guān)資料,文中給出了詳細(xì)的實(shí)例代碼,需要的朋友可以參考下2023-06-06深入了解Java中Cookie和Session的區(qū)別
會(huì)話跟蹤是Web程序中常用的技術(shù),用來跟蹤用戶的整個(gè)會(huì)話,常用的會(huì)話跟蹤技術(shù)是Cookie與Session,本文就詳細(xì)的介紹一下Java中Cookie和Session的區(qū)別,感興趣的可以了解一下2023-06-06據(jù)說這個(gè)是可以擼到2089年的idea2020.2(推薦)
這篇文章主要介紹了據(jù)說這個(gè)是可以擼到2089年的idea2020.2,本教程給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-09-09Spring security基于數(shù)據(jù)庫中賬戶密碼認(rèn)證
這篇文章主要介紹了Spring security基于數(shù)據(jù)庫中賬戶密碼認(rèn)證,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-03-03Java?C++題解leetcode字符串輪轉(zhuǎn)KMP算法詳解
這篇文章主要為大家介紹了Java?C++題解leetcode字符串輪轉(zhuǎn)KMP算法詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-09-09SpringBoot監(jiān)控SQL運(yùn)行情況的流程步驟
Druid是Java語言中最好的數(shù)據(jù)庫連接池,雖然?HikariCP?的速度稍快,但是,Druid能夠提供強(qiáng)大的監(jiān)控和擴(kuò)展功能?,也是阿里巴巴的開源項(xiàng)目,本文給大家介紹了SpringBoot監(jiān)控SQL運(yùn)行情況的流程步驟,需要的朋友可以參考下2024-03-03