**java中常用的註解分三類:
1.JDK註解
2.Java第三方註解:spring、spring、springboot
3.自定義註解**
-----------JDK註解-----
1、@Resource
詳解
@Resource註解與@Autowired註解作用非常相似
@Resource的裝配順序:
(1)、@Resource後面沒有任何內容,默認通過name屬性去匹配bean,找不到再按type去匹配
(2)、指定了name或者type則根據指定的類型去匹配bean
(3)、指定了name和type則根據指定的name和type去匹配bean,任何一個不匹配都將報錯
@Autowired和@Resource兩個註解的區別:
(1)、@Autowired默認按照byType方式進行bean匹配(適合單例,多實例報錯,巧記,spring推薦單例自動注入),@Resource默認按照byName方式進行bean匹配(適合多實例按名稱注入)
(2)、@Autowired是Spring的註解,@Resource是J2EE的註解,這個看一下導入註解的時候這兩個註解的包名就一清二楚了
Spring屬於第三方的,J2EE是Java自己的東西,因此,建議使用@Resource註解,以減少代碼和Spring之間的耦合。
1、共同點
兩者都可以寫在字段和setter方法上。兩者如果都寫在字段上,那麼就不需要再寫setter方法。
2、不同點
(1)@Autowired
@Autowired爲Spring提供的註解,需要導入包org.springframework.beans.factory.annotation.Autowired;只按照byType注入。
-----------Java第三方註解-----
spring註解
@Configuration把一個類作爲一個IoC容器,它的某個方法頭上如果註冊
@Bean,就會作爲這個Spring容器中的Bean。
@Scope註解 作用域
@Lazy(true) 表示延遲初始化
@Service用於標註業務層組件、
@Controller用於標註控制層組件(如struts中的action)
@Repository用於標註數據訪問組件,即DAO組件。
@Component泛指組件,當組件不好歸類的時候,我們可以使用這個註解進- 行標註。
@Scope用於指定scope作用域的(用在類上)
@Autowired 默認按類型裝配,如果我們想使用按名稱裝配,可以結合@Qualifier註解一起使用。如下:
@Autowired @Qualifier(“personDaoBean”) 存在多個實例配合使用
@PostConstruct 初始化註解。構造方法之後,init之前
@PreDestroy destroy方法之後,實例
@Async異步方法調用
springboot註解
@SpringBootApplication:包含了@ComponentScan、@Configuration和@EnableAutoConfiguration註解。其中@ComponentScan讓spring Boot掃描到Configuration類並把它加入到程序上下文。
@Configuration 等同於spring的XML配置文件;使用Java代碼可以檢查類型安全。
@EnableAutoConfiguration 自動配置。
@ComponentScan 組件掃描,可自動發現和裝配一些Bean。
@Component可配合CommandLineRunner使用,在程序啓動後執行一些基礎任務。
@RestController註解是@Controller和@ResponseBody的合集,表示這是個控制器bean,並且是將函數的返回值直 接填入HTTP響應體中,是REST風格的控制器。
@Autowired自動導入。
@PathVariable獲取參數。
@JsonBackReference解決嵌套外鏈問題。
@RepositoryRestResourcepublic配合spring-boot-starter-data-rest使用。
@ResponseBody:表示該方法的返回結果直接寫入HTTP response body中,一般在異步獲取數據時使用,用於構建RESTful的api。在使用@RequestMapping後,返回值通常解析爲跳轉路徑,加上@responsebody後返回結果不會被解析爲跳轉路徑,而是直接寫入HTTP response body中。比如異步獲取json數據,加上@responsebody後,會直接返回json數據。該註解一般會配合@RequestMapping一起使用。
@RestController:用於標註控制層組件(如struts中的action),@ResponseBody和@Controller的合集。
@ComponentScan:表示將該類自動發現掃描組件。
@Import:用來導入其他配置類。
@ImportResource:用來加載xml配置文件。
@Autowired:自動導入依賴的bean
@Value:注入Spring boot application.properties配置的屬性的值。
hibernate註解
@Entity:將pojo類標記成實體,可以指定一個name屬性,指定實體類的名稱
@Table:註釋改持久化類所映射的表
@UniqueConstraints:用於數據表的唯一約束 columnNames屬性
@Index用於數據庫建立索引
@DynamicInsert:指定用於插入記錄的insert語句是否在運行時動態生成。並且只插入那些非空字段。默認值時false
@DynamicUpdate:指定用於更新鉅鹿的update語句是否在運行是時動態生成,並且只更新那些修改過的字段,默認值是否false
@SelectBeforeUpdate:制動Hbiernate在更新某個持久化對象之前是否進行一次select(建議false)
@NotBlank只能作用在String上,不能爲null,而且調用trim()後,長度必須大於0
#swagger2註解
@Api()用於類; 表示標識這個類是swagger的資源
@ApiOperation()用於方法; 表示一個http請求的操作
@ApiParam()用於方法,參數,字段說明;表示對參數的添加元數據(說明或是否必填等)
@ApiModel()用於類 表示對類進行說明,用於參數用實體類接收
@ApiModelProperty()用於方法,字段;表示對model屬性的說明或者數據操作更改
@ApiIgnore()用於類,方法,方法參數 ;表示這個方法或者類被忽略
@ApiImplicitParam() 用於方法 ;表示單獨的請求參數
@ApiImplicitParams() 用於方法,包含多個 @ApiImplicitParam
Mybaits註解
@Select 簡單查詢
@Insert 簡單插入
@Update 簡單更新
@Delete 簡單刪除
@Param : 入參
@Results : 結果集合
@Result : 結果
lombok整理
@Data 註解在類上;提供類所有屬性的 getting 和 setting 方法,此外還提供了equals、canEqual、hashCode、toString 方法
@Setter :註解在屬性上;爲屬性提供 setting 方法
@Setter :註解在屬性上;爲屬性提供 getting 方法
@Log4j :註解在類上;爲類提供一個 屬性名爲log 的 log4j 日誌對象
@NoArgsConstructor :註解在類上;爲類提供一個無參的構造方法
@AllArgsConstructor :註解在類上;爲類提供一個全參的構造方法
@Cleanup : 可以關閉流
@Builder : 被註解的類加個構造者模式
@Synchronized : 加個同步鎖
@SneakyThrows : 等同於try/catch 捕獲異常
@NonNull : 如果給參數加個這個註解 參數爲null會拋出空指針異常
@Value : 註解和@Data類似,區別在於它會把所有成員變量默認定義爲private final修飾,並且不會生成set方法
@ToString:無需啓動調試器即可查看您的字段,註解會自動重寫對應的toStirng方法
-----------自定義便捷註解-----
一、定義可用的註解接口(理解爲對往暴露的一個可用的註解殼子,沒有實現複雜的邏輯)
先認識四種元註解,專門註解其他的註解:
巧記:文檔週期繼承目標
@Documented –註解是否將包含在JavaDoc中
@Retention –什麼時候使用該註解
@Target –註解用於什麼地方
@Inherited – 是否允許子類繼承該註解
@Target(ElementType.FIELD)//註解的作用範圍,就是註解是用在什麼地方的
@Retention(RetentionPolicy.RUNTIME)//註解的級別,就是註解能留存到什麼時候
@Documented
@Inherited
public @interface MyAnnotation {
public String value();//註解可以接收的參數
}
二、註解處理器(自定義註解的業務實現邏輯入口在這)
public class Inject {
public static void injectfeild(Object o){
Class<?> clazz = o.getClass(); //獲得傳進來的類
Field[] fields = clazz.getDeclaredFields();//通過反射獲取類的域(全局變量)
for (Field field : fields) {
// 查看這個字段是否有我們自定義的註解類標誌的
if (field.isAnnotationPresent(MyAnnotation.class)) {
MyAnnotation inject = field.getAnnotation(MyAnnotation.class); //獲取到我們的註解
String value=inject.value();//獲取註解的參數
field.setAccessible(true);
try {
//處理註解想要實現的業務邏輯
} catch (IllegalArgumentException | IllegalAccessException e) {
e.printStackTrace();
}
}
}
}
}
三、獲取獲取指定註解字段的值
/**
* @Author: Jiangxiaopeng
* @Description:獲取指定註解字段的值
* @Date: 2020/6/3
* Object object2 已知對象
* String reNameValue 註解字段指定重命名的名稱
**/
public static String getFeiledValueByObject(Object object2 , String reNameValue) throws IllegalAccessException {
Field[] fields = object2.getClass().getDeclaredFields();
for (Field field : fields) {
if (field.isAnnotationPresent(ReNameAnnotation.class)) {
ReNameAnnotation reNameAnnotation = (ReNameAnnotation) field.getAnnotation(ReNameAnnotation.class);
String reName= reNameAnnotation.reName();
if(reNameValue.equals(reName)){
field.setAccessible(true);
Object o=field.get(object2);
String a1 =o.toString();
return a1;
}
}
}
return null;
}
/**
* @Author: Jiangxiaopeng
* @Description:獲取指定註解字段的值
* @Date: 2020/6/3
* ProceedingJoinPoint point 通過他拿到方法入參所有對象,然後遍歷
* String reNameValue 註解字段指定重命名的名稱
**/
public static String getFeiledValueByPoint(ProceedingJoinPoint point,String reNameValue) throws IllegalAccessException {
// Field[] fields = clazz.getDeclaredFields();
Object[] args = point.getArgs();
for (Object object : args) {
Field[] fields = object.getClass().getDeclaredFields();
for (Field field : fields) {
if (field.isAnnotationPresent(ReNameAnnotation.class)) {
ReNameAnnotation reNameAnnotation = (ReNameAnnotation) field.getAnnotation(ReNameAnnotation.class);
String reName= reNameAnnotation.reName();
if(reNameValue.equals(reName)){
field.setAccessible(true);
Object o=field.get(object);
String a1 =o.toString();
return a1;
}
}
}
}
return null;
}
--------------------解決問題----------------
問題1:Java反射操作私有成員變量 Class can not access a member with modifiers "private"
解決:https://blog.csdn.net/hanchao5272/article/details/79435358
通過反射操作類的私有(private)成員變量時,需要通過field.setAccessible(true)
將字段設置爲可以訪問的。