ããããJDK 8ã®Lambdaãã¡ãã£ã¨ã¯åå¼·ããªãã¦ã¯ã¨æãã¤ã¤ãEclipseã¨ããç¡ãã¨ä½ãåºæ¥ãªãç¨åº¦ã«ã¯æ°å¼±ãªJavaããã°ã©ãå¢ãªã®ã§ãç°å¢ãä½ã£ã¦åå¼·ã§ããããã«è©¦ã¿ãã
ãããã¨
Trying Out Lambda Expressions in the Eclipse IDEã¨ãããEclipse IDEã§Lambdaå¼ã試ãããããªå¤§å¤æãé£ãè¨äºãããã®ã§ã³ã¬ãèªãã§ãµã³ãã«ã³ã¼ãã試ããã¾ããEclipse IDE with JDK 8 supportã®ãªã³ã¯ããJDK8対å¿ã®Eclipseããã¦ãã¼ãã§ããããã«ãªã£ã¦ããããã®è¨äºç¨ã«ç¨æãããEclipseã ã¨æãããããã¡ããã£ã¨è©¦ãåã«ã¯ã³ã¬ã§å åããã§ããã®ã§ã³ã¬ã使ãã
2014/06/11 è¿½è¨ Eclipse Kepler SR2のJava 8サポートのパッチ - kagamihogeの日記
2014/06/26 è¿½è¨ Java 8対å¿ã®Eclipse 4.4 Lunaããªãªã¼ã¹ããã¦ãã¾ãã
ãµã³ãã«åããã¦è©¦ãã¦ç解ããã®ãç®çãªã®ã§ãå²ã¨ã¨ãã¨ãã®ç¡ãè¨è¿°ã®ã¨ã³ããªã«ãªã£ã¦ã¾ãã詳ãããã¨ã¯ãªã³ã¯å ã®ã¨ã³ããªãèªãã§é ãããã
æºå
JDK8ã®ã¤ã³ã¹ãã¼ã«
ä½ã¯ã¨ãããJDK8ãç¡ãã¨ä½ãå§ã¾ããªãã
JDK 8 — Project KenaiããDownloadsãé¸ãã§JDK 8u20 Early Access Releases — Project Kenaiã«è¡ãåãã©ãããã©ã¼ã ãã¨ã®JDKãæã«å ¥ãããWindowsã®å ´åãã¤ã³ã¹ãã¼ã©ãããããã¨ã¯ãªãã¯ãã¦ããã ãã
java -versionã§ãã¼ã¸ã§ã³ç¢ºèªãã¦ã¿ãã
JDK8対å¿çã®Eclipse
Trying Out Lambda Expressions in the Eclipse IDEã®Eclipse IDE with JDK 8 supportãããã¦ã³ãã¼ãããã
Window -> Preferencesã®Java -> Compilerã§Compiler compliance levelã1.8(BETA)ãªãã¨ã確èªããã
Javaããã¸ã§ã¯ãä½ææã«JavaSE-1.8ã«ããã
æ¯è¼ççãã³ã¼ãã§è©¦ãã¦ã¿ãã
package jdk8test; import java.util.concurrent.Callable; public class Main { public static void main(String[] args) throws Exception { Callable<String> c = () -> "Hello from Callable"; System.out.println(c.call()); } }
åãã¾ããã
Lambdaãç¥ã
Trying Out Lambda Expressions in the Eclipse IDEã«æ²¿ã£ã¦ãµã³ãã«ã®ã½ã¼ã¹ã³ã¼ããåããã¦ãã£ã¦ã¿ããç¹ã«æããç¡ãéãããã®URLããã³ã¼ããæåãã¦ãã¾ããã俺ãªãã«å¤ãã¦ããå ´æãããã¾ãã
The Hello Application with Lambda Expressions
å¼æ°2ã¤åã£ã¦Stringè¿ãã¡ã½ããããã£ãæã¤interfaceãä½ããã§ããããLambdaå¼ã§æ§ç¯ãããé¢æ°åã¤ã³ã¿ã¼ãã§ã¼ã¹[Functional Interface]ã¨ãè¨ããããã
package jdk8test; public class Hello { interface HelloService { String hello(String firstname, String lastname); } public static void main(String[] args) { HelloService helloService = (String firstname, String lastname) -> { String hello = "Hello " + firstname + " " + lastname; return hello; }; System.out.println(helloService.hello("kagami", "hoge")); } }
Hello kagami hogeã¨è¡¨ç¤ºããããæ§æ¥ã¯âã®ããã«æ¸ãã¦ã¾ãããã£ã¦ã¤ãã§ãããã
HelloService helloService2 = new HelloService() { @Override public String hello(String firstname, String lastname) { String hello = "Hello " + firstname + " " + lastname; return hello; } }; System.out.println(helloService2.hello("kagami", "hoge"));
Using Lambda Expressions with Some Common Functional Interfaces
JDKæ¨æºã©ã¤ãã©ãªã®Functional Interfaceã§Lambdaå¼ä½¿ããä¾ã¯ãããªæãã£ãããã¨ãæ¸ãã¦ããã
FileFilterã¤ã³ã¿ã¼ãã§ã¼ã¹ããµã³ãã«ã¯é·ããã§ãããã¼ã«çãããã
package jdk8test; import java.io.File; import java.io.FileFilter; import java.nio.file.Paths; public class FileFilterTest { public static void main(String[] args) { FileFilter fileFilter = (f) -> { return f.getName().lastIndexOf(".zip") > 0; }; //true System.out.println( fileFilter.accept(Paths.get("C", "java", "jdk1.8.0", "src.zip").toFile())); //false System.out.println( fileFilter.accept(Paths.get("C", "java", "jdk1.8.0", "README.html").toFile())); }; }
åã¯ãããªæããªãã§ã大åã¹ãããªããæãã
FileFilter fileFilter2 = new FileFilter() { @Override public boolean accept(File pathname) { // ... return false; } };
ãã¨ããã¾ã¼ã«ã³ã³ãã³ãã¢ã·ã¹ããä¸æããããªããã¨ããããã¾ãä»æ¹ãªããã
Runnableã¤ã³ã¿ãã§ã¼ã¹ã
package jdk8test; public class HelloRunnable { public static void main(String args[]) { (new Thread(() -> { System.out.println("Hello from a thread"); })).start(); } }
åã¯ãããªæãã§ãããã
new Thread(new Runnable() { @Override public void run() { System.out.println("Hello from a thread"); } }).start();
Comparatorã¤ã³ã¿ãã§ã¼ã¹ã
package jdk8test; public class Employee { public String name; public Employee(String name) { super(); this.name = name; } }
package jdk8test; import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; import java.util.List; public class EmployeeSort { public static void main(String[] args) { Employee e1 = new Employee("kagami"); Employee e2 = new Employee("hoge"); Employee e3 = new Employee("foobar"); List<Employee> list = new ArrayList<>(); Collections.addAll(list, e1, e2, e3); Collections.sort(list, (x, y) -> x.name.compareTo(y.name)); for (Employee e : list) { System.out.println(e.name); } } }
foobar, hoge, kagamiã¨è¡¨ç¤ºããããåã¯âãªæããªãã§ãã³ã¬ã¯çããªã£ã¦ãæå¼·ãã
Collections.sort(list, new Comparator<Employee>() { @Override public int compare(Employee x, Employee y) { return x.name.compareTo(y.name); } });
How Are the Target Type and Lambda Parameter Type Inferred?
returnã«Lambdaå¼ã使ããfunctional interfaceã§ãªãã¨ãã¡ãããã
package jdk8test; public class HelloRunnable2 { public static Runnable getRunnable() { return () -> { System.out.println("Hello from a thread"); }; } public static void main(String args[]) { new Thread(getRunnable()).start(); } }
Lambda Expressions as Target Typesã¨ãããä¾ã¯ã¡ãã£ã¨è¤éã
package jdk8test; import java.util.concurrent.Callable; public class HelloCallable2 { public static void main(String[] args) { try { Callable<Runnable> c = () -> () -> { System.out.println("Hello from Callable"); }; c.call().run(); } catch (Exception e) { System.err.println(e.getMessage()); } } }
() -> () ->ã¨ãããæç¹ã§åå¿è ã®ä¿ºã¯å²ãã¨ç®ã¾ãããããã®ã§ãä¸æ©ãã¤é²ããã¨ã«ããã
ã¾ããæ§æ¥ã¯ãããªæãã«ãã¦æ¸ããé·ãâ¦â¦
Callable<Runnable> c3 = new Callable<Runnable>() { @Override public Runnable call() throws Exception { return new Runnable() { @Override public void run() { System.out.println("Hello from Callable"); } }; } };
次ãå¤å´ã®new Callable
Callable<Runnable> c4 = () -> { return new Runnable() { @Override public void run() { System.out.println("Hello from Callable"); } }; };
次ãreturn new Runnableã®ã¨ããã¯Lambdaå¼ã§ãã®ããã«æ¸ããã
Callable<Runnable> c5 = () -> { return () -> { System.out.println("Hello from Callable"); }; };
ã§ãæçµçã«ãããªãã
Callable<Runnable> c6 = () -> () -> { System.out.println("Hello from Callable"); };
é åã®åæåããããªé¢¨ã«ãããã
package jdk8test; import java.util.concurrent.Callable; public class CallableArray { public static void main(String[] args) throws Exception { Callable<String>[] c = new Callable[] { () -> "Hello from Callable a", () -> "Hello from Callable b", () -> "Hello from Callable c" }; System.out.println(c[1].call()); } }
Lambdaå¼ã®ãã£ã¹ããä¸è¨ã®ã³ã¼ãã¯The method doPrivileged(PrivilegedAction
String user = AccessController.doPrivileged(() -> System.getProperty("user.name"));
ãã®å ´åã¯ä¸è¨ã®ããã«æ¸ãã
String user = AccessController.doPrivileged((PrivilegedAction<String>)() -> System.getProperty("user.name"));
åèæ¼ç®åã§è¿ã£ã¦ãããã®ãLambdaå¼ã§æ¸ãã
package jdk8test; import java.util.concurrent.Callable; public class HelloCallableConditional { public static void main(String[] args) throws Exception { boolean flag = true; Callable<String> c = flag ? (() -> "Hello from Callable: flag true") : (() -> "Hello from Callable: flag false"); System.out.println(c.call()); } }
ã¡ã½ããã®ãªã¼ãã¼ãã¼ãã§Lambdaå¼ã使ãã
package jdk8test; import java.util.concurrent.Callable; public class HelloRunnableOrCallable { static String hello(Runnable r) { return "Hello from Runnable"; } static String hello(Callable c) { return "Hello from Callable"; } public static void main(String[] args) { String hello = hello(() -> "Hello Lambda"); System.out.println(hello); } }
ãããå®è¡ããã¨Hello from Callableã¨è¡¨ç¤ºãããããªãå¼æ°ãRunnableã§ã¯ãªãCallableãé¸ã°ããã®ãï¼ çç±ã¯ãCallable#callã¯è¿ãå¤ã®åãObjectã§ãRunnable#runã¯è¿ãå¤ã®åãvoidãªãããmainã§helloã¡ã½ããã«æ¸¡ãå¼æ°ã() -> "Hello Lambda"ãã¯ãæååãè¿ãä½ãããã§ãããã§ãvoid Runnable#runã¯ãã®è¦ä»¶ã«ãããããªãããObject Callable#callã¯ãããããã
thisã¯ãã®Lambdaå¼ãã©ãããã¦ãã¤ã³ã¹ã¿ã³ã¹ãæãã
package jdk8test; public class HelloLambda { Runnable r = () -> { System.out.println(this); }; public String toString() { return "Hello from Class HelloLambda"; } public static void main(String args[]) { new HelloLambda().r.run(); } }
Lambdaå¼ã®ãã©ã¡ã¼ã¿åã¨ãã¼ã«ã«å¤æ°åãè¡çªããå ´åãã³ã³ãã¤ã«ã¨ã©ã¼ã«ãªããä¸è¨ã®ã³ã¼ãã¯Lambdaå¼ã®e1, e2ã®ã¨ãã㧠Lambda expression's parameter e1 cannot redeclare another local variable defined in an enclosing scope. ãªã³ã³ãã¤ã«ã¨ã©ã¼ã«ãªãã
Employee e1 = new Employee("kagami"); Employee e2 = new Employee("hoge"); List<Employee> list = new ArrayList<>(); Collections.addAll(list, e1, e2); Collections.sort(list, (Employee e1, Employee e2) -> e1.name.compareTo(e2.name));
ç¡åã¡ã½ãããå®ç¾©ãã代ããã«æ¢åã®ã¡ã½ãããåç §ãããã
ã¾ãä¸ã®æ¹ã®sortã®ä¾ã§ä½¿ã£ãEmployeeã«staticã¡ã½ããcompareByNameãã¤ããã
public class Employee { ... public static int compareByName(Employee x, Employee y) { return x.name.compareTo(y.name); } }
ããæ¸ãã®ãã
Collections.sort(list, (x, y) -> x.name.compareTo(y.name));
ããæ¸ããã
Collections.sort(list, Employee::compareByName);
non-staticã®å ´åã¯ã©ãããEmployeeã«ã¡ã½ããã追å ããã
public class Employee { ... public int compareByNameNonStatic(Employee x, Employee y) { return x.name.compareTo(y.name); } }
ãã®å ´åã¯ã¤ã³ã¹ã¿ã³ã¹çµç±ã«ãªãã
Employee dummy = new Employee(""); Collections.sort(list, dummy::compareByNameNonStatic);
Virtual Extension Methods - Lambdaå¼ãããªããã©JDK8ã®æ°æ©è½ã¦ãã¨ã§ãã®è¨äºã§ç´¹ä»ããã¦ããã
ãã£ããè¨ãã°Interfaceã«ããã©ã«ãã®å®è£
ãæãããããã
public class VirtualExtension { interface Hoge { default String getString() { return "Hoge"; } } public static void main(String[] args) { Hoge h = new Hoge() {}; System.out.println(h.getString()); } }
JDK8ã®java.util.Map
public interface Map<K,V> { int size(); ... boolean isEmpty(); ... default boolean remove(Object key, Object value) { Object curValue = get(key); if (!Objects.equals(curValue, value) || (curValue == null && !containsKey(key))) { return false; } remove(key); return true; } .... default V replace(K key, V value) { return containsKey(key) ? put(key, value) : null; } }