Download - Google Guava & EMF @ GTUG Nantes
![Page 1: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/1.jpg)
Google Guava
2011/04/26
EclipseModelingFramework
&
Mikaël Barbero
![Page 2: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/2.jpg)
Introduction
1http://www.flickr.com/photos/drspam/295023450/
![Page 3: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/3.jpg)
About me
‣ Modeling consultant‣ Research engineer‣ Trainer‣ Conference Speaker‣ Language guy ;)
‣ Eclipse committer‣ Guava-OSGi packager‣ EMFPath lead
![Page 4: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/4.jpg)
Nantes
Paris
![Page 5: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/5.jpg)
Strategic members
![Page 6: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/6.jpg)
AcceleoEMFCompareATLGMFOCLMylyn IntentEEFSTP
Leading
![Page 7: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/7.jpg)
![Page 8: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/8.jpg)
![Page 9: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/9.jpg)
![Page 10: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/10.jpg)
![Page 11: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/11.jpg)
Available technologies
![Page 12: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/12.jpg)
GuavaOverview
2http://www.flickr.com/photos/slowburn/2986303105/
![Page 13: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/13.jpg)
http://www.flickr.com/photos/awagnon/1626025855/
![Page 14: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/14.jpg)
![Page 15: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/15.jpg)
Java library used internally @
Google for years
Superset of Google
Collections
About Guava
![Page 16: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/16.jpg)
About Guava
Apache License v2http://www.apache.org/licenses/LICENSE-2.0
![Page 17: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/17.jpg)
About Guava
2007 2008 2009 2010 2011
Google Collec
tions
v0.5
Google Collec
tions
v1Guava
r03
Guava r0
8
Frequent releases (quarterly base)Latest release (r09): April, 7th
![Page 18: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/18.jpg)
![Page 19: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/19.jpg)
![Page 20: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/20.jpg)
Why using Guava?
Simplexity
http://www.flickr.com/photos/gio_vencato/4941064345/
![Page 21: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/21.jpg)
Why using Guava?
http://www.flickr.com/photos/reway2007/3300379295/
![Page 22: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/22.jpg)
Why using Guava?
http://www.flickr.com/photos/funtik/1175522045/
Mainstream?
![Page 23: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/23.jpg)
Why using Guava?
Helping others
http://www.flickr.com/photos/thearches/4381959041/
![Page 24: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/24.jpg)
IO Networking Concurrency
Primitive types Collections
Inside Guava
GWT compatibility is tested (see @GwtCompatible)
![Page 25: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/25.jpg)
Comparison withApache Commons
http://stackoverflow.com/questions/4542550/what-are-the-big-improvements-between-guava-and-apache-equivalent-libraries
More ModernBetter
DesignedBetter
Supported
Java 5
Respects JDK contracts
Best practices and patterns
Orthogonality (@Beta to test designs)
Actively developed
(- commons 3.0)
Google depends on it
(e.g., Google Guice)
![Page 26: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/26.jpg)
Bestrep.
![Page 27: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/27.jpg)
Corest of the core
3http://www.flickr.com/photos/27384147@N02/5211738745/
![Page 28: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/28.jpg)
public class Person { final String name, nickname; final Movie favMovie;
@Override public boolean equals(Object object) { if (object instanceof Person) { Person that = (Person) object; return Objects.equal(this.name, that.name) && Objects.equal(this.nickname, that.nickname) && Objects.equal(this.favMovie, that.favMovie); } return false; }
@Override public int hashCode() { return Objects.hashCode(name, nickname, favMovie); }}
Objects class
Example from http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 29: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/29.jpg)
public class Person { final String name, nickname; final Movie favMovie;
//...
@Override public String toString() { return Objects.toStringHelper(this) .add("name", name) .add("nickname", nickname) .add("favMovie", favMovie) .toString(); }
public String preferredName() { return Objects.firstNonNull(nickname, name); }}
Objects class
Example from http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 30: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/30.jpg)
Preconditions
Defensive coding
if (state != State.PLAYABLE) { throw new IllegalStateException( "Can't play movie; state is " + state);}
Preconditions.checkState(state == State.PLAYABLE, "Can't play movie; state is %s", state);
Example from http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 31: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/31.jpg)
Preconditions
Defensive coding
public void setRating(StarRating rating) { if (rating == null) { throw new NullPointerException(); } this.rating = rating;}
public void setRating(StarRating rating) { this.rating = checkNotNull(rating);}
Example from http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 32: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/32.jpg)
Equivalences strategies
public interface Equivalence<T> { boolean equivalent(@Nullable T a, @Nullable T b); int hash(@Nullable T t);}
Equivalence equals = Equivalences.equals();Equivalence identity = Equivalences.identity();
Equivalence<String> elementEquivalence = ...;Equivalence<Iterable<String>> pairwise = Equivalences.pairwise(elementEquivalence);Collection<String> c1, c2;pairwise.equivalent(c1, c2);
![Page 33: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/33.jpg)
Suppliers
public interface Supplier<T> { T get();}
Supplier<String> s = ...;Supplier<String> memoizing = Suppliers.memoize(s);Supplier<String> expiring = Suppliers.memoizeWithExpiration(s, 100, TimeUnit.SECONDS);Supplier<String> ofInstance = Suppliers.ofInstance("Always returning");
![Page 34: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/34.jpg)
Throwables
Throwables.getCausalChain(throwable);Throwables.getRootCause(throwable);
Throwables.getStackTraceAsString(throwable);
Throwables.propagateIfInstanceOf(throwable, IOException.class);
Throwables.propagateIfPossible(throwable);
try { someMethodThatCouldThrowAnything();} catch (IKnowWhatToDoWithThisException e) { handle(e);} catch (Throwable t) { Throwables.propagateIfPossible(t); throw new RuntimeException("unexpected", t);}
![Page 35: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/35.jpg)
@Annotation
@Beta
@GwtCompatible @GwtIncompatible
@VisibleForTesting
![Page 36: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/36.jpg)
Strings
4http://www.flickr.com/photos/gernot/2554175292/
![Page 37: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/37.jpg)
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
CharMatcher
StringUtil example: allAscii, collapse, collapseControlChars, collapseWhitespace, indexOfChars, lastIndexNotOf, numSharedChars, removeChars, removeCrLf, replaceChars, retainAllChars, strip, stripAndCollapse, stripNonDigits, ...
Partial cross product of two notions: (a) what's a "matching" character?
(b) what to do with those matching characters?
CharMatcher:An instance of this type represents part (a), and the operation you invoke on it represents part (b).
+1
![Page 38: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/38.jpg)
Getting a CharMatcher
CharMatcher.is('x') CharMatcher.isNot('_') CharMatcher.oneOf("aeiou").negate() CharMatcher.inRange('a', 'z').or(inRange('A', 'Z'))
Subclass CharMatcher, implement matches(char c)
CharMatcher.WHITESPACE (Unicode) CharMatcher.JAVA_DIGIT CharMatcher.ASCIICharMatcher.ANY
Factory methods (examples)
Predefined constants(examples)
Now check out all that you can do...http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 39: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/39.jpg)
‣ boolean matchesAllOf(CharSequence)‣ boolean matchesAnyOf(CharSequence) ‣ boolean matchesNoneOf(CharSequence) ‣ int indexIn(CharSequence, int)‣ int lastIndexIn(CharSequence, int) ‣ int countIn(CharSequence) ‣ String removeFrom(CharSequence) ‣ String retainFrom(CharSequence) ‣ String trimFrom(CharSequence) ‣ String trimLeadingFrom(CharSequence) ‣ String trimTrailingFrom(CharSequence) ‣ String collapseFrom(CharSequence, char) ‣ String trimAndCollapseFrom(CharSequence, char) ‣ String replaceFrom(CharSequence, char)
Using your CharMatcher
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 40: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/40.jpg)
Using your CharMatcher
http://scaramoche.blogspot.com/2010/05/googles-guava-library-tutorial-part-1.html
String string = "Scream 4";CharMatcher matcher = CharMatcher.JAVA_LETTER_OR_DIGIT;int count = matcher.countIn(string);
System.out.println("Letter or digit count: "+count);// Letter or digit count: 7
System.out.println(matcher.matchesAllOf("scream"));// true
System.out.println(matcher.matchesAllOf("scream "));// false
System.out.println(matcher.matchesNoneOf("_?=)("));// true
![Page 41: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/41.jpg)
Splitter
‣ regular expression ‣ result as an array ‣ its way of handling empty pieces (which is very strange)
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
",a,,b,".split(",") returns...(a) "", "a", "", "b", "" (b) null, "a", null, "b", null (c) "a", null, "b" (d) "a", "b" (e) None of the above
Mini-puzzler
+1
JDK has splitter
![Page 42: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/42.jpg)
Splitter
http://www.flickr.com/photos/terence_s_jones/5060802981/
Splitter is String.split() on steroidshttp://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 43: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/43.jpg)
Splitter
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
The default behavior is simplistic:
//yields [" foo", " ", "bar", " quux", ""] Splitter.on(',').split(" foo, ,bar, quux,");
//yields ["foo", "bar", "quux"] Splitter.on(',') .trimResults() .omitEmptyStrings() .split(" foo, ,bar, quux,");
If you want extra features, ask for them!
![Page 44: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/44.jpg)
Ascii, CharsetsAscii
‣Charsets.ISO_8859_1;‣Charsets.US_ASCII;‣Charsets.UTF_16;‣Charsets.UTF_16BE; ‣Charsets.UTF_16LE;‣Charsets.UTF_8;
list of bytes constants for each Char between 0x00 & 0x7F
Charsets
Guaranteed to be supported by
all Java platform implementations
try { bytes = string.getBytes("UTF-8");} catch (UnsupportedEncodingException e) { // how can this possibly happen? throw new AssertionError(e);}
No more
![Page 45: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/45.jpg)
Strings
boolean b = Strings.isNullOrEmpty(s);
String str = Strings.emptyToNull(s);
String str = Strings.nullToEmpty(s);
![Page 46: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/46.jpg)
CaseFormat
‣ LOWER_CAMEL ‣ Java variable naming convention, e.g., "lowerCamel".
‣ LOWER_HYPHEN‣ Hyphenated variable naming convention, e.g., "lower-hyphen".
‣ LOWER_UNDERSCORE ‣ C++ variable naming convention, e.g., "lower_underscore".
‣ UPPER_CAMEL ‣ Java and C++ class naming convention, e.g., "UpperCamel".
‣ UPPER_UNDERSCORE ‣ Java and C++ constant naming convention, e.g., "UPPER_UNDERSCORE".
CaseFormat.to(CaseFormat.UPPER_UNDERSCORE, s);Example
![Page 47: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/47.jpg)
Collections
5http://www.flickr.com/photos/tochis/1169807846/
![Page 48: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/48.jpg)
Ordering
Comparator is easy to implement, but a pain to use
Push the Comparator<T> interface to the next level
http://scaramoche.blogspot.com/2010/05/googles-guava-library-tutorial-part-2.html
public interface Comparator<T> {
abstract int compare(T, T);
abstract boolean equals(Object);
}
![Page 49: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/49.jpg)
public class Employee implements Comparable<Employee> { private final int id; private final String name; private final int yearsOfService;
public Employee(int id, String name, int yearsOfService) { this.id = id; this.name = name; this.yearsOfService = yearsOfService; }
public int getId() { return id; }
public String getName() { return name; }
public int getYearsOfService() { return yearsOfService; }
@Override public int compareTo(Employee employee) { return this.getName().compareTo(employee.getName()); }
@Override public String toString() { return Objects.toStringHelper(this) .add("id", id) .add("name", name) .add("years of service", yearsOfService) .toString(); }}
http://scaramoche.blogspot.com/2010/05/googles-guava-library-tutorial-part-2.html
Simple data class
Ordering
![Page 50: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/50.jpg)
Ordering
Employee anakinSk = new Employee(4, "Anakin Skywalker", 4);Employee darthVader = new Employee(3, "Darth Vader", 5);Employee hanSolo = new Employee(2, "Han Solo", 10);List <Employee> employeeList = Lists.newArrayList(anakinSk, hanSolo, darthVader);System.out.println("employee list: "+employeeList);
employee list: [Employee{id=4, name=Anakin Skywalker, years of service=4}, Employee{id=2, name=Han Solo, years of service=10}, Employee{id=3, name=Darth Vader, years of service=5}]
http://scaramoche.blogspot.com/2010/05/googles-guava-library-tutorial-part-2.html
![Page 51: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/51.jpg)
Ordering
Comparator<Employee> yearsComparator = new Comparator<Employee>() { @Override public int compare(Employee employee1, Employee employee2) { return (employee1.getYearsOfService() - employee2 .getYearsOfService()); }};
Comparator<Employee> idComparator = new Comparator<Employee>() { @Override public int compare(Employee employee1, Employee employee2) { return (employee1.getId() - employee2.getId()); }};
Define your own Comparator
http://scaramoche.blogspot.com/2010/05/googles-guava-library-tutorial-part-2.html
![Page 52: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/52.jpg)
Ordering
Ordering<Employee> orderUsingYearsComparator = Ordering.from(yearsComparator);
Create an Ordering from a Comparator
List<Employee> sortedCopy = orderUsingYearsComparator.sortedCopy(employeeList);System.out.println("sorted copy: " + sortedCopy);
Use your ordering, e.g. to sort
sorted copy: [Employee{id=4, name=Anakin Skywalker, years of service=4}, Employee{id=3, name=Darth Vader, years of service=5}, Employee{id=2, name=Han Solo, years of service=10}]
http://scaramoche.blogspot.com/2010/05/googles-guava-library-tutorial-part-2.html
![Page 53: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/53.jpg)
Ordering
toString() ordering
Ordering<Object> toStringOrdering = Ordering.usingToString();
Ordering<Employee> natural = Ordering.natural();
Natural ordering (Comparable<T>)
http://scaramoche.blogspot.com/2010/05/googles-guava-library-tutorial-part-2.html
![Page 54: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/54.jpg)
What you can do with Ordering
‣ Ordering.min(Iterable<E>) ‣ Ordering.max(Iterable<E>)‣ Ordering.leastOf(Iterable<E>, int)‣ Ordering.greatestOf(Iterable<E>, int)
‣ Ordering.isOrdered(Iterable<? extends T>)‣ Ordering.isStrictlyOrdered(Iterable<? extends T>)
‣ Ordering.binarySearch(List<? extends T>, T)
![Page 55: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/55.jpg)
What you can do with Ordering
‣ Ordering.sortedCopy(Iterable<E>)‣ Ordering.immutableSortedCopy(Iterable<E>)
Better than new TreeSet(Collection)
Do not discard duplicates elements
Performed sort is stable
![Page 56: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/56.jpg)
Ordering is configurable
‣ Ordering.reverse()‣ Ordering.lexicographical()‣ Ordering.nullsFirst()‣ Ordering.nullsLast()‣ Ordering.reverse()
[] < [1] < [1, 1] < [1, 2] < [2]
Lexicographical returns an Ordering on Iterable of T
![Page 57: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/57.jpg)
ObjectArrays
‣ concat(T, T[])
‣ concat(T[], T)
‣ concat(T[], T[], Class<T>)
‣ newArray(Class<T>, int)
‣ newArray(T[], int)
![Page 58: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/58.jpg)
Multiset & Multimap
Historically, multisets (aka bags) and multimaps emulated atop maps
Multimap = Map<K, List<V>>
Multiset = Map<K, Integer>
![Page 59: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/59.jpg)
When to use Multiset?
‣"I kinda want a Set except I can have duplicates"‣ card games example‣ changing to List sacrifices contains() performance ‣"Are these Lists equal, ignoring order?"‣ write a utility method for this? Histograms
‣"What distinct tags am I using on my blog, and how many times do I use each one?"
Multiset performance varies by the number
of distinct elements, not total size.
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
![Page 60: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/60.jpg)
Map<String, Integer> tags = new HashMap<String, Integer>();for (BlogPost post : getAllBlogPosts()) { for (String tag : post.getTags()) {
int value = tags.containsKey(tag) ? tags.get(tag) : 0; tags.put(tag, value + 1);
}}
Multiset
distinct tags: tags.keySet()
count for "java" tag: tags.containsKey("java") ? tags.get("java") : 0;
total count: // oh crap...
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
Ever done this?
Usage
![Page 61: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/61.jpg)
Multiset
Multiset<String> tags = HashMultiset.create();for (BlogPost post : getAllBlogPosts()) {
tags.addAll(post.getTags());}
distinct tags: tags.elementSet();
count for "java" tag: tags.count("java");
total count: tags.size();
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
Would you rather do this?
Usage(hurrah)
![Page 62: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/62.jpg)
‣What if you need to remove/decrement?‣Don't accidentally go negative ‣Don't forget to prune! ‣(Or just use a Multiset.)
‣What about concurrency? ‣Lock the entire map just to add one tag? ‣(Or just use our ConcurrentMultiset.)
Multiset API
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
When you use a powerful library, your code can easily evolve.
![Page 63: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/63.jpg)
Multiset API
‣int count(Object element);
‣int add(E element, int occurrences);
‣boolean remove(Object element, int occurrences);
‣int setCount(E element, int newCount);
‣boolean setCount(E e, int oldCount, int newCount);
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
![Page 64: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/64.jpg)
Multiset implementations
ImmutableMultisetHashMultisetLinkedHashMultisetTreeMultisetEnumMultisetConcurrentHashMultiset
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
+1
![Page 65: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/65.jpg)
When to use Multimap?
Map<Salesperson, List<Sale>> map = new HashMap<Salesperson, List<Sale>>();public void makeSale(Salesperson salesPerson, Sale sale) { List<Sale> sales = map.get(salesPerson); if (sales == null) { sales = new ArrayList<Sale>(); map.put(salesPerson, sales); } sales.add(sale);}
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
Ever done this?
![Page 66: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/66.jpg)
When to use Multimap?
The code on the previous slide is ‣Verbose‣Bug-prone ‣Limited in functionality ‣Using the wrong abstraction
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
Multimap<Salesperson, Sale> multimap = ArrayListMultimap.create();public void makeSale(Salesperson salesPerson, Sale sale) { multimap.put(salesPerson, sale);}
Would you rather do this?
![Page 67: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/67.jpg)
More about MultimapA collection of key-value pairs (entries), like a Map,
except that keys don't have to be unique.
{a=1, a=2, b=3, c=4, c=5, c=6}
multimap.get(key) returns a modifiable Collection view of the values associated with that key.
Sometimes you want to think of it as a Map<K, Collection<V>> -- use the asMap() view:
{a=[1, 2], b=[3], c=[4, 5, 6]}http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
![Page 68: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/68.jpg)
Multimap subtypes
‣ListMultimap: the get() view implements List‣preserves the ordering of entries per key; ‣can have duplicate entries
‣SetMultimap: the get() view implements Set‣no duplicate entries, ‣ordering of entries is impl-dependent
‣SortedSetMultimap: the get() view implements SortedSet‣you get the idea
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
Hmm... sounds a lot like a plain old Map<K, Collection<V>>? But wait...
![Page 69: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/69.jpg)
Multimap, before
public Sale getBiggestSale() { Sale biggestSale = null; for (List<Sale> sales : map.values()) { Sale myBiggestSale = Collections.max(
sales, SALE_CHARGE_COMPARATOR);
if (biggestSale == null || myBiggestSale.getCharge() > biggestSale().getCharge()) { biggestSale = myBiggestSale; } } return biggestSale;}
Now we want to find the biggest Sale.
Without Multimap:
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
![Page 70: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/70.jpg)
Multimap, after
Multimap has six: ‣get(), ‣keys(), ‣keySet(), ‣values(), ‣entries(), ‣asMap().
public Sale getBiggestSale() { return Collections.max(multimap.values(), SALE_CHARGE_COMPARATOR);}
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
View collections are very powerful.
![Page 71: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/71.jpg)
Multimap APIMost Map methods are identical on Multimap:‣ size(), ‣ isEmpty(),‣ containsKey(), ‣ containsValue(),‣ put(), ‣ putAll(),‣ clear(),‣ values()
The others have analogues:‣ get() returns Collection<V> instead of V ‣ remove(K) becomes remove(K,V) and removeAll(K) ‣ keySet() becomes keys() (well, and keySet()) ‣ entrySet() becomes entries()
And Multimap has a few new things:‣ containsEntry(), ‣ replaceValues()
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
![Page 72: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/72.jpg)
Multimap implementations
ImmutableMultimapImmutableListMultimapImmutableSetMultimap
ArrayListMultimapHashMultimap
LinkedHashMultimapLinkedListMultimap
TreeMultimap
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
ListMultimapSetMultimap
SortedSetMultimap
+1
![Page 73: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/73.jpg)
BiMap
aka unique-valued mapvalues are unique, as well as its keys
Has an inverse() view, which is another BiMapbimap.inverse().inverse() == bimap
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
Stop creating two separate
forward and backward Maps!
+1
![Page 74: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/74.jpg)
BiMap Implementations
ImmutableBiMap HashBiMap EnumBiMapEnumHashBiMap
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
![Page 75: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/75.jpg)
Constrained Collections/Maps
//...public Object checkElement(Object element) { if (element == null) { throw new NullPointerException(); } return element;}//...
public interface Constraint<E> { E checkElement(E element);}
Constraints.notNull()
![Page 76: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/76.jpg)
Constrained Collections/Maps
constrainedCollection(Collection<E>, Constraint<? super E>)
constrainedList(List<E>, Constraint<? super E>)
constrainedMultiset(Multiset<E>, Constraint<? super E>)
constrainedSet(Set<E>, Constraint<? super E>)
constrainedSortedSet(SortedSet<E>, Constraint<? super E>)
Constraints.
![Page 77: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/77.jpg)
MapMaker
A ConcurrentMap builder, providing any combination of these features:‣Soft or weak keys‣Soft or weak values‣Timed expiration‣On-demand computation of values
Far more powerful, easy to use than WeakHashMap
Concurrent on-demand computation is really hard
+1
![Page 78: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/78.jpg)
MapMaker
ConcurrentMap<User, Graph> recommendations = new MapMaker()
.concurrencyLevel(4) .softKeys()
.weakValues()
.maximumSize(10000) .expireAfterWrite(10, TimeUnit.MINUTES) .makeComputingMap( new Function<User, Graph>() { public Graph apply(User user) { return createExpensiveGraph(user); } });
![Page 79: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/79.jpg)
Forwarding Object/Collections
Abstract implementations of existing types delegating all method calls to its delegate()
protected abstract Object delegate();
Decorator pattern without the burden ;)
![Page 80: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/80.jpg)
Forwarding Collections
ForwardingCollection ForwardingConcurrentMap
ForwardingIterator ForwardingList
ForwardingListIterator ForwardingListMultimap
ForwardingMap ForwardingMapEntry ForwardingMultimap
ForwardingMultiset ForwardingObject ForwardingQueue
ForwardingSet ForwardingSetMultimap ForwardingSortedMap ForwardingSortedSet
ForwardingSortedSetMultimapForwardingTable
![Page 81: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/81.jpg)
Static utilitiesIn classes with name ending with an s
‣ Lists‣ Maps‣ Multimaps‣ Multisets‣ Sets‣ SortedMaps‣ Tables‣ Iterators‣ Iterables‣ Collections2
![Page 82: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/82.jpg)
Static factories methods
Map<String, Class<? extends Handler>> m = new HashMap<String, Class<? extends Handler>>();
Map<String, Class<? extends Handler>> m2 = Maps.newHashMap();
Guava provides these for JDK collections and for Guava collections (Multi*...)
With overloads to accept Iterables to copy elements from
Rather than typing
you type
+1
![Page 83: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/83.jpg)
Maps as index
Maps.uniqueIndex()
Map<Integer, Employee> m = Maps.uniqueIndex(values, new Function<Employee, Integer>() { @Override public Integer apply(Employee input) { return input.getId(); }});
+1
![Page 84: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/84.jpg)
Multimaps as index +1
Multimaps.index()
Multimap<Integer, Employee> m = Multimaps.index(values, new Function<Employee, Integer>() { @Override public Integer apply(Employee input) { return input.getYearsOfService(); }});
![Page 85: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/85.jpg)
Map differences
So you want to compute the differences between two maps
Maps.difference( Map<? extends K,? extends V>, Map<? extends K,? extends V>)
+1
Guava has it too
Difference is an immutable snapshot of the state of the maps at the time this method is called
![Page 86: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/86.jpg)
MapDifference API
Map<K,MapDifference.ValueDifference<V>> entriesDiffering()
Map<K,V> entriesInCommon() Map<K,V> entriesOnlyOnLeft() Map<K,V> entriesOnlyOnRight()
ValueDifference API
V leftValue() V rightValue()
![Page 87: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/87.jpg)
Sets union/intersection/difference
difference(Set<E>, Set<?>)
symmetricDifference(Set<? extends E>, Set<? extends E>)
union(Set<? extends E>, Set<? extends E>)
intersection(Set<E>, Set<?>)
Returns Sets.SetView<E>
+1
![Page 88: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/88.jpg)
Sets combinations
Set<Set<E>> powerSet(Set<E>)
Set<List<B>> cartesianProduct( List<? extends Set<? extends B>>)
while the power set of a set with size n is of size 2^n, its memory usage is only O(n)
while the cartesian product of sets of size m, n, p is a set of size m x n x p, its actual memory consumption is much smaller (m + n + p)
![Page 89: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/89.jpg)
Immutable collections
JDK has Collections.unmodifiableFoo wrappers
‣Unmodifiable - you can't change it
‣Immutable - it can never change, no matter what
‣Immutability is tasty!‣See Effective Java Item 15 for some of the many reasons
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
![Page 90: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/90.jpg)
Immutable collections
ImmutableListImmutableSetImmutableMap
ImmutableSortedMapImmutableSortedSetImmutableMultisetImmutableMultimap
ImmutableListMultimapImmutableSetMultimap
ImmutableBiMap
+1
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
![Page 91: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/91.jpg)
Immutable collections
JDK wrappers still useful for unmodifiable views of changing data. But for most purposes, use Guava’s:
‣Brand-new, standalone implementations‣Immutability guaranteed!‣Very easy to use‣See following slides
‣Slightly faster‣Null hostile‣Use less memory‣Sometimes far less (ImmutableSet, factor of 2-3x)
http://google-collections.googlecode.com/files/google-collections-svgtug-2008-08-06.pdf
![Page 92: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/92.jpg)
Immutable collectionsFactory methods
ImmutableXXX.of()ImmutableXXX.of(E)ImmutableXXX.of(E, E)ImmutableXXX.of(E, E, E, E...)
ImmutableXXX.copyOf(Iterable)ImmutableXXX.copyOf(Iterator)
ImmutableMap.of(1, "one", 2, "two")ImmutableMap.copyOf(Map)
small maps only (up to 5 key/value pairs)
singletons
immutable empty XXX
Builder pattern otherwise
![Page 93: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/93.jpg)
Constants Sets
public static final Set<Integer> LUCKY_NUMBERS; static { Set<Integer> set = new LinkedHashSet<Integer>(); set.add(4); set.add(8); set.add(15); set.add(16); set.add(23); set.add(42); LUCKY_NUMBERS = Collections.unmodifiableSet(set); }
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 94: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/94.jpg)
Constants Sets
public static final Set<Integer> LUCKY_NUMBERS = Collections .unmodifiableSet( new LinkedHashSet<Integer>( Arrays.asList(4, 8, 15, 16, 23, 42)));
A little nicer. But uses four different classes! Something's weird.
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 95: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/95.jpg)
Constants Sets
public static final ImmutableSet<Integer> LUCKY_NUMBERS = ImmutableSet.of(4, 8, 15, 16, 23, 42);
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
Now we just say exactly what we mean. And get performance benefits as well!
We're using just one class (it implements Set)
of() method name inspired by java.util.EnumSet
![Page 96: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/96.jpg)
Constants Maps
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
public static final Map<String, Integer> ENGLISH_TO_INT;static { Map<String, Integer> map = new LinkedHashMap<String, Integer>(); map.put("four", 4); map.put("eight", 8); map.put("fifteen", 15); map.put("sixteen", 16); map.put("twenty-three", 23); map.put("forty-two", 42); ENGLISH_TO_INT = Collections.unmodifiableMap(map);}
![Page 97: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/97.jpg)
Constants Maps
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
public static final ImmutableMap<String, Integer> ENGLISH_TO_INT = ImmutableMap.<String,Integer>builder() .put("four", 4) .put("eight", 8) .put("fifteen", 15) .put("sixteen", 16) .put("twenty-three", 23) .put("forty-two", 42) .build();
Empowering the Builder Pattern!
![Page 98: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/98.jpg)
TableCollection with columns and rows
No more Map<T1, Map<T2,T3>>
@Beta since r07
Table<R,C,V> composed of Table.Cell<R,C,V>
6 viewsSet<Table.Cell<R,C,V>> cellSet()
Map<R,V> column(C)Set<C> columnKeySet()
Map<C,Map<R,V>> columnMap()Map<C,V> row(R)
Set<R> rowKeySet()Map<R,Map<C,V>> rowMap()
Tables.transpose() (flips row and column keys)
2 impl.
HashBasedTableTreeBasedTable
![Page 99: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/99.jpg)
Functionnalflavor
6
http://www.flickr.com/photos/leamarzloff/3085027173/
![Page 100: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/100.jpg)
in com.google.common.base package
Function<F, T> to transform a collection
Predicate<T> to filter out a collection
public interface Function<F, T> {
T apply(F from);}
public interface Predicate<T> {boolean apply(T from);
}
![Page 101: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/101.jpg)
in com.google.common.collect package
Iterables.filter()
Iterators.filter()
Collections2.filter()
Sets.filter()
http://www.flickr.com/photos/luis_is_rubbish_at_photography/5464233571/
![Page 102: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/102.jpg)
4224 128
4224 7 12813
public static void demo(Collection<Integer> c) { Predicate<Integer> isEven = new Predicate<Integer>() { @Override public boolean apply(Integer input) { return (input.intValue() % 2 == 0); } }; Collection<Integer> fCol =
Collections2.filter(c, isEven); }
![Page 103: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/103.jpg)
in com.google.common.collect package
Iterables.transform()
Iterators.transform()
Collections2.transform()
Lists.transform()
http://www.flickr.com/photos/brotherxii/2203037632/
![Page 104: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/104.jpg)
ORANGEAPPLE KIWI PEARBANANA
OrangeApple Kiwi PearBanana
public void demo(Collection<String> c) { Function<String, String> toUpperCase = new Function<String, String>() { @Override public String apply(String input) { return input.toUpperCase(); } }; Collection<String> tCol = Collections2.transform(c, toUpperCase); }
![Page 105: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/105.jpg)
Beware of
lazynesshttp://www.flickr.com/photos/torek/2467519466/
![Page 106: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/106.jpg)
Copy!
Lists.newArrayList() Lists.newLinkedList() Sets.newHashSet() Sets.newLinkedHashSet() Sets.newTreeSet()
ImmutableList.copyOf() ImmutableSet.copyOf()
or make it immutable...
http://www.flickr.com/photos/visionnewspaper/314107094/
![Page 107: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/107.jpg)
Predicates
Functions
composeforPredicate
andornotcompose
Compose and combine http://www.flickr.com/photos/jgscism/5484243543/
![Page 108: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/108.jpg)
Compose and combine
Function<String, String> toUpper = new Function<String, String>() { @Override public String apply(String input) { return input.toUpperCase(); }};
Function<Integer, String> toHexString = new Function<Integer, String>() { @Override public String apply(Integer input) { return Integer.toHexString(input.intValue()); }};
Function<Integer, String> toUpperHexString = Functions.compose(toUpper, toHexString);
![Page 109: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/109.jpg)
Compose and combine
Predicate<String> isEmpty = new Predicate<String>() { @Override public boolean apply(String input) { return input.length() == 0; // isEmpty() is Java6 only }};
Predicate<Object> isNull = new Predicate<Object>() { @Override public boolean apply(Object input) { return input == null; }};
Predicate<String> nullOfEmpty = Predicates.or(isNull, isEmpty);
![Page 110: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/110.jpg)
Maps transform & filter
Maps.filterEntries()
Maps.filterKeys()
Maps.filterValues()
Maps.transformEntries()
Maps.transformValues()
Equivalence for Multimaps
![Page 111: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/111.jpg)
Primitives
7
![Page 112: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/112.jpg)
package that helps you work with the primitive types
common.primitives
int, long, double, float, char, byte, short, and boolean
If you need help doing a primitive task:
1. check the wrapper class (e.g. java.lang.Integer)2. check java.util.Arrays3. check com.google.common.primitives4. it might not exist!
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 113: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/113.jpg)
Guava doesn't do primitive-based collections; try fastutil, or trove4j, or...
common.primitives
Booleans, Bytes, Chars, Doubles, Floats, Ints, Longs and (wait for it) Shorts
Contains the classes
Each has the exact same structure (but has only the subset of operations that make sense for its type).
Many of the byte-related methods have alternate versions in the classes
SignedBytes and UnsignedBytes. (Bytes are peculiar...)
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 114: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/114.jpg)
Method Longs Ints Shorts Chars Doubles Bytes S.Bytes U.Bytes Booleans
hashCode x x x x x x x
compare x x x x x x x x
checkedCast x x x x x
saturadCast x x x x x
contains x x x x x x
indexOf x x x x x x x
lastIndexOf x x x x x x x
min x x x x x x
max x x x x x x
concat x x x x x x x
join x x x x x x x
toArray x x x x x x x
asList x x x x x x x
lexComparator x x x x x x x
toByteArray x x x x
fromByteArray x x x x
The big table
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 115: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/115.jpg)
IO & Network
8
http://www.flickr.com/photos/buzzingbye/222969493/
![Page 116: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/116.jpg)
common.iopublic interface InputSupplier<T> { T getInput() throws IOException;} public interface OutputSupplier<T> { T getOutput() throws IOException;}
2 key interfaces
Typically: InputSupplier<InputStream>, OutputSupplier<Writer>, etc.
‣ byte stream means "InputStream or OutputStream"ByteStreams utilities class
‣ char stream means "Reader or Writer."CharStreams utilities class
Terminology
This lets all Guava’s utilities be useful for many kinds of I/O.
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
![Page 117: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/117.jpg)
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
‣byte[] toByteArray(InputStream) ‣byte[] toByteArray(InputSupplier) ‣void readFully(InputStream, byte[]) ‣void write(byte[], OutputSupplier) ‣long copy(InputStream, OutputStream) ‣long copy(InputSupplier, OutputSupplier) ‣long length(InputSupplier)‣boolean equal(InputSupplier, InputSupplier) ‣InputSupplier slice(InputSupplier, long, long) ‣InputSupplier join(InputSupplier...)
ByteStreams
CharStreams is similar, but deals in Reader, Writer, String and CharSequence (often requiring you to specify a Charset).
![Page 118: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/118.jpg)
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
Files The Files class works one level higher than ByteStreams and CharStreams
byte[] toByteArray(File) void write(byte[], File) void write(CharSequence, File, Charset) long copy(File, File) long copy(InputSupplier, File) long copy(File, OutputSupplier) long copy(File, Charset, Appendable) long move(File, File) boolean equal(File, File)
![Page 119: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/119.jpg)
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
More about Files
File createTempDir() void deleteDirectoryContents(File) void deleteRecursively(File) long getChecksum(File, Checksum) byte[] getDigest(File, MessageDigest) String readFirstLine(File, Charset) List<String> readLines(File, Charset) T readLines(File, Charset, LineProcessor<T>) String toString(File, Charset)
![Page 120: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/120.jpg)
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
Flushables and Closeables
Closeables.closeQuietly(Closeable closeable)Closeables.close(
Closeable closeable, boolean swallowIOException) throws IOException
Flushables.flushQuietly(Flushable flushable)Flushables.flush(
Flushable flushable, boolean swallowIOException) throws IOException
Very usefull in finally blocks (avoid nesting try/catch)
![Page 121: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/121.jpg)
HostSpecifiersyntactically valid host specifier, suitable for use in a URI
InternetDomainName~RFC 1035, i18n DN
InetAddressesutility pertaining to Inet(4|6)Address instances
http://guava-libraries.googlecode.com/files/Guava_for_Netflix_.pdf
common.net
Work with literals of:‣URI‣URL‣@IP (v4/v6)
Never cause DNS services to be accessed
(JDK does...)
![Page 122: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/122.jpg)
Concurrency
9http://www.flickr.com/photos/kh-67/3339157498/
![Page 123: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/123.jpg)
Immutable* ConcurrentHashMultiset
Multimaps.synchronizedMultimap MapMaker
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
Concurrency in Guava
![Page 124: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/124.jpg)
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
common.util.concurrent
It’s all about Future (as in java.util.concurrent)(never heard of it, go take a nap)
"A handle to an in-progress computation."
"A promise from a service to supply us with a result."
![Page 125: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/125.jpg)
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
Future
public interface Future<V> { //... V get(); //... }
JDK Future
Guava ListenableFuture
public interface ListenableFuture<V> extends Future<V> { void addListener(Runnable r, Executor e); }
![Page 126: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/126.jpg)
Future with one new method: addListener
When the future is done (success, exception, cancellation), the listeners run
the killer app: "To serve as a foundation for higher-level abstractions"
See Futures
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
ListenableFuture
![Page 127: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/127.jpg)
When to use? Always.
(+) Most Futures methods require it. (+) It's easier than changing to ListenableFuture later. (+) Providers of utility methods won't need to provide Future and ListenableFuture variants of their methods.
(−) "ListenableFuture" is lengthier than "Future." (−) Classes like ExecutorService give you a plain Future by default.
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
ListenableFuture
![Page 128: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/128.jpg)
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
Transform and chain
Function<QueryResult, List<Row>> rowsFunction = new Function<QueryResult, List<Row>>() { public List<Row> apply(QueryResult queryResult) { return queryResult.getRows(); }};
Future<QueryResult> queryFuture = ...; Future<List<Row>> rowsFuture = transform(queryFuture, rowsFunction);
![Page 129: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/129.jpg)
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
Transform and chain
Function<RowKey, ListenableFuture<QueryResult>> queryFunction = new Function<RowKey, ListenableFuture<QueryResult>>() { public ListenableFuture<QueryResult> apply(RowKey rowKey) { return dataService.read(rowKey); }};
ListenableFuture<RowKey> rowKeyFuture = indexService.lookUp(query);ListenableFuture<QueryResult> queryFuture = chain(rowKeyFuture, queryFunction);
![Page 130: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/130.jpg)
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
Futures
Got a Iterable<Future<V>>?
Decide what you want:
Future of List<V> List of Future<V>
Futures.allAsList()Futures.successfulAsList()
![Page 131: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/131.jpg)
MoreExecutors.sameThreadExecutorfor quick tasks that can run inline
MoreExecutors.getExitingExecutorServicefor "half-daemon" threads
UncaughtExceptionHandlers.systemExitfor exiting after unexpected errors
ThreadFactoryBuildernew ThreadFactoryBuilder()
.setDaemon(true)
.setNameFormat("WebRequestHandler-%d")
.build();
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
Executors
![Page 132: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/132.jpg)
"An object with an operational state, plus asynchronous start() and stop() lifecycle methods
to transfer into and out of this state."
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
Services
Example: web servers, RPC servers, monitoring initialization, ...
![Page 133: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/133.jpg)
AbstractExecutionThreadService One thread automatically created for you at startup
AbstractIdleService Thread only needed for startup and shutdown (e.g., service that already has its own thread)
AbstractServiceFull control over threads creation
http://guava-libraries.googlecode.com/files/guava-concurrent-slides.pdf
Services
![Page 134: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/134.jpg)
EMF for dummies
10http://www.flickr.com/photos/bendylan/259110679/
![Page 135: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/135.jpg)
"Class diagram to Super Java Bean"
Java Framework and code generation facility
(My definition)
![Page 136: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/136.jpg)
About those modeling things
‣It’s just about defining the entities/concepts/classes you will manipulate
‣You can define concepts in several ways‣Annotated Java classes‣XML Schema‣Ecore file‣UML Class diagram
‣You give the input to EMF, and it handles conversion and generation of the ULTIMATE POJO API
![Page 137: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/137.jpg)
About those modeling things
‣Thin framework layer inserted into your POJO‣you can even hide it ;)
‣The layer is as thin as imaginable and provides high power-to-weight ratio‣opposite references‣adapters‣edit‣lazy loading‣serialization (REST)‣factory‣reflective calls / metadata generation
![Page 138: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/138.jpg)
About those modeling things
What can you define in Ecore files?
‣Package‣Classes‣Attributes‣References
![Page 139: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/139.jpg)
About those modeling things
‣PackagesLogical organization
‣ClassesClassical OO concepts
‣AttributesPrimitive type fields (with cardinality)
‣ReferencesClass type fields (with cardinality), opposite, containment
![Page 140: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/140.jpg)
EObject?
The thin layer that changes it all
Object eGet(EStructuralFeature feature);void eSet(EStructuralFeature feature, Object newValue);boolean eIsSet(EStructuralFeature feature);void eUnset(EStructuralFeature feature);
EList<EObject> eContents();TreeIterator<EObject> eAllContents();EObject eContainer();
![Page 141: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/141.jpg)
time to play
http://www.flickr.com/photos/squonk/1715142327/
http://www.flickr.com/photos/8728229@N07/4592234883/
![Page 142: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/142.jpg)
EMFPath
11http://www.flickr.com/photos/eseartista/1604034788/
![Page 143: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/143.jpg)
Path
![Page 144: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/144.jpg)
Set of functions and predicates for EMF objects
Code generators for your own Ecore models
and few other utility classes
public interface Function<F, T> {
T apply(F from);
}public interface Predicate<T> {
boolean apply(T from);}
![Page 145: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/145.jpg)
‣ parent (eContainer)
‣ ancestor‣ ancestorOrSelf‣ child (eContents)
‣ descendant (eAllContents)
‣ descendantOrSelf‣ following‣ followingSibling‣ preceding‣ precedingSibling
Lazy EObjects containment tree walking
EObject myObject;Collection<EObject> fs = followingSibling.of(myObject);
http
://w
ww
.flic
kr.c
om/p
hoto
s/m
usic
love
natu
re/1
4459
7827
2/
![Page 146: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/146.jpg)
HavingIsKind/IsTypeIsAncestor/IsChild
Common predicates
public static Collection<EObject> demoHaving(Collection<EObject> c) {
return Collections2.filter(c, Having.feature(EcorePackage.Literals.ENAMED_ELEMENT__NAME,
StringPredicates.firstUpperCase) ); }
![Page 147: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/147.jpg)
non-EMF functions & predicates
length : Function<String, Integer>toL1Case : Function<String, String>toLowerCase : Function<String, String>toU1Case : Function<String, String>toUpperCase : Function<String, String>trim : Function<String, String>replaceAll(Pattern, String)replaceAll(String, String)replaceFirst(Pattern, String)replaceFirst(String, String)substring(int)substring(int, int)
Strings
Predicates to test ordering:equalless thangreater thanless or equalgreater or equal
Comparable
![Page 148: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/148.jpg)
Ecore API has been Guava-ified
‣ EObject.eResource() is wrapped as a Function in EObjectPath.eResource
‣ EObject.eIsProxy() is wrapped as a Predicate in EObjectPath.eIsProxy
‣ EClass.getESuperTypes() is wrapped as a Function in EClass.eSuperTypes
‣ EReference.isContainment() is wrapped as a Predicate in ERefrencePath.isContainment
![Page 149: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/149.jpg)
Ecore has been Guava-ified through a generator
that is available for your own Ecore model
+
![Page 150: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/150.jpg)
time to play
http://www.flickr.com/photos/squonk/1715142327/
http://www.flickr.com/photos/8728229@N07/4592234883/
![Page 151: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/151.jpg)
Recap
12http://www.flickr.com/photos/loty/326761635/
![Page 152: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/152.jpg)
1. Functionnal flavor of collection handling2. CharMatcher / Splitter / Joiner3. Immutable Collections4. Multimap / Multiset / Bimap5. MapMaker6. EMF is generating plain old POJO
What you should remember
about this presentation
![Page 153: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/153.jpg)
1. Guava is cool, powerful and the definitive extension to JDK! 2. Never write your own POJO by hand for now, use EMF!3. Always generate EMFPath classes to handle EMF objects!
What you should REALLY remember
about this presentation
http://code.google.com/p/guava-libraries/http://code.google.com/p/guava-osgi/
http://eclipse.org/modeling/emf/http://code.google.com/a/eclipselabs.org/p/emfpath/
![Page 154: Google Guava & EMF @ GTUG Nantes](https://reader030.vdocuments.us/reader030/viewer/2022020715/54b761624a7959b0558b45d4/html5/thumbnails/154.jpg)
Q&A
http://www.flickr.com/photos/wwworks/4759535950/