反射
import org.junit.Test;
import java.util.Arrays;
/*本类用于测试反射技术*/
public class TestReflect {
/*单元测试方法:
* public +void +没有参数 +@Test(表示这是一个单元测试方法)
* 注意:单元测试工具需要导包,选择带有 “JUnit4” 的即可*/
@Test
public void getClazz() throws ClassNotFoundException {
//1.练习获取字节码文件的三种方式
Class<?> class1 = Class.forName("cn.tedu.reflection.Student");
Class<?> class2 = Student.class;
Class<?> class3 = new Student().getClass();
//打印的是Student类对应的字节码对象
System.out.println(class1);//class cn.tedu.reflection.Student
System.out.println(class1.getName());//cn.tedu.reflection.Student
//通过字节吗对象,获取Student类的类名
System.out.println(class2.getSimpleName());//Student
//通过字节码对象获取Student类对应的包对象
System.out.println(class3.getPackage());
//通过字节码对象获取Student类对应的包对象,在获取这个包对象的名字
System.out.println(class3.getPackage().getName());
}
@Test
public void getStu(){
//1.创建学生类对象
Student s1 = new Student("张三", 3);
Student s2 = new Student("李四", 4);
Student s3 = new Student("王五", 5);
//2.准备数组将刚刚创建好的学生类对象,放入进去
Student[] s={s1,s2,s3};
System.out.println(Arrays.toString(s));
for (Student st:s) {
// System.out.println(st);
st.eat(10);
st.play();
}
}
}
/*本类用于测试反射的物料类,假装这个类是别人写的*/
public class Student {
//1.定义成员变量
String name;
int age;
//2.生成本类的无参构造与有参构造
public Student(){
}
public Student(String name, int age) {
this.name = name;
this.age = age;
}
//3.定义普通方法
public void play(){
System.out.println("玩儿");
}
public void eat(int n){
System.out.println("中午吃"+n+"_");
}
//4.添加重写的toString()方法
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
", age=" + age +
'}';
}
}
注解
首先注意:注解定义的语法与Java不同
定义自定义注解的格式是:@interface 注解名{}
通过原注解@Target规定自定义注解可以使用在哪些位置,我们可以使用“ElementType.静态常量”的方式来指定自定义注解具体位置。而且,值可以写多个,,格式:@Target({值1,值2,值3...})
通过原注解@Retention规定自定义注解的生命周期,我们使用“RetentionPolicy.静态常量”的方式来指定自定义注解的存活时间。注意:这里的值只能写一个:SOURCE CLASS RUNTIME 3选1
注解在使用时,在规定位置,格式:@注解名 即可
注意:int age();不是方法的定义,而是给自定义注解添加了一个age属性
注解中还可以添加特殊属性value。特殊属性的定义方式与普通属性一样,要求:名字必须是value,类型不作限制
import org.junit.Test;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/*本类用于注解的入门案例:尝试自定义一个注解*/
public class TestAnnotation {
}
//1.定义自定义注解
/*1.首先注意:注解定义的语法与Java不同
* 2.定义自定义注解的格式是:@interface 注解名{}*/
//2.通过@Target注解标记自定义注解Rice可以使用的位置
//@Target(ElementType.TYPE)//只能在类上加自定义注解
/*3.通过原注解@Target规定自定义注解可以使用在哪些位置
* 我们可以使用“ElementType.静态常量”的方式来指定自定义注解具体位置
* 而且,值可以写多个,,格式:@Target({值1,值2,值3...})*/
@Target({ElementType.TYPE,ElementType.METHOD})
//3.通过@Retention注解标记自定义注解的生命周期
/*4.通过原注解@Retention规定自定义注解的生命周期
* 我们使用“RetentionPolicy.静态常量”的方式来指定自定义注解的存活时间
* 注意:这里的值只能写一个:SOURCE CLASS RUNTIME 3选1 */
@Retention(RetentionPolicy.RUNTIME)//到运行时都有效
@interface Rice{
//5.我们可以给注解增加功能--添加注解的属性
/*6.注意:int age();不是方法的定义,而是给自定义注解添加了一个age属性*/
// int age();//给自定义注解添加了一个普通属性age,类型是int
int age() default 0;//给自定义注解的普通属性赋予默认值0
/*7.注解中还可以添加特殊属性value
* 特殊属性的定义方式与普通属性一样,要求:名字必须是value,类型不作限制*/
// String value();//定义一个特殊属性value,类型是Sting
String value() default "lemon";//定义特殊属性,并给特殊属性赋予默认值
}
//4.定义一个类用来测试自定义注解
/*5.注解在使用时,在规定位置,格式:@注解名 即可*/
//@Rice
class TestAnno{
/*测试1:分别给TestAnno类,name属性 eat方法都添加了Rice注解
* 结论:属性上的注解出错了,说明自定义注解可以加在什么位置,由@Target决定*/
// @Rice//报错了
String name;
/*测试2:当我们给Rice注解添加了一个age属性后,@Rice注解使用时直接报错
* 结论:当注解没有定义属性时,可以直接调用
* 当注解定义了属性以后,必须给属性赋值,格式:@Rice(age=10)*/
/*测试3:给age属性赋予默认值之后,可以直接使用@Rice注解
* 不需要给age属性赋值,因为age属性已经有默认值0了*/
/*测试4:给Rice注解添加了特殊属性value以后,也必须给属性赋值
* 只不过特殊属性value赋值时可以简写成@Rice("Apple")*/
/*测试5:如果特殊属性也赋予了默认值,那么可以直接使用这个注解
* 但是想给注解的所有属性赋值,每条赋值语句都不能简写,包括特殊属性*/
// @Rice(10)//普通属性的值不能直接赋值
// @Rice(age=10)
// @Rice("orange")
@Rice(age=10,value="orange")
public void eat(){
System.out.println("干饭干饭");
}
}
单例设计模式
饿汉式
直接创建好对象,不管你是不是使用
/*本类用于实现单例设计模式方案1:饿汉式*/
public class Singleton1 {
public static void main(String[] args) {
MySingle ms = MySingle.getMs();
MySingle ms1 = MySingle.getMs();
//用==检验是否为同一个对象
System.out.println(ms==ms1);
}
}
//创建自己的单例模式
class MySingle{
//1.构造方法私有化
/*1.构造方法私有化的目的:为了防止外界随意实例化本类对象*/
private MySingle(){
}
//2.创建本类对象,并将对象私有化
private static MySingle ms=new MySingle();
//3.提供公共的访问方式,向外界返回创建好的对象
public static MySingle getMs(){
return ms;
}
}
懒汉式
等到你使用的时候,在创建对象
/*本类用于实现单例设计模式方案2:懒汉式*/
public class Singleton2 {
public static void main(String[] args) {
MySingle2 my1 = MySingle2.getMs2();
MySingle2 my2 = MySingle2.getMs2();
System.out.println(my1==my2);
}
}
class MySingle2{
private MySingle2(){}
private static MySingle2 ms;
public static MySingle2 getMs2(){
if(ms==null){
ms=new MySingle2();
}
return ms;
}
}