test/tools/javac/lambda/lambdaExecution/LambdaTranslationTest1.java

Tue, 14 May 2013 11:11:09 -0700

author
rfield
date
Tue, 14 May 2013 11:11:09 -0700
changeset 1752
c09b7234cded
parent 0
959103a6100f
permissions
-rw-r--r--

8012556: Implement lambda methods on interfaces as static
8006140: Javac NPE compiling Lambda expression on initialization expression of static field in interface
Summary: Lambdas occurring in static contexts or those not needing instance information should be generated into static methods. This has long been the case for classes. However, as a work-around to the lack of support for statics on interfaces, interface lambda methods have been generated into default methods. For lambdas in interface static contexts (fields and static methods) this causes an NPE in javac because there is no 'this'. MethodHandles now support static methods on interfaces. This changeset allows lambda methods to be generated as static interface methods. An existing bug in Hotspot (8013875) is exposed in a test when the "-esa" flag is used. This test and another test that already exposed this bug have been marked with @ignore.
Reviewed-by: mcimadamore

     1 /*
     2  * Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.  Oracle designates this
     8  * particular file as subject to the "Classpath" exception as provided
     9  * by Oracle in the LICENSE file that accompanied this code.
    10  *
    11  * This code is distributed in the hope that it will be useful, but WITHOUT
    12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
    13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
    14  * version 2 for more details (a copy is included in the LICENSE file that
    15  * accompanied this code).
    16  *
    17  * You should have received a copy of the GNU General Public License version
    18  * 2 along with this work; if not, write to the Free Software Foundation,
    19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
    20  *
    21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
    22  * or visit www.oracle.com if you need additional information or have any
    23  * questions.
    24  */
    26 /**
    27  * @test
    28  * @bug 8003639
    29  * @summary convert lambda testng tests to jtreg and add them
    30  * @run testng LambdaTranslationTest1
    31  */
    33 import org.testng.annotations.Test;
    35 import static org.testng.Assert.assertEquals;
    37 @Test
    38 public class LambdaTranslationTest1 extends LT1Sub {
    40     String cntxt = "blah";
    42     private static final ThreadLocal<Object> result = new ThreadLocal<>();
    44     private static void setResult(Object s) { result.set(s); }
    45     private static void appendResult(Object s) { result.set(result.get().toString() + s); }
    47     private static void assertResult(String expected) {
    48         assertEquals(result.get().toString(), expected);
    49     }
    51     static Integer count(String s) {
    52         return s.length();
    53     }
    55     static int icount(String s) {
    56         return s.length();
    57     }
    59     static void eye(Integer i) {
    60         setResult(String.format("I:%d", i));
    61     }
    63     static void ieye(int i) {
    64         setResult(String.format("i:%d", i));
    65     }
    67     static void deye(double d) {
    68         setResult(String.format("d:%f", d));
    69     }
    71     public void testLambdas() {
    72         TBlock<Object> b = t -> {setResult("Sink0::" + t);};
    73         b.apply("Howdy");
    74         assertResult("Sink0::Howdy");
    76         TBlock<String> b1 = t -> {setResult("Sink1::" + t);};
    77         b1.apply("Rowdy");
    78         assertResult("Sink1::Rowdy");
    80         for (int i = 5; i < 10; ++i) {
    81             TBlock<Integer> b2 = t -> {setResult("Sink2::" + t);};
    82             b2.apply(i);
    83             assertResult("Sink2::" + i);
    84         }
    86         TBlock<Integer> b3 = t -> {setResult("Sink3::" + t);};
    87         for (int i = 900; i > 0; i -= 100) {
    88             b3.apply(i);
    89             assertResult("Sink3::" + i);
    90         }
    92         cntxt = "blah";
    93         TBlock<String> b4 = t -> {setResult(String.format("b4: %s .. %s", cntxt, t));};
    94         b4.apply("Yor");
    95         assertResult("b4: blah .. Yor");
    97         String flaw = "flaw";
    98         TBlock<String> b5 = t -> {setResult(String.format("b5: %s .. %s", flaw, t));};
    99         b5.apply("BB");
   100         assertResult("b5: flaw .. BB");
   102         cntxt = "flew";
   103         TBlock<String> b6 = t -> {setResult(String.format("b6: %s .. %s .. %s", t, cntxt, flaw));};
   104         b6.apply("flee");
   105         assertResult("b6: flee .. flew .. flaw");
   107         TBlock<String> b7 = t -> {setResult(String.format("b7: %s %s", t, this.protectedSuperclassMethod()));};
   108         b7.apply("this:");
   109         assertResult("b7: this: instance:flew");
   111         TBlock<String> b8 = t -> {setResult(String.format("b8: %s %s", t, super.protectedSuperclassMethod()));};
   112         b8.apply("super:");
   113         assertResult("b8: super: I'm the sub");
   115         TBlock<String> b7b = t -> {setResult(String.format("b9: %s %s", t, protectedSuperclassMethod()));};
   116         b7b.apply("implicit this:");
   117         assertResult("b9: implicit this: instance:flew");
   119         TBlock<Object> b10 = t -> {setResult(String.format("b10: new LT1Thing: %s", (new LT1Thing(t)).str));};
   120         b10.apply("thing");
   121         assertResult("b10: new LT1Thing: thing");
   123         TBlock<Object> b11 = t -> {setResult(String.format("b11: %s", (new LT1Thing(t) {
   124             String get() {
   125                 return "*" + str.toString() + "*";
   126             }
   127         }).get()));};
   128         b11.apply(999);
   129         assertResult("b11: *999*");
   130     }
   132     public void testMethodRefs() {
   133         LT1IA ia = LambdaTranslationTest1::eye;
   134         ia.doit(1234);
   135         assertResult("I:1234");
   137         LT1IIA iia = LambdaTranslationTest1::ieye;
   138         iia.doit(1234);
   139         assertResult("i:1234");
   141         LT1IA da = LambdaTranslationTest1::deye;
   142         da.doit(1234);
   143         assertResult("d:1234.000000");
   145         LT1SA a = LambdaTranslationTest1::count;
   146         assertEquals((Integer) 5, a.doit("howdy"));
   148         a = LambdaTranslationTest1::icount;
   149         assertEquals((Integer) 6, a.doit("shower"));
   150     }
   152     public void testInner() throws Exception {
   153         (new In()).doInner();
   154     }
   156     protected String protectedSuperclassMethod() {
   157         return "instance:" + cntxt;
   158     }
   160     private class In {
   162         private int that = 1234;
   164         void doInner() {
   165             TBlock<String> i4 = t -> {setResult(String.format("i4: %d .. %s", that, t));};
   166             i4.apply("=1234");
   167             assertResult("i4: 1234 .. =1234");
   169             TBlock<String> i5 = t -> {setResult(""); appendResult(t); appendResult(t);};
   170             i5.apply("fruit");
   171             assertResult("fruitfruit");
   173             cntxt = "human";
   174             TBlock<String> b4 = t -> {setResult(String.format("b4: %s .. %s", cntxt, t));};
   175             b4.apply("bin");
   176             assertResult("b4: human .. bin");
   178             final String flaw = "flaw";
   180 /**
   181  Callable<String> c5 = () ->  "["+flaw+"]" ;
   182  System.out.printf("c5: %s\n", c5.call() );
   183  **/
   185             TBlock<String> b5 = t -> {setResult(String.format("b5: %s .. %s", flaw, t));};
   186             b5.apply("BB");
   187             assertResult("b5: flaw .. BB");
   189             cntxt = "borg";
   190             TBlock<String> b6 = t -> {setResult(String.format("b6: %s .. %s .. %s", t, cntxt, flaw));};
   191             b6.apply("flee");
   192             assertResult("b6: flee .. borg .. flaw");
   194             TBlock<String> b7b = t -> {setResult(String.format("b7b: %s %s", t, protectedSuperclassMethod()));};
   195             b7b.apply("implicit outer this");
   196             assertResult("b7b: implicit outer this instance:borg");
   198             /**
   199              TBlock<Object> b9 = t -> { System.out.printf("New: %s\n", (new LT1Thing(t)).str); };
   200              b9.apply("thing");
   202              TBlock<Object> ba = t -> { System.out.printf("Def: %s\n", (new LT1Thing(t) { String get() { return "*" + str.toString() +"*";}}).get() ); };
   203              ba.apply(999);
   205              */
   206         }
   207     }
   208 }
   210 class LT1Sub {
   211     protected String protectedSuperclassMethod() {
   212         return "I'm the sub";
   213     }
   214 }
   216 class LT1Thing {
   217     final Object str;
   219     LT1Thing(Object s) {
   220         str = s;
   221     }
   222 }
   224 interface LT1SA {
   225     Integer doit(String s);
   226 }
   228 interface LT1IA {
   229     void doit(int i);
   230 }
   232 interface LT1IIA {
   233     void doit(Integer i);
   234 }

mercurial