Groovy 2.0What’s up doc?  Guillaume Laforge  Groovy Project Manager        @glaforge                           1
Groovy 2.0What’s up doc?  Guillaume Laforge  Groovy Project Manager        @glaforge                           1
Guillaume Laforge •   Groovy Project Manager at VMware     •Initiator of the Grails framework     •Creator of the Gaelyk  ...
Agenda (1/2) • What’s new in Groovy 1.8?  • Nicer DSLs with command chains  • Runtime performance improvements  • GPars bu...
Agenda (2/2) • What’s cooking for Groovy 2.0?  • Alignments with JDK 7   • Project Coin (small language changes)   • Invok...
Command chains •   A grammar improvement allowing you     to drop dots & parens     when chaining method calls     • an ex...
Command chains       !pull!request!!on!github!                                   6
Command chains         Alternation of         method names       !pull!request!!on!github!                                ...
Command chains         Alternation of         method names       !pull!request!!on!github!                      and parame...
Command chains       !pull!request!!on!github!                                   6
Command chains        Equivalent to:       !pull!request!!on!github!       !!!!!(!!!!!!!).!!(!!!!!!)                      ...
Command chains    commit!2!!changes!on!!master!!branch                                           7
Command chains    !!!!!!(!).!!!!!!!(!!).!!!!!!!(!!!!!!)    commit!2!!changes!on!!master!!branch                           ...
Command chains                 8
Command chains   //!methods!with!multiple!arguments!(commas)                                                 8
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor                  ...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   //!leverage!nam...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   //!leverage!nam...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   //!leverage!nam...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   //!leverage!nam...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   //!leverage!nam...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   //!leverage!nam...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   //!leverage!nam...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   //!leverage!nam...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   !!!!(!!!!!!).!!...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   !!!!(!!!!!!).!!...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   !!!!(!!!!!!).!!...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   !!!!(!!!!!!).!!...
Command chains   //!methods!with!multiple!arguments!(commas)   take!coffee!!with!sugar,!milk!!and!liquor   !!!!(!!!!!!).!!...
GPars bundled •   GPars is bundled in the Groovy distribution •   GPars covers a wide range of parallel     and concurrent...
Closure enhancements • Closure annotation parameters •    Some more functional flavor     • composition         •         c...
Closure annotation parameters     @Retention(RetentionPolicy.RUNTIME)     @interface!Invariant!{!!!!     !!!!Class!value()...
Closure annotation parameters     @Retention(RetentionPolicy.RUNTIME)     @interface!Invariant!{!!!!     !!!!Class!value()...
Closure memoization                      12
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()                                                  ...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms         ...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Closure memoization   def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize()   assert!plus(1,!2)!==!3!//!after!1000ms   assert...
Builtin JSON support  •   Consuming  •   Producing  •   Pretty-printing                        13
Builtin JSON support   import!groovy.json.*!   def!payload!=!new!URL(   !!!!"http://github.../json/commits/...").text!   d...
Builtin JSON supportimport!groovy.json.*!!def!json!=!new!JsonBuilder()!!json.person!{!!!!!!!!name!"Guillaume"!!!!age!34!!!...
Builtin JSON supportimport!groovy.json.*!!def!json!=!new!JsonBuilder()!!json.person!{!!!!           {!!!!!!!!name!"Guillau...
Builtin JSON support      import!groovy.json.*!      !      println!JsonOutput.prettyPrint(      !!!!{"person":{"name":"Gu...
New AST transformations• @Log                       • Controlling execution                                 •   @ThreadInt...
@Log•   Four different loggers can be injected    •@Log    •@Commons                   import!groovy.util.logging.*!    •@...
@Log•   Four different loggers can be injected    •@Log    •@Commons                   import!groovy.util.logging.*!    •@...
Controlling code execution  •   Your application may run user’s code      •what if the code runs in infinite loops or for t...
@ThreadInterrupt     @ThreadInterrupt     import!groovy.transform.ThreadInterrupt!     !     while!(true)!{     !!!!//!eat...
@ThreadInterrupt       @ThreadInterrupt       import!groovy.transform.ThreadInterrupt!       !       while!(true)!{   {   ...
@ToString•       Provides a default toString() method to your types•       Available annotation options    •    includeNam...
@EqualsAndHashCode•   Provides default implementations for equals() and    hashCode() methods            import!groovy.tra...
@TupleConstructor•   Provides a «classical» constructor with all properties•   Several annotation parameter options availa...
@InheritConstructors•   Classes like Exception are painful when extended,    as all the base constructors should be replic...
@InheritConstructors•   Classes like Exception are painful when extended,    as all the base constructors should be replic...
Miscelanous •   Compilation customizers •   Java 7 diamond operator •   Slashy and dollar slashy strings •   New GDK metho...
Compilation customizers •   Ability to apply some customization to the Groovy     compilation process •   Three available ...
Imports customizer   def!configuration!=!new!CompilerConfiguration()   !   def!custo!=!new!ImportCustomizer()   custo.addS...
What’sin storefor 2.0?
2.0Around the corner...
Groovy 2.0 •   A more modular Groovy •   Java 7 alignements: Project Coin     • binary literals     • underscore in litera...
Groovy Modularity •   Groovy’s «all» JAR weighs in at 6 MB • Nobody needs everything  • Template engine, Ant scripting, Sw...
The new JARs •   A smaller groovy.jar: 3MB •   Modules     •console                    •   sql     •docgenerator          ...
Extension modules •   Create your own module     •contribute instance extension methods  package!foo  class!StringExtensio...
Extension modules •   Create your own module     •contribute instance extension methods   Same structure                  ...
Extension modules •   Create your own module     •contribute class extension methods              package!foo             ...
Extension module descriptor moduleName!=!stringExtensions moduleVersion!=!1.0 //!coma>separated!list!of!classes extensionC...
Java 7 / JDK 7  •   Project Coin and InvokeDynamic                                       36
Binary literals•   We had decimal, octal and hexadecimal notations for    number literals•   We can now use binary represe...
Underscore in literals•   Now we can also add underscores    in number literals for more readability    long!creditCardNum...
Multicatch•   One block for multiple exception caught    •rather than duplicating the block        try!{        !!!!/*!......
InvokeDynamic • Groovy 2.0 supports JDK 7’s invokeDynamic  • compiler has a flag for compiling against JDK 7  • might use t...
Static Type Checking  •   Goal: make the Groovy compiler «grumpy»!      •   and throw compilation errors (not at runtime) ...
Typos in a variable or method import!groovy.transform.TypeChecked ! void!method()!{} ! @TypeChecked!test()!{ !!!!//!Cannot...
Typos in a variable or method import!groovy.transform.TypeChecked ! void!method()!{} ! @TypeChecked!test()!{ !!!!//!Cannot...
Typos in a variable or method                                         Annotation can be at import!groovy.transform.TypeChe...
Wrong assignments     //!cannot!assign!value!of!type...!to!variable...     int!x!=!new!Object()     Set!set!=!new!Object()...
Wrong assignments     //!cannot!assign!value!of!type...!to!variable...     int!x!=!new!Object()     Set!set!=!new!Object()...
Wrong return types     //!checks!if/else!branch!return!values     @TypeChecked     int!method()!{     !!!!if!(true)!{!Stri...
Wrong return types     //!checks!if/else!branch!return!values     @TypeChecked     int!method()!{                 Compilat...
Type inference     @TypeChecked!test()!{     !!!!def!name!=!"!!Guillaume!!"     !     !!!!//!String!type!infered!(even!ins...
Statically checked & dyn. meth.       @TypeChecked       String!greeting(String!name)!{       !!!!//!call!method!with!dyna...
Instanceof checks   @TypeChecked!   void.test(Object!val)!{   !!!!if!(val!instanceof.String)!{   !!!!!!!!println!val.toUpp...
Instanceof checks                                             No need   @TypeChecked!                                     ...
Instanceof checks                                              No need    @TypeChecked!                                   ...
Lowest Upper Bound •   Represents the lowest «super» type classes     have in common     •may be virtual (aka «non-denotab...
Lowest Upper Bound •   Represents the lowest «super» type classes     have in common     •may be virtual (aka «non-denotab...
Lowest Upper Bound •   Represents the lowest «super» type classes     have in common     •may be virtual (aka «non-denotab...
Flow typing •   Static type checking shouldn’t complain even for bad coding     practicies which work without type checks ...
Gotcha: static checking vs dynamic  •   Type checking works at compile-time      •adding @TypeChecked doesn’t change behav...
Gotcha: runtime metaprogramming      @TypeChecked!      void.test()!{      !!!!Integer.metaClass.foo!=!{}      !!!!123.foo...
Gotcha: runtime metaprogramming      @TypeChecked!      void.test()!{      !!!!Integer.metaClass.foo!=!{}      !!!!123.foo...
Gotcha: runtime metaprogramming      @TypeChecked!      void.test()!{      !!!!Integer.metaClass.foo!=!{}      !!!!123.foo...
Gotcha: explicit type for closures  @TypeChecked!test()!{  !!!!["a",!"b",!"c"].collect!{  !!!!!!!!it.toUpperCase()!//!Not!...
Gotcha: explicit type for closures  @TypeChecked!test()!{  !!!!["a",!"b",!"c"].collect!{!String!it!>>  !!!!!!!!it.toUpperC...
Closure shared variables        @TypeChecked!test()!{        !!!!def!var!=!"abc"!!!!!!!        !!!!def!cl!=!{!var!=!new!Da...
Closure shared variables                           var assigned in the closure:                            «shared closure...
Closure shared variables                                    var assigned in the closure:                                  ...
Closure shared variables                                          var assigned in the closure:                            ...
Closure shared variables       class!A!!!!!!!!!!!{!void.foo()!{}!}       class!B!extends!A!{!void.bar()!{}!}       @TypeCh...
Closure shared variables       class!A!!!!!!!!!!!{!void.foo()!{}!}       class!B!extends!A!{!void.bar()!{}!}       @TypeCh...
Static Compilation  •   Given your Groovy code can be type checked...      we can as well compile it «statically»      •  ...
Static Compilation: advantages  •    You gain:      • Type safety       • thanks to static type checking        • static c...
Static Compilation: disadvantages  •   But you loose:      •   Dynamic features          •metaclass changes, categories, e...
Statically compiled & dyn methods       @CompileStatic       String!greeting(String!name)!{       !!!!//!call!method!with!...
What about performance? •   Comparisons between:     •   Java     •   Groovy static compilation (Groovy 2.0)     •   Groov...
What about performance?                                            Pi (π)     Binary                              Fibonacc...
Summary •   Main themes of the Groovy 2.0 release     •Modularity     •   Embark the JDK 7 enhancements         •Project C...
62
Thank you!                             ge                      e Lafor lopment         Gu illaum ovy Deve                 ...
Questions & Answers •   Got questions, really?                              Q&A                                    64
Image credits •   Bugs bunny: http://storage.canalblog.com/63/56/517188/47634843.jpeg •   Pills: http://www.we-ew.com/wp-c...
Upcoming SlideShare
Loading in...5
×

Groovy 1.8 and 2.0 at GR8Conf Europe 2012

3,981

Published on

Published in: Technology, Business
0 Comments
8 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total Views
3,981
On Slideshare
0
From Embeds
0
Number of Embeds
4
Actions
Shares
0
Downloads
63
Comments
0
Likes
8
Embeds 0
No embeds

No notes for slide

Transcript of "Groovy 1.8 and 2.0 at GR8Conf Europe 2012"

  1. 1. Groovy 2.0What’s up doc? Guillaume Laforge Groovy Project Manager @glaforge 1
  2. 2. Groovy 2.0What’s up doc? Guillaume Laforge Groovy Project Manager @glaforge 1
  3. 3. Guillaume Laforge • Groovy Project Manager at VMware •Initiator of the Grails framework •Creator of the Gaelyk and Caelyf toolkits • Co-author of Groovy in Action • Follow me on... •My blog: http://glaforge.appspot.com •Twitter: @glaforge •Google+: http://gplus.to/glaforge 2
  4. 4. Agenda (1/2) • What’s new in Groovy 1.8? • Nicer DSLs with command chains • Runtime performance improvements • GPars bundled for taming your multicores • Closure enhancements • Builtin JSON support • New AST transformations 3
  5. 5. Agenda (2/2) • What’s cooking for Groovy 2.0? • Alignments with JDK 7 • Project Coin (small language changes) • Invoke Dynamic support • Continued runtime performance improvements • Static type checking • Static compilation • Modularity 4
  6. 6. Command chains • A grammar improvement allowing you to drop dots & parens when chaining method calls • an extended version of top-level statements like println • Less dots, less parens allow you to •write more readable business rules •in almost plain English sentences • (or any language, of course) 5
  7. 7. Command chains !pull!request!!on!github! 6
  8. 8. Command chains Alternation of method names !pull!request!!on!github! 6
  9. 9. Command chains Alternation of method names !pull!request!!on!github! and parameters (even named ones) 6
  10. 10. Command chains !pull!request!!on!github! 6
  11. 11. Command chains Equivalent to: !pull!request!!on!github! !!!!!(!!!!!!!).!!(!!!!!!) 6
  12. 12. Command chains commit!2!!changes!on!!master!!branch 7
  13. 13. Command chains !!!!!!(!).!!!!!!!(!!).!!!!!!!(!!!!!!) commit!2!!changes!on!!master!!branch 7
  14. 14. Command chains 8
  15. 15. Command chains //!methods!with!multiple!arguments!(commas) 8
  16. 16. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor 8
  17. 17. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor //!leverage!named>args!as!punctuation 8
  18. 18. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good 8
  19. 19. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good //!closure!parameters!for!new!control!structures 8
  20. 20. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} 8
  21. 21. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} //!zero>arg!methods!require!parens 8
  22. 22. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} //!zero>arg!methods!require!parens select!all!!unique()!from!names 8
  23. 23. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} //!zero>arg!methods!require!parens select!all!!unique()!from!names //!possible!with!an!odd!number!of!terms 8
  24. 24. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} //!zero>arg!methods!require!parens select!all!!unique()!from!names //!possible!with!an!odd!number!of!terms take!3!!cookies 8
  25. 25. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor !!!!(!!!!!!).!!!!(!!!!!!!!!!!).!!!(!!!!!!) //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} //!zero>arg!methods!require!parens select!all!!unique()!from!names //!possible!with!an!odd!number!of!terms take!3!!cookies 8
  26. 26. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor !!!!(!!!!!!).!!!!(!!!!!!!!!!!).!!!(!!!!!!) //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good !!!!!(!!!!!!!!!!!!!!!).!!!!!!(!!!!) //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} //!zero>arg!methods!require!parens select!all!!unique()!from!names //!possible!with!an!odd!number!of!terms take!3!!cookies 8
  27. 27. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor !!!!(!!!!!!).!!!!(!!!!!!!!!!!).!!!(!!!!!!) //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good !!!!!(!!!!!!!!!!!!!!!).!!!!!!(!!!!) //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} !!!!!(!!).!!!!(!!).!!!!(!!) //!zero>arg!methods!require!parens select!all!!unique()!from!names //!possible!with!an!odd!number!of!terms take!3!!cookies 8
  28. 28. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor !!!!(!!!!!!).!!!!(!!!!!!!!!!!).!!!(!!!!!!) //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good !!!!!(!!!!!!!!!!!!!!!).!!!!!!(!!!!) //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} !!!!!(!!).!!!!(!!).!!!!(!!) //!zero>arg!methods!require!parens select!all!!unique()!from!names !!!!!!(!!!).!!!!!!!!.!!!!(!!!!!) //!possible!with!an!odd!number!of!terms take!3!!cookies 8
  29. 29. Command chains //!methods!with!multiple!arguments!(commas) take!coffee!!with!sugar,!milk!!and!liquor !!!!(!!!!!!).!!!!(!!!!!!!!!!!).!!!(!!!!!!) //!leverage!named>args!as!punctuation check!that:!margarita!!tastes!good !!!!!(!!!!!!!!!!!!!!!).!!!!!!(!!!!) //!closure!parameters!for!new!control!structures given!{}!!when!{}!!then!{} !!!!!(!!).!!!!(!!).!!!!(!!) //!zero>arg!methods!require!parens select!all!!unique()!from!names !!!!!!(!!!).!!!!!!!!.!!!!(!!!!!) //!possible!with!an!odd!number!of!terms take!3!!cookies !!!!(!). 8
  30. 30. GPars bundled • GPars is bundled in the Groovy distribution • GPars covers a wide range of parallel and concurrent paradigms •actors, fork/join, map/filter/reduce, dataflow, agents •parallel arrays, executors, STM, and more... • And you can use it from plain Java as well! 9
  31. 31. Closure enhancements • Closure annotation parameters • Some more functional flavor • composition • compose several closures into one single closure • trampoline • avoid stack overflow errors for recursive algorithms • memoization • remember the outcome of previous closure invocations • currying improvements 10
  32. 32. Closure annotation parameters @Retention(RetentionPolicy.RUNTIME) @interface!Invariant!{!!!! !!!!Class!value()!//!a!closure!class } ! { @Invariant({.number.>=.0.}) class!Distance!{!!!! !!!!float!number!!!! !!!!String!unit }! ! def!d!=!new!Distance(number:!10,!unit:!"meters")! def!anno!=!Distance.getAnnotation(Invariant) def!check!=!anno.value().newInstance(d,!d) assert!check(d) 11
  33. 33. Closure annotation parameters @Retention(RetentionPolicy.RUNTIME) @interface!Invariant!{!!!! !!!!Class!value()!//!a!closure!class } ! { @Invariant({.number.>=.0.}) class!Distance!{!!!! !!!!float!number!!!! Poor- man’s GCon tracts !!!!String!unit }! ! def!d!=!new!Distance(number:!10,!unit:!"meters")! def!anno!=!Distance.getAnnotation(Invariant) def!check!=!anno.value().newInstance(d,!d) assert!check(d) 11
  34. 34. Closure memoization 12
  35. 35. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() 12
  36. 36. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms 12
  37. 37. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately 12
  38. 38. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms 12
  39. 39. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms assert!plus(2,!2)!==!4!//!return!immediately!! 12
  40. 40. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms assert!plus(2,!2)!==!4!//!return!immediately!! ! 12
  41. 41. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms assert!plus(2,!2)!==!4!//!return!immediately!! ! //!at!least!10!invocations!cached 12
  42. 42. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms assert!plus(2,!2)!==!4!//!return!immediately!! ! //!at!least!10!invocations!cached def!plusAtLeast!=!{!...!}.memoizeAtLeast(10) 12
  43. 43. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms assert!plus(2,!2)!==!4!//!return!immediately!! ! //!at!least!10!invocations!cached def!plusAtLeast!=!{!...!}.memoizeAtLeast(10) ! 12
  44. 44. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms assert!plus(2,!2)!==!4!//!return!immediately!! ! //!at!least!10!invocations!cached def!plusAtLeast!=!{!...!}.memoizeAtLeast(10) ! //!at!most!10!invocations!cached 12
  45. 45. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms assert!plus(2,!2)!==!4!//!return!immediately!! ! //!at!least!10!invocations!cached def!plusAtLeast!=!{!...!}.memoizeAtLeast(10) ! //!at!most!10!invocations!cached def!plusAtMost!=!{!...!}.memoizeAtMost(10). 12
  46. 46. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms assert!plus(2,!2)!==!4!//!return!immediately!! ! //!at!least!10!invocations!cached def!plusAtLeast!=!{!...!}.memoizeAtLeast(10) ! //!at!most!10!invocations!cached def!plusAtMost!=!{!...!}.memoizeAtMost(10). //!between!10!and!20!invocations!cached 12
  47. 47. Closure memoization def!plus!=!{!a,!b!>>!sleep!1000;!a!+!b!}.memoize() assert!plus(1,!2)!==!3!//!after!1000ms assert!plus(1,!2)!==!3!//!return!immediately assert!plus(2,!2)!==!4!//!after!1000ms assert!plus(2,!2)!==!4!//!return!immediately!! ! //!at!least!10!invocations!cached def!plusAtLeast!=!{!...!}.memoizeAtLeast(10) ! //!at!most!10!invocations!cached def!plusAtMost!=!{!...!}.memoizeAtMost(10). //!between!10!and!20!invocations!cached def!plusAtLeast!=!{!...!}.memoizeBetween(10,.20) 12
  48. 48. Builtin JSON support • Consuming • Producing • Pretty-printing 13
  49. 49. Builtin JSON support import!groovy.json.*! def!payload!=!new!URL( !!!!"http://github.../json/commits/...").text! def!slurper!=!new!JsonSlurper() def!doc!=!slurper.parseText(payload)! doc.commits.message.each!{!println!it!} 14
  50. 50. Builtin JSON supportimport!groovy.json.*!!def!json!=!new!JsonBuilder()!!json.person!{!!!!!!!!name!"Guillaume"!!!!age!34!!!!!!!!pets!"Hector",!"Felix"}!println!json.toString() 15
  51. 51. Builtin JSON supportimport!groovy.json.*!!def!json!=!new!JsonBuilder()!!json.person!{!!!! {!!!!!!!!name!"Guillaume" !!!!"person":!{!!!!!!!! !!!!!!!!"name":!"Guillaume",! !!!!!age!34!!!! !!!!!!!!"age":!34,!!!!!!!!!!!!pets!"Hector",!"Felix" !!!!!!!!"pets":![!!!!!!!!!!!!}! !!!!!!!!!!!!"Hector",!!!!!!!! !println!json.toString() !!!!!!!!!!!!"Felix"!!!!!!!! !!!!!!!!]!!!! !!!!} } 15
  52. 52. Builtin JSON support import!groovy.json.*! ! println!JsonOutput.prettyPrint( !!!!{"person":{"name":"Guillaume","age":34,!+! !!!!"pets":["Hector","Felix"]}}) ! {!!!! !!!!"person":!{!!!!!!!! !!!!!!!!"name":!"Guillaume",!!! !!!!!!!!"age":!34,!!!!!!!! !!!!!!!!"pets":![!!!!!!!!!!!! !!!!!!!!!!!!"Hector",!!!!!!!!!! !!!!!!!!!!!!"Felix"!!!!!!!! !!!!!!!!]!!!! !!!!} } 16
  53. 53. New AST transformations• @Log • Controlling execution • @ThreadInterrupt• @Field • @TimedInterrupt • @ConditionalInterrupt• @AutoClone • @InheritConstructor• @AutoExternalizable • @WithReadLock• @Canonical • @WithWriteLock • @ToString • @EqualsAndHashCode • @TupleConstructor • @ListenerList 17
  54. 54. @Log• Four different loggers can be injected •@Log •@Commons import!groovy.util.logging.*! •@Log4j ! @Log •@Slf4j class!Car!{!!!! !!!!Car()!{!!!!!!!! !!!!!!!!log.info!Car!constructed! !• Possible to implement !!!!} }! your own strategy ! def!c!=!new!Car() 18
  55. 55. @Log• Four different loggers can be injected •@Log •@Commons import!groovy.util.logging.*! •@Log4j ! @Log •@Slf4j Guarded w/ an if class!Car!{!!!! !!!!Car()!{!!!!!!!! !!!!!!!!log.info!Car!constructed! !• Possible to implement !!!!} }! your own strategy ! def!c!=!new!Car() 18
  56. 56. Controlling code execution • Your application may run user’s code •what if the code runs in infinite loops or for too long? •what if the code consumes too many resources? • 3 new transforms at your rescue •@ThreadInterrupt: adds Thread#isInterrupted checks so your executing thread stops when interrupted •@TimedInterrupt: adds checks in method and closure bodies to verify it’s run longer than expected •@ConditionalInterrupt: adds checks with your own conditional logic to break out from the user code 19
  57. 57. @ThreadInterrupt @ThreadInterrupt import!groovy.transform.ThreadInterrupt! ! while!(true)!{ !!!!//!eat!lots!of!CPU } 20 33
  58. 58. @ThreadInterrupt @ThreadInterrupt import!groovy.transform.ThreadInterrupt! ! while!(true)!{ { !!!!if!(Thread.currentThread.isInterrupted()) !!!!!!!!throw.new!InterruptedException() } !!!!//!eat!lots!of!CPU } 20 33
  59. 59. @ToString• Provides a default toString() method to your types• Available annotation options • includeNames, includeFields, includeSuper, excludes import!groovy.transform.ToString! ! @ToString class!Person!{!!!! !!!!String!name!!!! !!!!int!age }! ! println!new!Person(name:!Pete,!age:!15) //!=>!Person(Pete,!15) 21
  60. 60. @EqualsAndHashCode• Provides default implementations for equals() and hashCode() methods import!groovy.transform.EqualsAndHashCode! ! @EqualsAndHashCode class!Coord!{!!!! !!!!int!x,!y }! ! def!c1!=!new!Coord(x:!20,!y:!5) def!c2!=!new!Coord(x:!20,!y:!5)! ! assert!c1!==!c2 assert!c1.hashCode()!==!c2.hashCode() 22
  61. 61. @TupleConstructor• Provides a «classical» constructor with all properties• Several annotation parameter options available import!groovy.transform.TupleConstructor! ! @TupleConstructor! class!Person!{!!!! !!!!String!name!!!! !!!!int!age }! ! def!m!=!new!Person(Marion,!4)!!!!!! ! assert!m.name!==!Marion assert!m.age!!==!4 23
  62. 62. @InheritConstructors• Classes like Exception are painful when extended, as all the base constructors should be replicated class!CustomException!extends!Exception!{ !!!!CustomException()!!!!!!!!!!!!!!!!!!!!!!!!{!super()!!!!!!!} !!!!CustomException(String!msg)!!!!!!!!!!!!!!{!super(msg)!!!!} !!!!CustomException(String!msg,!Throwable!t)!{!super(msg,!t)!} !!!!CustomException(Throwable!t)!!!!!!!!!!!!!{!super(t)!!!!!!} } 24
  63. 63. @InheritConstructors• Classes like Exception are painful when extended, as all the base constructors should be replicated import!groovy.transform.* @InheritConstructors class!CustomException!extends!Exception!{ !!!!CustomException()!!!!!!!!!!!!!!!!!!!!!!!!{!super()!!!!!!!} !!!!CustomException(String!msg)!!!!!!!!!!!!!!{!super(msg)!!!!} !!!!CustomException(String!msg,!Throwable!t)!{!super(msg,!t)!} !!!!CustomException(Throwable!t)!!!!!!!!!!!!!{!super(t)!!!!!!} } 24
  64. 64. Miscelanous • Compilation customizers • Java 7 diamond operator • Slashy and dollar slashy strings • New GDK methods • (G)String to Enum coercion • Customizing the Groovysh prompt • Executing remote scripts 25
  65. 65. Compilation customizers • Ability to apply some customization to the Groovy compilation process • Three available customizers •ImportCustomizer •ASTTransformationCustomizer •SecureASTCustomizer • But you can implement your own 26
  66. 66. Imports customizer def!configuration!=!new!CompilerConfiguration() ! def!custo!=!new!ImportCustomizer() custo.addStaticStar(Math.name) configuration.addCompilationCustomizers(custo)! ! def!result!=!new!GroovyShell(configuration) !!!!!!!!!!!!!//!import!static!java.lang.Math.* !!!!.evaluate("!cos!PI/3!") !!!!!!!!!!!!!! 27
  67. 67. What’sin storefor 2.0?
  68. 68. 2.0Around the corner...
  69. 69. Groovy 2.0 • A more modular Groovy • Java 7 alignements: Project Coin • binary literals • underscore in literals • multicatch • JDK 7: InvokeDynamic • Static type checking • Static compilation 30
  70. 70. Groovy Modularity • Groovy’s «all» JAR weighs in at 6 MB • Nobody needs everything • Template engine, Ant scripting, Swing UI building... • Provide a smaller core •and several smaller JARs per feature • Provide hooks for setting up DGM methods, etc. 31
  71. 71. The new JARs • A smaller groovy.jar: 3MB • Modules •console • sql •docgenerator • swing •groovydoc • servlet •groovysh • templates •ant • test •bsf • testng •jsr-223 • json •jmx • xml 32
  72. 72. Extension modules • Create your own module •contribute instance extension methods package!foo class!StringExtension!{ !!!!static.introduce(String!self,!String!name)!{ !!!!!!!!"Hi!${name),!I’m!${self}" !!!!} } //!usage:!"Guillaume".introduce("Cédric") 33
  73. 73. Extension modules • Create your own module •contribute instance extension methods Same structure as Categories package!foo class!StringExtension!{ !!!!static.introduce(String!self,!String!name)!{ !!!!!!!!"Hi!${name),!I’m!${self}" !!!!} } //!usage:!"Guillaume".introduce("Cédric") 33
  74. 74. Extension modules • Create your own module •contribute class extension methods package!foo class!StaticStringExtension!{ !!!!static.hi(String!self)!{ !!!!!!!!"Hi!" !!!!} } //!usage:!String.hi() 34
  75. 75. Extension module descriptor moduleName!=!stringExtensions moduleVersion!=!1.0 //!coma>separated!list!of!classes extensionClasses!=!foo.StringExtension //!coma>separated!list!of!classes staticExtensionClasses!=!foo.StaticStringExtension 35
  76. 76. Java 7 / JDK 7 • Project Coin and InvokeDynamic 36
  77. 77. Binary literals• We had decimal, octal and hexadecimal notations for number literals• We can now use binary representations too int!x!=!0b10101111 assert!x!==!175 ! byte!aByte!=!0b00100001 assert!aByte!==!33 ! int!anInt!=!0b1010000101000101 assert!anInt!==!41285 37
  78. 78. Underscore in literals• Now we can also add underscores in number literals for more readability long!creditCardNumber!=!1234_5678_9012_3456L long!socialSecurityNumbers!=!999_99_9999L float!monetaryAmount!=!12_345_132.12 long!hexBytes!=!0xFF_EC_DE_5E long!hexWords!=!0xFFEC_DE5E long!maxLong!=!0x7fff_ffff_ffff_ffffL long!alsoMaxLong!=!9_223_372_036_854_775_807L long!bytes!=!0b11010010_01101001_10010100_10010010 38
  79. 79. Multicatch• One block for multiple exception caught •rather than duplicating the block try!{ !!!!/*!...!*/ }!catch(IOException!|!NullPointerException!e)!{ !!!!/*!one!block!to!treat!2!exceptions!*/ } 39
  80. 80. InvokeDynamic • Groovy 2.0 supports JDK 7’s invokeDynamic • compiler has a flag for compiling against JDK 7 • might use the invokeDynamic backport for < JDK 7 • Benefits • more runtime performance! • at least as fast as current «dynamic» Groovy •in the long run, will allow us to get rid of code! • call site caching, thanks to MethodHandles • metaclass registry, thanks to ClassValues • will let the JIT inline calls more easily 40
  81. 81. Static Type Checking • Goal: make the Groovy compiler «grumpy»! • and throw compilation errors (not at runtime) • Not everybody needs dynamic features all the time • think Java libraries scripting • Grumpy should... • tell you about your method or variable typos • complain if you call methods that don’t exist • shout on assignments of wrong types • infer the types of your variables • figure out GDK methods • etc... 41
  82. 82. Typos in a variable or method import!groovy.transform.TypeChecked ! void!method()!{} ! @TypeChecked!test()!{ !!!!//!Cannot!find!matching!method!metthhoood() !!!!metthhoood() ! !!!!def!name!=!"Guillaume" !!!!//!variable!naamme!is!undeclared !!!!println!naamme } 42
  83. 83. Typos in a variable or method import!groovy.transform.TypeChecked ! void!method()!{} ! @TypeChecked!test()!{ !!!!//!Cannot!find!matching!method!metthhoood() !!!!metthhoood() ! !!!!def!name!=!"Guillaume" Compilation !!!!//!variable!naamme!is!undeclared errors! !!!!println!naamme } 42
  84. 84. Typos in a variable or method Annotation can be at import!groovy.transform.TypeChecked class or method level ! void!method()!{} ! @TypeChecked!test()!{ !!!!//!Cannot!find!matching!method!metthhoood() !!!!metthhoood() ! !!!!def!name!=!"Guillaume" Compilation !!!!//!variable!naamme!is!undeclared errors! !!!!println!naamme } 42
  85. 85. Wrong assignments //!cannot!assign!value!of!type...!to!variable... int!x!=!new!Object() Set!set!=!new!Object() ! def!o!=!new!Object() int!x!=!o ! String[]!strings!=![a,b,c] int!str!=!strings[0] ! //!cannot!find!matching!method!plus() int!i!=!0 i!+=!1 43
  86. 86. Wrong assignments //!cannot!assign!value!of!type...!to!variable... int!x!=!new!Object() Set!set!=!new!Object() Compilation ! errors! def!o!=!new!Object() int!x!=!o ! String[]!strings!=![a,b,c] int!str!=!strings[0] ! //!cannot!find!matching!method!plus() int!i!=!0 i!+=!1 43
  87. 87. Wrong return types //!checks!if/else!branch!return!values @TypeChecked int!method()!{ !!!!if!(true)!{!String!} !!!!else!{!42!} } //!works!for!switch/case!&!try/catch/finally ! //!transparent!toString()!implied @TypeChecked String!greeting(String!name)!{ !!!!def!sb!=!new!StringBuilder() !!!!sb!<<!"Hi!"!<<!name } 44
  88. 88. Wrong return types //!checks!if/else!branch!return!values @TypeChecked int!method()!{ Compilation !!!!if!(true)!{!String!} error! !!!!else!{!42!} } //!works!for!switch/case!&!try/catch/finally ! //!transparent!toString()!implied @TypeChecked String!greeting(String!name)!{ !!!!def!sb!=!new!StringBuilder() !!!!sb!<<!"Hi!"!<<!name } 44
  89. 89. Type inference @TypeChecked!test()!{ !!!!def!name!=!"!!Guillaume!!" ! !!!!//!String!type!infered!(even!inside!GString) !!!!println!"NAME!=!${name.toUpperCase()}"! ! !!!!//!Groovy!GDK!method!support !!!!//!(GDK!operator!overloading!too) !!!!println!name.trim() ! !!!!int[]!numbers!=![1,!2,!3] !!!!//!Element!n!is!an!int !!!!for!(int!n!in!numbers)!{ !!!!!!!!println!n !!!!} } 45
  90. 90. Statically checked & dyn. meth. @TypeChecked String!greeting(String!name)!{ !!!!//!call!method!with!dynamic!behavior !!!!//!but!with!proper!signature !!!!generateMarkup(name.toUpperCase()) } ! //!usual!dynamic!behavior String!generateMarkup(String!name)!{ !!!!def!sw!=!new!StringWriter() !!!!new!MarkupBuilder(sw).html!{ !!!!!!!!body!{ !!!!!!!!!!!!div!name !!!!!!!!} !!!!} !!!!sw.toString() } 46
  91. 91. Instanceof checks @TypeChecked! void.test(Object!val)!{ !!!!if!(val!instanceof.String)!{ !!!!!!!!println!val.toUpperCase() !!!!}!else.if!(val!instanceof.Number)!{ !!!!!!!!println!"X"!*!val.intValue() !!!!} } 47
  92. 92. Instanceof checks No need @TypeChecked! for casts void.test(Object!val)!{ !!!!if!(val!instanceof.String)!{ !!!!!!!!println!val.toUpperCase() !!!!}!else.if!(val!instanceof.Number)!{ !!!!!!!!println!"X"!*!val.intValue() !!!!} } 47
  93. 93. Instanceof checks No need @TypeChecked! for casts void.test(Object!val)!{ !!!!if!(val!instanceof.String)!{ !!!!!!!!println!val.toUpperCase() !!!!}!else.if!(val!instanceof.Number)!{ !!!!!!!!println!"X"!*!val.intValue() !!!!} } Can call String#multiply(int) from the Groovy Development Kit 47
  94. 94. Lowest Upper Bound • Represents the lowest «super» type classes have in common •may be virtual (aka «non-denotable») @TypeChecked!test()!{ !!!!//!an!integer!and!a!BigDecimal !!!!return![1234,!3.14] } 48
  95. 95. Lowest Upper Bound • Represents the lowest «super» type classes have in common •may be virtual (aka «non-denotable») @TypeChecked!test()!{ !!!!//!an!integer!and!a!BigDecimal !!!!return![1234,!3.14] } Inferred return type: List<Number & Comparable> 48
  96. 96. Lowest Upper Bound • Represents the lowest «super» type classes have in common •may be virtual (aka «non-denotable») @TypeChecked!test()!{ !!!!//!an!integer!and!a!BigDecimal !!!!return![1234,!3.14] } Inferred return type: List<Number & Comparable> 48
  97. 97. Flow typing • Static type checking shouldn’t complain even for bad coding practicies which work without type checks @TypeChecked!test()!{ !!!!def!var!=!123!!!!!!!!!//!inferred!type!is!int !!!!int.x!=!var!!!!!!!!!!!//!var!is!an!int !!!!var!=!"123"!!!!!!!!!!!//!assign!var!with!a!String !!!!x!=!var.toInteger()!!!//!no!problem,!no!need!to!cast !!!!var!=!123 !!!!x!=!var.toUpperCase()!//!error,!var!is!int! } 49
  98. 98. Gotcha: static checking vs dynamic • Type checking works at compile-time •adding @TypeChecked doesn’t change behavior • do not confuse with static compilation • Most dynamic features cannot be type checked •metaclass changes, categories •dynamically bound variables (ex: script’s binding) • However, compile-time metaprogramming works •as long as proper type information is defined 50
  99. 99. Gotcha: runtime metaprogramming @TypeChecked! void.test()!{ !!!!Integer.metaClass.foo!=!{} !!!!123.foo() } 51
  100. 100. Gotcha: runtime metaprogramming @TypeChecked! void.test()!{ !!!!Integer.metaClass.foo!=!{} !!!!123.foo() } Not allowed: metaClass property is dynamic 51
  101. 101. Gotcha: runtime metaprogramming @TypeChecked! void.test()!{ !!!!Integer.metaClass.foo!=!{} !!!!123.foo() } Method not Not allowed: recognized metaClass property is dynamic 51
  102. 102. Gotcha: explicit type for closures @TypeChecked!test()!{ !!!!["a",!"b",!"c"].collect!{ !!!!!!!!it.toUpperCase()!//!Not!OK !!!!} } • A « Groovy Enhancement Proposal » to address the issue 52
  103. 103. Gotcha: explicit type for closures @TypeChecked!test()!{ !!!!["a",!"b",!"c"].collect!{!String!it!>> !!!!!!!!it.toUpperCase()!//!OK,!it’s!a!String !!!!} } • A « Groovy Enhancement Proposal » to address the issue 52
  104. 104. Closure shared variables @TypeChecked!test()!{ !!!!def!var!=!"abc"!!!!!!! !!!!def!cl!=!{!var!=!new!Date()!} !!!!cl() !!!!var.toUpperCase()!!//!Not!OK! } 53
  105. 105. Closure shared variables var assigned in the closure: «shared closure variable» @TypeChecked!test()!{ !!!!def!var!=!"abc"!!!!!!! !!!!def!cl!=!{!var!=!new!Date()!} !!!!cl() !!!!var.toUpperCase()!!//!Not!OK! } 53
  106. 106. Closure shared variables var assigned in the closure: «shared closure variable» @TypeChecked!test()!{ Impossible to !!!!def!var!=!"abc"!!!!!!! ensure the !!!!def!cl!=!{!var!=!new!Date()!} assignment !!!!cl()really happens !!!!var.toUpperCase()!!//!Not!OK! } 53
  107. 107. Closure shared variables var assigned in the closure: «shared closure variable» @TypeChecked!test()!{ Impossible to !!!!def!var!=!"abc"!!!!!!! ensure the !!!!def!cl!=!{!var!=!new!Date()!} assignment !!!!cl()really happens !!!!var.toUpperCase()!!//!Not!OK! } Only methods of the most specific compatible type (LUB) are allowed by the type checker 53
  108. 108. Closure shared variables class!A!!!!!!!!!!!{!void.foo()!{}!} class!B!extends!A!{!void.bar()!{}!} @TypeChecked!test()!{ !!!!def!var!=!new!A() !!!!def!cl!=!{!var!=!new!B()!} !!!!cl() !!!!var.foo()!!!//!OK! } 54
  109. 109. Closure shared variables class!A!!!!!!!!!!!{!void.foo()!{}!} class!B!extends!A!{!void.bar()!{}!} @TypeChecked!test()!{ !!!!def!var!=!new!A() !!!!def!cl!=!{!var!=!new!B()!} !!!!cl() !!!!var.foo()!!!//!OK! } var is at least an instance of A 54
  110. 110. Static Compilation • Given your Groovy code can be type checked... we can as well compile it «statically» • ie. generate the same byte code as javac • Also interesting for those stuck in JDK < 7 to benefit from performance improvements 55
  111. 111. Static Compilation: advantages • You gain: • Type safety • thanks to static type checking • static compilation builds upon static type checking • Faster code • as close as possible to Java’s performance • Code immune to «monkey patching» • metaprogramming badly used can interfere with framework code • Smaller bytecode size 56
  112. 112. Static Compilation: disadvantages • But you loose: • Dynamic features •metaclass changes, categories, etc. • Dynamic method dispatch •although as close as possible to «dynamic» Groovy 57
  113. 113. Statically compiled & dyn methods @CompileStatic String!greeting(String!name)!{ !!!!//!call!method!with!dynamic!behavior !!!!//!but!with!proper!signature !!!!generateMarkup(name.toUpperCase()) } ! //!usual!dynamic!behavior String!generateMarkup(String!name)!{ !!!!def!sw!=!new!StringWriter() !!!!new!MarkupBuilder(sw).html!{ !!!!!!!!body!{ !!!!!!!!!!!!div!name !!!!!!!!} !!!!} !!!!sw.toString() } 58
  114. 114. What about performance? • Comparisons between: • Java • Groovy static compilation (Groovy 2.0) • Groovy with primitive optimizations (Groovy 1.8+) • Groovy without optimizations (Groovy 1.7) 59
  115. 115. What about performance? Pi (π) Binary Fibonacci quadrature trees Java 188 ms 97 ms 3.6 s Static1.7 1.8 2.0 compilation 202 ms 101 ms 4.4 s Primitive optimizations 360 ms 111 ms 23.7 s No prim. optimizations 2590 ms 3220 ms 50.0 s 60
  116. 116. Summary • Main themes of the Groovy 2.0 release •Modularity • Embark the JDK 7 enhancements •Project Coin •Invoke Dynamic • Static aspects • Static type checking • Static compilation 61
  117. 117. 62
  118. 118. Thank you! ge e Lafor lopment Gu illaum ovy Deve Gro H ead of om ge@ gmail.c Emai l: glafor forge e :@ gla .to/glaforg Twitter : http://gplus spot.com + pp Google p://glaforge.a tt Blog: h 63
  119. 119. Questions & Answers • Got questions, really? Q&A 64
  120. 120. Image credits • Bugs bunny: http://storage.canalblog.com/63/56/517188/47634843.jpeg • Pills: http://www.we-ew.com/wp-content/uploads/2011/01/plan-b-pills.jpg • Chains: http://2.bp.blogspot.com/-GXDVqUYSCa0/TVdBsON4tdI/AAAAAAAAAW4/EgJOUmAxB28/s1600/breaking-chains5_copy9611.jpg • Slurp: http://www.ohpacha.com/218-532-thickbox/gamelle-slurp.jpg • Grumpy: http://mafeuilledechou.fr/__oneclick_uploads/2010/05/grumpy.jpg • Modularity: http://php.jglobal.com/blog/wp-content/uploads/2009/11/modularity.jpg • Agenda: http://www.plombiereslesbains.fr/images/stories/agenda.jpg • Java 7: http://geeknizer.com/wp-content/uploads/java7.jpg • Road Runner: http://newspaper.li/static/4ada046b7772f0612fec4e3840142308.jpg • Porky: http://joshuadsandy.files.wordpress.com/2011/05/porky-pig-5.jpg • Will E help: http://www.clipart-fr.com/data/clipart/looney/looney_004.jpg • Coyote road runner: http://www.jenkle.com/wp-content/uploads/2010/12/coyote-wallpaper1.jpg • Around the corner: http://3.bp.blogspot.com/-wvfO5NUbi8Q/TzBqTh4SOsI/AAAAAAAADOg/lRE9XVHGiOc/s1600/around-the-corner_large.jpg • Lube: http://images.motorcycle-superstore.com/ProductImages/OG/0000_Motul_Chain_Lube_Road_--.jpg 65
  1. A particular slide catching your eye?

    Clipping is a handy way to collect important slides you want to go back to later.

×