Skip to content

Instantly share code, notes, and snippets.

@jbgi
Created October 15, 2017 06:54
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jbgi/1a3697d380f2071eb8c2fd3ad259c011 to your computer and use it in GitHub Desktop.
Save jbgi/1a3697d380f2071eb8c2fd3ad259c011 to your computer and use it in GitHub Desktop.
Using existentials to implement abstract type alias in Java
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;
interface Person {
int age();
}
interface People<T> {
T fromList(List<Person> ps);
List<Integer> getAges(T people);
People<?> module = new People<List<Person>>() {
public List<Person> fromList(List<Person> ps) {
return ps;
}
public List<Integer> getAges(List<Person> people) {
return people.stream().map(Person::age).collect(Collectors.toList());
}
};
}
// run with:
// javac Program.java
// java -cp . Program
public class Program<T> {
People<T> P;
Program(People<T> P) {this.P = P;}
void run() {
T people = P.fromList(Arrays.asList(() -> 21, () -> 37));
System.out.println(P.getAges(people)); // print "[21, 37]"
}
public static void main(String[] args) {
new Program<>(People.module).run();
}
}
@yawaramin
Copy link

How about

public class Program {
  public static <PeopleT> void main(String[] args) {
    People<PeopleT> module = (People<PeopleT>)People.module;

    PeopleT people = module.fromList(Arrays.asList(() -> 21, () -> 37));
    System.out.println(module.getAges(people)); // print "[21, 37]"
  }
}

@jbgi
Copy link
Author

jbgi commented Oct 15, 2017

but the cast-free alternative is only one more method call:

public class Program {
  public static void main(String[] args) {
    run(People.module);
  }
  static <PeopleT> void run(People<PeopleT> module) {
    PeopleT people = module.fromList(Arrays.asList(() -> 21, () -> 37));
    System.out.println(module.getAges(people)); // print "[21, 37]"
  }
}

so I personally would not do it.

@yawaramin
Copy link

Ah, true. The run method is indeed more elegant.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment