Maison  >  Article  >  Java  >  Explication détaillée du mécanisme de rappel de JAVA CallBack

Explication détaillée du mécanisme de rappel de JAVA CallBack

高洛峰
高洛峰original
2017-01-24 13:34:281107parcourir

Préface

CallBack signifie rappel. Les personnes familiarisées avec la programmation Windows connaîtront les quatre mots « fonction de rappel », mais les programmeurs Java n'en savent peut-être pas grand-chose. La « fonction de rappel » ou « méthode de rappel » est un concept très important dans la conception et le développement de logiciels. La maîtrise de l'idée de « fonction de rappel » est très nécessaire pour les programmeurs (quel que soit le langage utilisé).

J'ai récemment appris Java et suis entré en contact avec le mécanisme de rappel (CallBack). Lorsque je l'ai rencontré pour la première fois, j'ai trouvé que c'était assez déroutant, et les explications pertinentes que j'ai trouvées sur Internet étaient soit expliquées en une phrase, soit relativement simples et semblaient fournir une définition du CallBack. Bien sûr, après avoir compris les rappels, je suis allé lire diverses explications sur Internet, et il n'y a vraiment eu aucun problème. Cependant, pour moi, en tant que débutant, il manque un processus étape par étape. Ici, je vais décrire ma compréhension personnelle du mécanisme de rappel, du moins profond au plus profond. S'il y a quelque chose qui ne va pas, n'hésitez pas à m'éclairer !

Avant de commencer, imaginez une scène : les enfants de la maternelle viennent d'apprendre l'addition en 10 près.

Chapitre 1. L'origine de l'histoire

L'institutrice de maternelle a écrit une équation « 1 1 = » au tableau et Xiao Ming a rempli les blancs.

Depuis que Xiao Ming a appris l'addition en 10, il peut calculer ce problème entièrement par lui-même. Le code pour simuler le processus est le suivant :

public class Student
{
private String name = null;
public Student(String name)
{
// TODO Auto-generated constructor stub
this.name = name;
}
public void setName(String name)
{
this.name = name;
}
private int calcADD(int a, int b)
{
return a + b;
}
public void fillBlank(int a, int b)
{
int result = calcADD(a, b);
System.out.println(name + "心算:" + a + " + " + b + " = " + result);
}
}

<.>Lorsque Xiao Ming remplissait les espaces (fillBalnk), il a fait un calcul mental (clacADD) et a constaté que le résultat était 2, et a écrit le résultat dans la case vide. Le code du test est le suivant :

public class Test
{
public static void main(String[] args)
{
int a = ;
int b = ;
Student s = new Student("小明");
s.fillBlank(a, b);
}
}

Les résultats d'exécution sont les suivants :


Le calcul mental de Xiao Ming : 1 1 = 2


Ce processus Il est entièrement complété par l'objet instance de la classe Student seul et n'implique pas le mécanisme de rappel.


Chapitre 2. La recherche des ennuis par l'institutrice de maternelle

Pendant la pause, l'institutrice de maternelle a eu une idée soudaine et a écrit « 168 291 = » au tableau pour que Xiao Ming termine , puis est retourné au bureau.


Fleur à frotter ! Pourquoi tous les professeurs ont-ils des problèmes avec Xiao Ming ? C'est évidemment exagéré, d'accord ! À cette époque, il était évident que Xiao Ming ne pouvait plus s'appuyer sur le calcul mental comme ci-dessus. Lorsqu'il était confus, Xiao Hong, un camarade de classe, a remis une calculatrice qui ne pouvait calculer que l'addition (profiteur) ! ! ! ! Xiao Ming savait comment utiliser une calculatrice, il a donc utilisé la calculatrice pour calculer les résultats et remplir les blancs.


Le code de la calculatrice est :

public class Calculator
{
public int add(int a, int b)
{
return a + b;
}
}

Modifier la classe Etudiant et ajouter une méthode pour utiliser la calculatrice :

