*

JDK8(java 8)の新機能のラムダ式の利用方法[その3:java8が用意している関数型インターフェース]

公開日: : 最終更新日:2015/05/02 Java


スポンサードリンク



[その1:概要]
[その2:関数型インターフェースを例としたラムダ式]
と説明させていただいておりますが、

今回はjava.util.functionパッケージに新機能として追加されている関数型インターフェースの説明をさせていただきます。

その1、その2とご覧いただいた方の感想として、引数無しの関数型インターフェースならRunnableインターフェースで事足りるけど
引数が・・・、戻り値が・・・でみたいな関数型インターフェースを作るの面倒ですよね。

そう、そうなんです。よく使う事が予想される関数型インターフェースは既に定義済みなんです。

C#のFuncデリゲートやActionデリゲートみたいに、言語がある程度のバリエーションの物を用意するのが筋だろう!、
と思うのが普通です。

C#のデリゲートをご存知無い方も、@FunctionalInterfaceの単一メソッドに置き換えて
想像していただければ感じがつかめると思います。

ちなみに、
C#のFuncデリゲートFuncは以下のように
Func()からFunc<T1, T2, T3, T4, TResult>
Txは引数のテンプレート、TResultは戻り値、引数は0個から4個までバリエーションが存在しており
デリゲートFuncは5種類定義されています。

ActionデリゲートはFuncの戻り値無し版で、こちらも5個定義されています。
Action()からAction<T1, T2, T3, T4>

このFunc、Actionデリゲートの存在のおかげで、ユーザがデリゲートを定義する手間が格段に減ります。

「Java 8」でも同じ様に単純な引数、戻り値の組み合わせの関数型インターフェースを、
ユーザがわざわざ定義する必要がないようになっています。

と、いつものことながら前置きが長くなりましたが、
本エントリーでは「ラムダ式ラムダ式(Lambda Expressions)」の利用を前提として「java.util.functionパッケージに用意されている関数型インターフェース」の説明を行わせていただきます。

なお、このインターフェース一覧は、Qiitaの「Java8 ラムダ式用のクラス」にございますので、一覧でご覧になりたい方はこちらもご覧いただければと思います。

「java.util.functionパッケージに用意されている関数型インターフェース」

用意されているインターフェースを羅列してもいいのですが、
それでは全てを覚える必要が生じます。必要な時に見るよ!と一人でツッコミ

実際はそうではないです。
その理由は、用意されているインターフェースの名前とメソッドは決められた命名規則で命名されているからです。

基準となる関数型インターフェース

命名規則の基準となるインターフェースは6つです。

Functionインターフェース

引数が一つで、戻り値が任意のテンプレート
処理を実行する時は、applyメソッドを呼び出します。

・定義
Function<T1, TResult>

・利用サンプル(引数がInteger、戻り値がStringの場合)

UnaryOperatorインターフェース

Functionの拡張インターフェース。引数も戻り値も同じ型のテンプレート
処理を実行する時は、Functionインターフェースと同じでapplyメソッドを呼び出します。

・定義
UnaryOperator<T1>

・利用サンプル(引数、戻り値がString)

Predicateインターフェース

戻り値がbooleanで、引数は任意のテンプレート
処理を実行する時は、testメソッドを呼び出します。

・定義
Predicate<T1>

・利用サンプル(引数がDate)

Supplierインターフェース

引数が無しで、戻り値は任意のテンプレート
処理を実行する時は、getメソッドを呼び出します。

・定義
Supplier<T1>

・利用サンプル(戻り値がArrayList<String>、本来はList<String>と指定すべきですが、分かりやすさのためにArrayListに会わせてます。)

Consumer

引数は任意のテンプレート、戻り値が無い場合に利用
処理を実行する時は、acceptメソッドを呼び出します。

・定義
Consumer<T1>

・利用サンプル(引数がString)

BinaryOperator

引数2つと、戻り値のテンプレートが同じ型の時に利用
処理を実行する時は、applyメソッドを呼び出します。

・定義
BinaryOperator<T1>

・利用サンプル(String型)

命名規則

「基準となる関数型インターフェース」に関連するインターフェースも用意されています。
プリミティブ型のint/long/doubleが引数や戻り値の場合には、専用のインタフェースも用意されています。
ラッパークラスとオートボクシング機能による性能劣化が起こらないように、こっち使って!との意図が見えますね。

ただし(int)、(int,int)、(long)、(long,long)、(double)、(double,double)
の引数の組み合わせのみ存在しています。それ以外はラッパークラスを利用する必要があります。

XXXは「基準となる関数型インターフェース」です。

  1. 全ての規則の基準は「基準となる関数型インターフェース」。このルールは他と併用
  2. 引数と戻り値の型が全て同じ関数型インターフェースで、例えばその型がlongの場合はLongBinaryOperator(この場合はBinaryOperatorしかありえない)
  3. 例えば引数がlongで戻り値がintの場合は、LongToIntXXX、ただし引数がテンプレートの場合はToIntXXX、戻り値がテンプレートor無しの場合はLongXXXのみとなる
  4. 引数が2つのテンプレートの場合はBiXXX(BinaryOperatorは当然対象外)。このルールは他と併用で場所はXXXの直前
  5. Consumer以外はint/long/doubleとテンプレートの組み合わせの引数のインターフェースは存在せず。ObjIntConsumer(テンプレートとintが引数)、ObjLongConsumer、ObjDoubleConsumerのみ例外

 

