Java
Calling Java functions
Consider a typical Java "Hello, world" program:
import java.lang.System;
class Main {
public static void main(String[] args) {
System.out.println("Hello, world!");
}
}To translate it directly to Keen:
An import beginning with java/ imports a class from the Java standard library.
(Replace . with /.
So java/io/PrintStream imports java.io.PrintStream .)
Keen is not Java and doesn't have many of Java's features, such as classes and methods.
When Keen imports a Java class,
the class' public properties and methods are translated to functions.
- A
staticfield becomes a function with no arguments. The class name is omitted.
For example, Java'sSystem.outbecomesoutin Keen. - A
staticmethod can be called directly. The class name is omitted.
For example, Java'sMath.sqrtbecomessqrtin Keen. - An instance field becomes a function taking the class as an argument.
For example, Java'sPoint.xinstance field becomes a functionxin Keen. - For an instance method, a
thisargument of the class' type is prepended to the arguments.
For example, the instance methodprintlntakes ajava/io/PrintStream(such asout) as its first argument. - A class constructors becomes a function named
new.
All functions that come from Java have the java, global, and unsafe specs.
In Java, methods on a class can be called anywhere without importing the class.
Keen doesn't work like that; if you want to call a method, you need to import the class.
The Java program above only needed import java.lang.System;,
while the Keen version needs to import both java/io/PrintStream and java/lang/System.
Null values
In Java, all reference types have a null value.
Keen considers null values to be unsafe,
so don't don't mark a call to a function that comes from Java as trusted
unless you are sure it won't return null.
java-null is an unsafe function returning a Java null value for a type.
As a convenience, is-null a is equivalent to
reference-equal a, java-null.
The below example reads a directory, handling the case where it does not exist.
Casting
Java subclasses implicitly convert to their superclasses (and interfaces).
For reference types, reinterpret-cast corresponds to a Java cast.
This can be used to convert a Java class to a subclass.
Generics
Keen supports Java generic types such as List.
Type translation
Java types translate to the following Keen types:
| Java | Keen |
|---|---|
void | void |
bool | bool |
byte | int8 |
short | int16 |
int | int32 |
long | int |
float | float32 |
double | float64 |
t[] | t buffer |
Since Java Arrays are mutable, they are translated as buffer instead of array.
If a Java method treats an Array argument as read-only.
you could use cast-mutable to pass in a Keen array.
If a Java method returns an Array that will never be mutated,
you could use cast-immutable to get it as a Keen array.
There are additional functions in keen/unsafe for converting between types
that have the same runtime representation, such as char8 buffer and nat8[].
(These work in any target, not just Java.)
Implementing Java interfaces
Keen record types can implement Java interfaces directly. It works just like implementing a Keen interface.
Keen doesn't make use of Java generics, so:
- Java's
sortfunction acts on anObject buffer. - The interface is just
Comparatorwith no type parameter. - The comparator accepts
Objectparameters and downcasts them usingreinterpret-cast.
Nested classes
A nested class like Map.Entry is imported as Map$Entry.
The name of the type is just Entry.
Keen types
There are no guarantees about how Keen translates to Java.
A Keen interface isn't always a Java interface.
A Keen record isn't always a Java record.
So don't expect to use Java reflection.