public class Student
{
private String name = null;
public Student(String name)
{
// TODO Auto-generated constructor stub
this.name = name;
}
public void setName(String name)
{
this.name = name;
}
@SuppressWarnings("unused")
private int calcADD(int a, int b)
{
return a + b;
}
private int useCalculator(int a, int b)
{
return new Calculator().add(a, b);
}
public void fillBlank(int a, int b)
{
int result = useCalculator(a, b);
System.out.println(name + "使用计算器:" + a + " + " + b + " = " + result);
}
}

Le code du test est le suivant :

public class Test
{
public static void main(String[] args)
{
int a = ;
int b = ;
Student s = new Student("小明");
s.fillBlank(a, b);
}
}

Les résultats d'exécution sont les suivants :


Xiao Ming utilise la calculatrice : 168 291 = 459


Ce processus n'implique toujours pas le mécanisme de rappel, mais une partie du travail de Xiao Ming a été transférée et est assistée par la calculatrice.


3. L'enseignante de maternelle est revenue


et a découvert que Xiao Ming avait terminé l'addition de trois chiffres. L'enseignante pensait que Xiao Ming était très intelligent et malléable. talent. Il a donc écrit "26549 16487 =" au tableau et a demandé à Xiao Ming de remplir les blancs avant le cours, puis est retourné au bureau.


Xiao Ming regardait les amis s'amuser en dehors de la classe et ne pouvait s'empêcher de se sentir triste. Si nous ne sortons pas pour jouer, cette récréation sera gâchée ! ! ! ! En regardant la calculatrice que Xiao Hong lui a remise, Xiao Ming a proposé un plan : laisser Xiao Hong le faire à sa place.


Xiao Ming a dit à Xiao Hong que le sujet était "26549 16487 = ", puis a souligné l'endroit spécifique où le résultat doit être rempli, puis est sorti jouer joyeusement.


Ici, au lieu d'implémenter Xiaohong séparément, nous considérons cette calculatrice qui ne peut effectuer que des additions et Xiaohong dans son ensemble, une super calculatrice qui peut calculer les résultats et remplir les blancs. Les paramètres qui doivent être transmis à ce super calculateur sont deux ajouts et le poste à remplir, et ces contenus doivent être informés à l'avance par Xiao Ming. Cela signifie que Xiao Ming veut révéler une partie de sa méthode à Xiao Hong. Le moyen le plus simple est de dire à Xiaohong la citation et les deux ajouts ensemble.


Par conséquent, la méthode add de la super calculatrice doit contenir deux opérandes et une référence à Xiao Ming lui-même. Le code est le suivant :

public class SuperCalculator
{
public void add(int a, int b, Student xiaoming)
{
int result = a + b;
xiaoming.fillBlank(a, b, result);
}
}

Du côté de Xiao Ming Désormais, il n'est plus nécessaire de faire du calcul mental ou d'utiliser une calculatrice, il n'y a donc qu'un moyen de demander de l'aide à Xiaohong. Le code est le suivant :

public class Student
{
private String name = null;
public Student(String name)
{
// TODO Auto-generated constructor stub
this.name = name;
}
public void setName(String name)
{
this.name = name;
}
public void callHelp (int a, int b)
{
new SuperCalculator().add(a, b, this);
}
public void fillBlank(int a, int b, int result)
{
System.out.println(name + "求助小红计算:" + a + " + " + b + " = " + result);
}
}

Le code du test est le suivant :

public class Test
{
public static void main(String[] args)
{
int a = ;
int b = ;
Student s = new Student("小明");
s.callHelp(a, b);
}
}

Le résultat en cours d'exécution est :

Xiao Ming demande de l'aide à Xiao Hong pour calculer : 26549 16487 = 43036
Le processus d'exécution est le suivant : Xiao Ming appelle la méthode add de Xiao Hong (nouveau SuperCalculator()) via sa propre méthode callHelp, et utilise sa propre référence

(ceci) comme paramètre lors de l'appel entrant, après que Xiaohong ait utilisé la calculatrice pour obtenir le résultat, elle a rappelé la méthode fillBlank de Xiaoming et a rempli le résultat dans l'espace vide du tableau.

Lumière, lumière, lumière ! À ce stade, la fonction de rappel apparaît officiellement. La méthode fillBlank de Xiao Ming est ce que nous appelons souvent la fonction de rappel.

