Вопрос был:
Как вернуть ответ от асинхронного вызова?
, который может быть интерпретирован как:
Как сделать синхронный асинхронный код синхронным?
Решение будет состоять в том, чтобы избежать обратных вызовов и использовать комбинацию Promises и async / await.
Я хотел бы привести пример для запроса Ajax.
(Хотя он может быть записан в Javascript, я предпочитаю писать его на Python и компилировать его в Javascript, используя Transcrypt . Это будет достаточно ясно.)
Позволяет сначала включить использование JQuery, чтобы
$
был доступен какS
:__pragma__ ('alias', 'S', '$')
Определить функцию, которая возвращает Promise, в этом случае вызов Ajax:
def read(url: str): deferred = S.Deferred() S.ajax({'type': "POST", 'url': url, 'data': { }, 'success': lambda d: deferred.resolve(d), 'error': lambda e: deferred.reject(e) }) return deferred.promise()
Использовать асинхронный код, как если бы он был синхронным:
async def readALot(): try: result1 = await read("url_1") result2 = await read("url_2") except Exception: console.warn("Reading a lot failed")
Полиморфизм
1. Static binding / Compile-Time binding / Early binding / Перегрузка метода (в том же классе)
2.
class Calculation {
void sum(int a,int b){System.out.println(a+b);}
void sum(int a,int b,int c){System.out.println(a+b+c);}
public static void main(String args[]) {
Calculation obj=new Calculation();
obj.sum(10,10,10); // 30
obj.sum(20,20); //40
}
}
class Animal {
public void move(){
System.out.println("Animals can move");
}
}
class Dog extends Animal {
public void move() {
System.out.println("Dogs can walk and run");
}
}
public class TestDog {
public static void main(String args[]) {
Animal a = new Animal(); // Animal reference and object
Animal b = new Dog(); // Animal reference but Dog object
a.move();//output: Animals can move
b.move();//output:Dogs can walk and run
}
}
Простыми словами:
Статический полиморфизм : имя одного и того же метода перегружено с другим типом или числом параметров в того же класса (другая подпись). Вызов целевого метода разрешается во время компиляции.
Динамический полиморфизм : тот же метод переопределен с той же сигнатурой в разных классах . Тип объекта, на который вызывается метод, неизвестен во время компиляции, но будет решаться во время выполнения.
Обычно перегрузка не считается полиморфизмом.
Из java tutorial page :
Подклассы класса могут определять свое собственное уникальное поведение и совместно использовать одни и те же функциональные возможности родительского class
blockquote>
Связывание относится к ссылке между вызовом метода и определением метода.
blockquote>На этом рисунке ясно показано, что является связыванием.
На этом рисунке вызов a1.methodOne () является привязкой к соответствующему определению методаOne (), и вызов «a1.methodTwo ()» является привязкой к соответствующему определению методаTwo ().
Для каждого вызова метода должно быть правильное определение метода. Это правило в java. Если компилятор не видит правильного определения метода для каждого вызова метода, он выдает ошибку.
Теперь переходим к статической привязке и динамической привязке в java.
Статическая привязка В Java:
Статическая привязка - это привязка, которая происходит во время компиляции. Его также называют ранним связыванием, потому что привязка происходит до того, как программа действительно запускает
blockquote>.
Статическое связывание может быть продемонстрировано, как показано на рисунке ниже.
На этом рисунке «a1» является ссылочной переменной типа A, указывающей на объект класса A. «a2» также является ссылочной переменной типа A, но указывает к объекту класса B.
Во время компиляции при связывании компилятор не проверяет тип объекта, к которому указывает конкретная ссылочная переменная. Он просто проверяет тип ссылочной переменной, через которую вызывается метод, и проверяет, существует ли в нем тип определения метода.
Например, для вызова метода «a1.method ()» в выше, компилятор проверяет, существует ли определение метода для метода () в классе А. Поскольку «a1» - это тип класса A. Аналогично, для вызова метода «a2.method ()» он проверяет, существует ли определение метода для метода () в классе A. Поскольку «a2» также является классом типа A. Он не проверяет, на какие объекты указывают «a1» и «a2». Этот тип привязки называется статическим связыванием.
Динамическое связывание в Java:
Динамическое связывание - это привязка, которая происходит во время выполнения. Это также называется поздним связыванием, потому что привязка происходит, когда программа фактически запущена.
blockquote>Во время выполнения для привязки используются реальные объекты. Например, для вызова «a1.method ()» в приведенном выше изображении будет вызван метод () фактического объекта, к которому указывается «a1». Для вызова «a2.method ()» используется метод () фактического объекта, на который указывает «a2». Этот тип привязки называется динамическим связыванием.
Динамическое связывание вышеуказанного примера может быть продемонстрировано, как показано ниже.
Ссылка статическое связывание-и-динамическое связывание-в-Java
Статический полиморфизм: где решение решить, какой метод выполнить, определяется во время компиляции. Метод перегрузки может быть примером этого.
Динамический полиморфизм: это решение о выборе того, какой метод выполнить, задается во время выполнения. Примером может служить метод Overriding.
Полиморфизм: Полиморфизм - это способность объекта принимать различные формы. Наиболее частое использование полиморфизма в ООП происходит, когда ссылка на родительский класс используется для ссылки на объект дочернего класса.
Полиморфизм динамической привязки / времени выполнения:
Время выполнения Полиморфизм, также известный как метод переопределения. В этом механизме, с помощью которого вызов переопределенной функции разрешен во время выполнения.
public class DynamicBindingTest {
public static void main(String args[]) {
Vehicle vehicle = new Car(); //here Type is vehicle but object will be Car
vehicle.start(); //Car's start called because start() is overridden method
}
}
class Vehicle {
public void start() {
System.out.println("Inside start method of Vehicle");
}
}
class Car extends Vehicle {
@Override
public void start() {
System.out.println("Inside start method of Car");
}
}
Выход:
Метод внутреннего запуска автомобиля
Статический связывание / полиморфизм времени компиляции:
Какой метод следует вызывать, решается только во время компиляции.
public class StaticBindingTest {
public static void main(String args[]) {
Collection c = new HashSet();
StaticBindingTest et = new StaticBindingTest();
et.sort(c);
}
//overloaded method takes Collection argument
public Collection sort(Collection c){
System.out.println("Inside Collection sort method");
return c;
}
//another overloaded method which takes HashSet argument which is sub class
public Collection sort(HashSet hs){
System.out.println("Inside HashSet sort method");
return hs;
}
}
Выход: Внутри коллекции sort metho
Перегрузка метода - это полиморфизм времени компиляции, давайте возьмем пример, чтобы понять концепцию.
class Person //person.java file
{
public static void main ( String[] args )
{
Eat e = new Eat();
e.eat(noodle); //line 6
}
void eat (Noodles n) //Noodles is a object line 8
{
}
void eat ( Pizza p) //Pizza is a object
{
}
}
В этом примере у Человека есть метод еды, который представляет, что он может либо есть пиццу, либо лапшу. То, что метод есть, перегружается, когда мы скомпилируем этот Person.java, компилятор разрешает вызов метода «e.eat (лапша) [который находится в строке 6] с определением метода, указанным в строке 8, который является методом, который берет лапшу в качестве параметра и весь процесс выполняется компилятором, так что это полиморфизм времени компиляции. Процесс замены вызова метода с помощью определения метода называется связыванием, в этом случае он выполняется компилятором, поэтому он называется ранним связыванием.
Перегрузка метода известна как статический полиморфизм, а также известна как полиморфизм времени компиляции или статическая привязка, поскольку перегруженные вызовы методов решаются во время компиляции на основе списка аргументов и ссылки, на которую мы вызываем метод.
И переопределение метода известно как динамический полиморфизм или простой полиморфизм или диспетчер времени выполнения или динамическое связывание, потому что переопределенный вызов метода разрешен во время выполнения.
Чтобы понять, почему это так, давайте возьмем пример Mammal
и Human
class
class Mammal {
public void speak() { System.out.println("ohlllalalalalalaoaoaoa"); }
}
class Human extends Mammal {
@Override
public void speak() { System.out.println("Hello"); }
public void speak(String language) {
if (language.equals("Hindi")) System.out.println("Namaste");
else System.out.println("Hello");
}
}
. Я включил вывод, а также байт-код в нижних строках кода
Mammal anyMammal = new Mammal();
anyMammal.speak(); // Output - ohlllalalalalalaoaoaoa
// 10: invokevirtual #4 // Method org/programming/mitra/exercises/OverridingInternalExample$Mammal.speak:()V
Mammal humanMammal = new Human();
humanMammal.speak(); // Output - Hello
// 23: invokevirtual #4 // Method org/programming/mitra/exercises/OverridingInternalExample$Mammal.speak:()V
Human human = new Human();
human.speak(); // Output - Hello
// 36: invokevirtual #7 // Method org/programming/mitra/exercises/OverridingInternalExample$Human.speak:()V
human.speak("Hindi"); // Output - Namaste
// 42: invokevirtual #9 // Method org/programming/mitra/exercises/OverridingInternalExample$Human.speak:(Ljava/lang/String;)V
. И посмотрев на выше кода мы видим, что байт-коды человеческих млекопитающих.speak (), human.speak () и human.speak («Hindi») совершенно разные, потому что компилятор способен различать их на основе списка аргументов и ссылки на класс. И поэтому перегрузка метода известна как статический полиморфизм.
Но байт-код для anyMammal.speak () и humanMammal.speak () тот же, поскольку в соответствии с компилятором оба метода вызываются по ссылке Mammal, но вывод для оба вызова метода различны, потому что во время выполнения JVM знает, какой объект держит ссылку, и JVM вызывает метод объекта, и поэтому метод Overriding известен как динамический полиморфизм.
Итак, из выше кода и байт-кода, ясно, что во время компиляции фазовый метод вызова рассматривается из ссылочного типа. Но во время выполнения метод будет вызываться из объекта, который хранится ссылка.
Если вы хотите узнать больше об этом, вы можете узнать больше о . Как перегрузка и переопределение метода обработки JVM внутри .
Полиморфизм времени компиляции (статическое связывание / раннее связывание): при статическом полиморфизме, если мы будем называть метод в нашем коде, то какое определение этого метода нужно называть фактически, разрешается только во время компиляции.
(или)
Во время компиляции Java знает, какой метод вызывать, проверяя сигнатуры метода. Таким образом, это называется полиморфизмом во время компиляции или статическим связыванием.
Динамический полиморфизм (поздний привяз / полиморфизм времени выполнения): во время выполнения Java ждет, пока среда выполнения не определит, на какой объект на самом деле указывается ссылка , Разрешение метода было принято во время выполнения, из-за этого мы называем полиморфизм времени выполнения.
Полиморфизм Dynamic (run time) - это полиморфизм, существовавший во время выполнения. Здесь компилятор Java не понимает, какой метод вызывается во время компиляции. Только JVM решает, какой метод вызывается во время выполнения.
Например,
Политический тип статического (времени компиляции) - это полиморфизм, проявляющийся во время компиляции. Здесь компилятор Java знает, какой метод вызывается. Перегрузка метода и переопределение метода с использованием статических методов; метод переопределения с использованием частных или окончательных методов является примером статического полиморфизма
Например,
Подробнее читайте в разделе «Что такое полиморфизм» (Google).
Полиморфизм относится к способности объекта вести себя по-разному для одного и того же триггера.
Статический полиморфизм (полиморфизм времени компиляции)
Динамический полиморфизм (полиморфизм времени выполнения)
метод перегрузки является примером compile time
/ static polymorphism
, поскольку привязка метода между вызовом метода и определением метода происходит во время компиляции, и это зависит от ссылки класса (ссылка, созданная во время компиляции, и переходит в стек).
метод переопределения является примером run time
/ dynamic polymorphism
, поскольку привязка метода между вызовом метода и определением метода происходит во время выполнения и зависит от объекта класса (объект, созданный во время выполнения, и переходит к куча).