Showing posts with label tip. Show all posts
Showing posts with label tip. Show all posts

Tuesday, 20 January 2015

Java8 Lambdas Tip - Collect SortedGroupingBy

Java8 introduces a great new feature which easily allows your code to decompose a List of objects into a Map of Lists of objects keyed on a particular attribute.

This is best shown by example.
Let's say you have a list of Books as below:


public class Book{
    String author;
    Date published;
    int copiesSold;
    String catagory;

    public String getAuthor() {
        return author;
    }

    public Date getPublished() {
        return published;
    }

    public int getCopiesSold() {
        return copiesSold;
    }

    public String getCatagory() {
        return catagory;
    }
}

To group them into a map of authors to books used to be a little bit painful but is now a one liner!

Map<String, List<Book>> authorsToBooks = books
       .stream()
       .collect(Collectors.groupingBy(Book::getAuthor));

The only problem with this that you might have is that the default Map implementation returned is a HashMap which of course is unordered and you might well want to order by the key, in this example by the author.  Of course, you could always sort the Map in a second step but there's a way to do it in one line.

To fix that let's introduce this static utility function:

public static <T, K extends Comparable<K>> Collector<T, ?, TreeMap<K, List<T>>> 
   sortedGroupingBy(Function<T, K> function) {
        return Collectors.groupingBy(function, 
           TreeMap::new, Collectors.toList());
}

We can call it like this:

Map<String, List<Book>> authorsToBooks = books
       .stream()
       .collect(sortedGroupingBy(Book::getAuthor));

This time the map implementation is a TreeMap which has returned the Map of authors to their books in alphabetical order. 

Saturday, 17 January 2015

Maven Tip: Adding a Custom Jar to your Maven Project

Sometimes you come across a jar which you want to include in your Maven project but is not in Maven Central.  This happened to me recently with a great web scraping library called jaunt which I wanted to include in my Maven java project.

One way (maybe the best way) is to add the jar to you local Maven repository which you can do with this command.


mvn install:install-file -Dfile=jaunt0.9.9.4.jar -DgroupId=com.jaunt.code -DartifactId=jaunt -Dversion=0.9.9.4 -Dpackaging=jar

Then add to your dependencies in Maven as below:

 <dependency>
            <groupId>com.jaunt.code</groupId>
            <artifactId>jaunt</artifactId>
            <version>0.9.9.4</version>
  </dependency>

The issue with this methodology is if you want to share your project with people who don't have access to you local Maven repository.  For example, if you want to put your project on Git for general release.

Of course you could always check in the actual source but that's not always possible or necessarily desirable. If you have any good solutions please leave in the comments.   

Thursday, 8 January 2015

IntelliJ find and replace: How to remove all lines not containing a certain text

This is essentially just an exercise in Regex but it's a little tricky (at least I found it non-trivial).

Supposing you want to remove all lines not containing xxx this is how you would go about it.

In the find box type: 

^((?!xxx).)*\n

and just leave the replace box empty.