この規則で専用インターフェースの名前が類推できます。

命名規則でのインターフェース名の導出の例1

例1:引数が2つと、戻り値がintのインターフェース

まず命名規則1から「基準となる関数型インターフェース」を確定します。
引数が2つと、戻り値1つがintなので、3つの型が全て同じことからBinaryOperatorインターフェースが確定します。
次に命名規則2が当てはまりますので、最終的にIntBinaryOperatorという名前が確定します。

命名規則でのインターフェース名の導出の例2

例2:引数がそれぞれ異なるテンプレート2つ、戻り値がdouble

まず命名規則1から「基準となる関数型インターフェース」を確定します。
引数がテンプレートで、戻り値がdoubleなので
2つの引数の型が異なり、戻り値もdoubleなのでBinaryOperatorではない、
戻り値がbooleanでないのでPredicateでもない、
引数のどちらも型がdoubleでないのでUnaryOperatorでもない

消去法でFunctionインターフェースかなーとなります。
しかしFunctionは引数が1つしか指定できません。
そこは、命名規則4を適用してBiFunctionで条件をクリアーできるので、
「基準となる関数型インターフェース」はFunctionと確定します。
戻り値がdoubleなので、命名規則3よりToDoubleBiFunctionインターフェースという名前が確定します。

基準となる関数型インターフェースの派生インターフェース

基準となる関数型インターフェースの派生インターフェースを全て一覧で記載しようと思ったのですが
どう考えても表形式の方が見やすいですし、
「命名規則」をせっかく作ったのに意味が薄れるので、と変な事情でやめておきますが、
別エントリーとして作成いたします。

「JDK8(Java 8)の新機能のラムダ式の利用方法[その3:JDK8が用意している関数型インターフェース]」は以上となります。


スポンサードリンク



関連記事

Java8の新機能に完全対応のEclipseメジャーリリースとなる Eclipse 4.4 Luna (ルナ) が遂にリリース

Eclipse メジャーリリースとなる Eclipse 4.4 Luna (ルナ) が遂にリリースさ

記事を読む

Eclipse(4.3,4.4)の使い方[パースペクティブのツールバーのカスタマイズ(「コマンド・グループ可用性」と「ショートカット」タブ)]

「パースペクティブのカスタマイズ」画面には、以下の4つのタブが存在しております。 ツール・バ

記事を読む

Eclipse(4.3,4.4)の使い方[各画面エリアの名称とパースペクティブのビューのカスタマイズ]

本エントリーでは、Eclipse(Eclipse4.3,4.4)の各画面エリアの名称の説明と、ビュー

記事を読む

JUnit入門その3[Eclipse4.4のJUnitプラグインとMockフレームワークのJMockitの併用の基本]

JUnit入門その3ではMockフレームワークのJMockitを利用したテスト環境の構築と使い方につ

記事を読む

Mac(OS X)におけるJava8(jdk8)等のインストール、アップデート、アンインストール方法

Windowsとは異なりMac(OS X)ではJDKの管理(インストール、アンインストール)が難しい

記事を読む

Eclipse(4.3,4.4)のJava言語のリファクタリング機能の使い方[リファクタリングの説明と「名前変更」と「移動」]

本エントリーでは、Eclipse(4.3,4.4)の「リファクタリング」機能の使い方を説明させていた

記事を読む

Selenium入門その4[Selenium WebDriver(Java/Junit4)の基本コマンド]

前回はEclipse環境でSelenium WebDriverでJava/Junit4を利用したテス

記事を読む

Javaによる非同期処理入門その1[非同期処理の実装方法の概説]

Javaによる非同期処理に関するエントリーを前々から作成したいと思っていたのですが、ついに作成してみ

記事を読む

JUnit入門その5[DBUnitの概要説明]

前回エントリーでは「JUnit入門その4」と題してDBUnitをEclipseで動作させるための環境

記事を読む

Eclipse4.4(Java)におけるビルド・パス関係の設定方法[ビルド・パス上のソース・フォルダー]

Eclipse4.4(Java)におけるビルド関係のビルド・パス上のソース・フォルダーの利用方法を説

記事を読む

Message

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

Selenium入門その6[Selenium3でWebDriver(Java/Junit4)の環境を作成しEdge,Chrome,Firefoxで確認してみる]

Selenium3も3.0.1がリリースされましたし、今後は本格的にS

Selenium利用時のトラブルシューティング方法[クリック編]

Seleniumは便利なテスト自動化ツールですし、今後は更なる利用者の

Java8のラムダ式とStream APIを利用してコーディング量の削減サンプル集

Java8になりラムダ式と「Stream API」が利用できるようにな

Selenium入門その5[ページオブジェクトパターン(Page Object Design Pattern)を利用して変更に強いテストを作成する方法]

Selenium入門その2 では「UIマップファイル」と言う仕組みが

Javaによる非同期処理入門その1[非同期処理の実装方法の概説]

Javaによる非同期処理に関するエントリーを前々から作成したいと思って

→もっと見る

Optimization WordPress Plugins & Solutions by W3 EDGE
PAGE TOP ↑