Lambda-Ausdruck, eine neue Funktion von Java8. Mithilfe des Lambda-Ausdrucks können Sie die Schnittstellenimplementierung durch nur eine Funktion ersetzen, sich von anonymen inneren Klassen verabschieden und der Code sieht prägnanter und leichter verständlich aus.
Java8 hat auch einige andere neue Funktionen, die jedoch möglicherweise nicht auf Android verfügbar sind.
Studio 2.x und höher unterstützt den Jack-Compiler. Mit ihm können Sie den Lambda-Ausdruck von Java8 verwenden, es gibt jedoch keine Garantie, dass andere Funktionen verfügbar sind.
Hinweis: Das Android SDK integriert einen Teil des Quellcodes des JDK. Einigen Klassen im nativen JDK sind möglicherweise einige Implementierungen neuer Funktionen hinzugefügt, bei denen in Android jedoch nicht. Ein weiteres Beispiel ist das java.util.function-Paket von java8, das in niedrigeren Versionen nicht verfügbar ist
Sie können auch das Plug-in retrolambda verwenden, um den Lambda-Ausdruck von java8 zu unterstützen.
Fügen Sie die folgende Konfiguration hinzu
android { jackOptions { enabled true } compileOptions {//jack、retrolambda编译必需 sourceCompatibility JavaVersion.VERSION_1_8 targetCompatibility JavaVersion.VERSION_1_8 } }
, damit der Jack-Compiler den Lambda-Ausdruck unterstützen kann
Verwenden Sie die neueste Version 2.3 Studio, JDK 1.8-Umgebung, Gradle2.3 und die obige Konfiguration
Nach dem Testen kann es auch auf dem 4.4-Simulator
ausgeführt werden Konfigurationsdemo: http://www.php.cn/
retrolambda ist mit Java5, 6 und 7 unter Verwendung des Lambda-Ausdrucks kompatibel.
Die Konfiguration ist wie folgt
buildscript { repositories { jcenter() } dependencies { classpath 'com.android.tools.build:gradle:2.2.3' classpath 'me.tatarka:gradle-retrolambda:3.6.0' }} apply plugin: 'me.tatarka.retrolambda'android { defaultConfig { minSdkVersion 11 //这个没有硬性要求 } compileOptions {//jack、retrolambda编译必需 sourceCompatibility JavaVersion.VERSION_1_8 targetCompatibility JavaVersion.VERSION_1_8 }}
Hinweis: Viele Open-Source-Projekte verwenden immer noch Retrolambda
Zunächst müssen wir wissen, dass dieser Ausdruck als Ganzes einen „Objekttyp“ ausdrückt.
Code:
Runnable runnable = () -> System.out.println("hi, 我是 stone");runnable.run();
() ist eigentlich die Methodenparameterliste. Wenn hier keine Parameter übergeben werden, entspricht sie der Methode ohne Parameter . Da Runnable nur einen void run() hat, wird der Methodenname hier nicht geschrieben, sodass der Methodenname ignoriert wird.
-> Darauf folgt der Methodenkörper. Hier gibt es nur einen Druckcode. Sie können die geschweiften Klammern des Methodenkörpers weglassen: {}.
Lambda-Ausdruck mit Parametern und RückgabewertCode:Hinweis: Code wie „new Runnable“ wird hier ebenfalls weggelassen, da der Compiler eine automatische Typinferenz durchführt. Wenn Sie () direkt aufrufen -> >
button.setOnTouchListener((view, event)-> { if (event.getAction() == MotionEvent.ACTION_DOWN) { if (flag) { return true; } } return super.onTouchEvent(event); });Wenn Parameter vorhanden sind, übergeben Sie einfach den Parameternamen, und der Name kann nach Belieben definiert werden ; Typdefinition oder Es spielt keine Rolle, ob es nicht definiert ist. Wenn es nicht definiert ist, leitet der Compiler es automatisch ab.
Wenn ein Rückgabewert vorhanden ist, können Sie return im Methodenkörper verwenden. Sie können return auch weglassen, wenn nur ein Teil des Codes vorhanden ist, wie folgt:
button.setOnTouchListener((v, e) -> super.onTouchEvent(e));Passen Sie die Schnittstelle an und verwenden Sie sie Lambda-Ausdruck
interface IGetData<T> {//lambda只能用于单一方法类型匹配 T get();// T getOne(int i); //多个抽象方法,直接编译不过 }Definieren Sie die Methode mit den Parametern wie die oben definierte Schnittstelle:
void print(IGetData<String> data) { String msg = data.get(); System.out.println(msg); }Verwenden Sie Lambda Ausdruck als Parameter und Aufruf von print():
print(() -> "张三"); print(() -> { System.out.println("干活了"); return "李四"; });Ausgabe:
03-08 06:46:00.430 1510-1510/? I/System.out: 张三 03-08 06:46:00.430 1510-1510/? I/System.out: 干活了 03-08 06:46:00.430 1510-1510/? I/System.out: 李四Lambda-Ausdruck verwenden, um das Commander-Muster zu vereinfachen Funktionen und einfacher Implementierungsprozess von Commander-Muster:
Nun, zunächst müssen Sie eine Befehlsschnittstelle definieren: IAction
public interface IAction {//原 命令者 抽象出一个 执行命令的方法 void perform(); }und dann vier spezifische Befehlsklassen OpenAction, CloseAction, SaveAction und DeleteAction definieren.
CloseAction-Code:
public class CloseAction implements IAction { private Editor mEditor; public CloseAction(Editor editor) { this.mEditor = editor; } @Override public void perform() { this.mEditor.close(); } }Die anderen drei Implementierungen ähneln CloseAction. Editor-Klasse (Empfänger) definiert jede spezifische Implementierung des Empfangs von vier Befehlen:
public class Editor { public void save() { System.out.println("save"); } public void delete() { System.out.println("delete"); } public void open() { System.out.println("open"); } public void close() { System.out.println("close"); } }
Hinweis: Wenn verschiedene Editoren unterschiedliche Anforderungen an diese Befehle haben, wenn es unterschiedliche Implementierungen gibt, Sie können auch eine IEditor-Schnittstelle definieren und dann verschiedene Editoren implementieren. Auf diesen Punkt wird nicht näher eingegangenSchließlich gibt es einen Aufrufer, der eine Klasse sein kann:
public class Invoker { private IAction action; public Invoker(IAction action) { this.action = action; } public void invoke() { this.action.perform(); } }Client initiiert einen Befehl:
Editor editor = new Editor(); new Invoker(new OpenAction(editor)).invoke(); new Invoker(new CloseAction(editor)).invoke(); new Invoker(new SaveAction(editor)).invoke(); new Invoker(new DeleteAction(editor)).invoke();Der Aufrufer kann hier nicht als Klasse, sondern als Methode im Client definiert werden:
private void invoke(IAction action) { action.perform(); }Client initiiert einen Befehlsaufruf:
invoke(new OpenAction(editor)); invoke(new CloseAction(editor)); invoke(new SaveAction(editor)); invoke(new DeleteAction(editor));Lambda-Ausdruck Vereinfachte Version behält den Aufruf (Iaction-Aktion) in IAction, Editor und Client bei. Client initiiert einen Befehlsaufruf:
Editor editor = new Editor(); invoke(() -> editor.open()); invoke(() -> editor.close()); invoke(() -> editor.save()); invoke(() -> editor.delete());Auf diese Weise entfällt nach Verwendung des Lambda-Ausdrucks die Definition der spezifischen Befehlsklasse. Und Sie sehen auf einen Blick, welche Methode letztendlich ausgeführt wurde. Machen Sie sich keine Sorgen, dass das Schreiben auf diese Weise die ursprüngliche Trennung von Anforderung und Ausführung des Commander-Modus zerstört.
Denn invoke(() -> editor.open()); 209861d5cd2975725c730f519ed6ad71
invoke(new IAction() { @Override public void perform() { editor.open(); } });Wenn Sie die aufrufende Klasse Invoker beibehalten, wird sie wie folgt aufgerufen:
Das obige ist der detaillierte Inhalt vonDetaillierte Einführung in den Beispielcode von Lambda Expression, einer neuen Funktion von Android mit Java 8. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!