De cette façon, on peut clairement voir que pour répondre à la question à remplir de l'enseignant, Xiao Ming n'a plus besoin d'attendre que l'ajout soit terminé et que le résultat est rempli au tableau avant de pouvoir suivre Xiao Ming. Les amis se sont amusés et la super calculatrice Xiaohong a fait le travail de remplir les blancs. Les avantages du retrait ont déjà commencé à se manifester.

Chapitre 4. Belle-mère à la porte

幼稚园的门口有一个头发花白的老婆婆,每天风雨无阻在那里摆着地摊卖一些快过期的垃圾食品。由于年纪大了,脑子有些糊涂,经常算不清楚自己挣了多少钱。有一天,她无意间听到了小明跟小伙伴们吹嘘自己如何在小红的帮助下与幼师斗智斗勇。于是,婆婆决定找到小红牌超级计算器来做自己的小帮手,并提供一包卫龙辣条作为报酬。小红经不住诱惑,答应了。

回看一下上一章的代码,我们发现小红牌超级计算器的add方法需要的参数是两个整型变量和一个Student对象,但是老婆婆她不是学生,是个小商贩啊,这里肯定要做修改。这种情况下,我们很自然的会想到继承和多态。如果让小明这个学生和老婆婆这个小商贩从一个父类进行继承,那么我们只需要给小红牌超级计算器传入一个父类的引用就可以啦。

不过,实际使用中,考虑到java的单继承,以及不希望把自身太多东西暴漏给别人,这里使用从接口继承的方式配合内部类来做。

换句话说,小红希望以后继续向班里的小朋友们提供计算服务,同时还能向老婆婆提供算账服务,甚至以后能够拓展其他人的业务,于是她向所有的顾客约定了一个办法,用于统一的处理,也就是自己需要的操作数和做完计算之后应该怎么做。这个统一的方法,小红做成了一个接口,提供给了大家,代码如下:

public interface doJob
{
public void fillBlank(int a, int b, int result);
}

因为灵感来自帮小明填空,因此小红保留了初心,把所有业务都当做填空(fillBlank)来做。

同时,小红修改了自己的计算器,使其可以同时处理不同的实现了doJob接口的人,代码如下:

public class SuperCalculator
{
public void add(int a, int b, doJob customer)
{
int result = a + b;
customer.fillBlank(a, b, result);
}
}

   

小明和老婆婆拿到这个接口之后,只要实现了这个接口,就相当于按照统一的模式告诉小红得到结果之后的处理办法,按照之前说的使用内部类来做,代码如下:

小明的:

public class Student
{
private String name = null;
public Student(String name)
{
// TODO Auto-generated constructor stub
this.name = name;
}
public void setName(String name)
{
this.name = name;
}
public class doHomeWork implements doJob
{
@Override
public void fillBlank(int a, int b, int result)
{
// TODO Auto-generated method stub
System.out.println(name + "求助小红计算:" + a + " + " + b + " = " + result);
}
}
public void callHelp (int a, int b)
{
new SuperCalculator().add(a, b, new doHomeWork());
}
}

   

老婆婆的:

public class Seller
{
private String name = null;
public Seller(String name)
{
// TODO Auto-generated constructor stub
this.name = name;
}
public void setName(String name)
{
this.name = name;
}
public class doHomeWork implements doJob
{
@Override
public void fillBlank(int a, int b, int result)
{
// TODO Auto-generated method stub
System.out.println(name + "求助小红算账:" + a + " + " + b + " = " + result + "元");
}
}
public void callHelp (int a, int b)
{
new SuperCalculator().add(a, b, new doHomeWork());
}
}

   

测试程序如下:

public class Test
{
public static void main(String[] args)
{
int a = ;
int b = ;
int c = ;
int d = ;
Student s = new Student("小明");
Seller s = new Seller("老婆婆");
s.callHelp(a, b);
s.callHelp(c, d);
}
}

运行结果如下:

小明求助小红计算:56 + 31 = 87

老婆婆求助小红算账:26497 + 11256 = 37753元 

最后的话

可以很明显的看到,小红已经把这件事情当做一个事业来做了,看她给接口命的名字doJob就知道了。

更多详解 JAVA的回调机制CallBack相关文章请关注PHP中文网!

Déclaration:
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn