java回调机制详解

原文出自这儿:https://blog.csdn.net/fengye454545/article/details/80198446   为了自己能够加深理解自己动手敲了一遍,也写写,有时间看看。更详细建议访问原创博主。

======================================================================================

回调函数

高大上(装逼)定义:回调函数就是一个通过函数指针(或接口)调用的函数。即你把函数指针(或接口)作为参数传递给另一个函数,当这个指针(或接口)被用来调用其所指向的函数时,我们就说这是回调函数。回调函数不是由该函数的实现方直接调用,而是在特定的事件或条件发生时由另外的一方调用,用于对该事件或条件进行响应。

通俗化(草根)定义:有个类A,有方法a();另一个类B,方法b();当在A类中调用了B类的b()方法,在B()中触发特定事件或条件后回过来调用A类中的某个方法比如a()

=================================================

看例子:小明和小李相约一起去吃早饭,但是小李起的有点晚要先洗漱,等小李洗漱完成后,通知小明再一起去吃饭。小明就是类A,小李就是类B。一起去吃饭这个事件就是方法a(),小李去洗漱就是方法b()。

小白这样做(虽然达到了目的,但没有回调思想,是A类主动调用自己的方法):

小李类:

package test1;

public class Xl1 {
	public void WashFace() {
		System.out.println("小李洗脸中。。。");
	}

}

小明类:

package test1;
public class Xm1 {
	
	public void eatRice() {
		System.out.println("小明叫小李一起去吃饭");
		Xl1 xl=new Xl1();
		xl.WashFace();
//		在小明自己的方法中调用,没有回调思想,
//		还是小明自己等到小李后主动再叫了一遍去吃饭。
		TogatherEat();
	}
	public void TogatherEat() {
		System.out.println("两人在食堂吃饭中。。。");
	}
	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Xm1 xm=new Xm1();
		xm.eatRice();
	}

}

改进一下B类就是回调函数:

package test1;

public class Xl2 {
	public void WashFace() {
		System.out.println("小李洗脸中。。。");
		
		//这里是小李去叫小明,实现了回调A中的方法
		Xm1 xm=new Xm1();
		xm.TogatherEat();
	}

}

============================================================

有点水平的这样做:通过接口实现同步回调

EatRice接口:

package test2;

public interface EatRice {
	public void eat(String food);
}

A类小明实现EatRice的接口:

package test2;

public class Xm2 implements EatRice{

	@Override
	public void eat(String food) {
		// TODO Auto-generated method stub
		System.out.println("小明小李一起去吃"+food);
	}
	
        //通知小李去吃饭
	public void Call_XL() {
		Xl2 xl=new Xl2();
		xl.WashFace(this, "基围虾");
	}

	public static void main(String a[]) {
		Xm2 xm=new Xm2();
		xm.Call_XL();
	}

}

B类小李做完事后 回调即可

package test2;

public class Xl2 {
	public void WashFace(EatRice er,String food) {
		System.out.println("小李先洗脸!");
		er.eat(food);
	}
}

===============================================================

高手这样做,这是高手。。这真是高手。。。(异步回调机制)

借用高手的原文:

上面讲的都是同步回调,可是事实上,小李要洗漱后才能吃饭,在小李洗漱的时候,小明是要做自己的事情的,比如他在玩手机,这样子就是异步回调了。而且我们把代码正规化,比如在android点击事件中,你会发现你只要实现View.setOnclickListener(this),即可实现回调,那么像这样子的规范是如何实现的,在这一节里我将会提到。废话少说,先上代码。

EatRice接口没有变化,这里就省去接口代码展示
--------------------- 
作者:FYM-WR 
来源:CSDN 
原文:https://blog.csdn.net/fengye454545/article/details/80198446 
版权声明:本文为博主原创文章,转载请附上博文链接!

A类小明:

package test3;

public class Xm3 implements EatRice {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Xm3 xm=new Xm3();
		xm.Call_XL();
	}
	
	public void Call_XL() {
		
		Xl3 xl=new Xl3();
		xl.setEatRiceListener(this,"基围虾");
	}

	@Override
	public void eat(String food) {
		// TODO Auto-generated method stub
		System.out.println("小李小明一起去吃"+food);
	}

}

B类小李:

package test3;

public class Xl3 {
	public EatRice er;
	
	public void setEatRiceListener(EatRice er, String food) {
		this.er = er;
		WashFace(food);
	   }

	
	public void WashFace(String food) {
		System.out.println("小李要洗脸!\n");
		new Thread(new Runnable() {

			@Override
			public void run() {
				try {
					play();
					Thread.sleep(10000);
					System.out.println("十秒后\n");
					er.eat(food);
				}
				catch(InterruptedException e){
					e.printStackTrace();
				}
				
			}
			
		}).start();
		
	}
	
	public void play() {
		System.out.println("小明在玩手机\n");
	}
	
}

总结:更加深入理解力监听事件的原理,其实像安卓的触摸、按钮监听原理类似,以后写代码灵活性可以更高,原创博主好文章,致谢!原创链接:https://blog.csdn.net/fengye454545/article/details/80198446

猜你喜欢

转载自blog.csdn.net/cj151525/article/details/84953077