-
-
Notifications
You must be signed in to change notification settings - Fork 1.5k
Nim for Java programmers
hlaaftana edited this page May 1, 2020
·
11 revisions
DISCLAIMER!
Unofficial, work in progress! This is still a stub. Please help extending it. There may be inaccuracies in this guide. The guide assumes some intermediate knowledge.
The general tutorials can be found here:
http://nim-lang.org/docs/tut1.html
http://nim-lang.org/docs/tut2.html
The manual provides an overview of the language: http://nim-lang.org/docs/manual.html
| Feature | Java | Nim |
|---|---|---|
| Compilation | JVM bytecode | C/C++/Obj-C/JS source |
| Paradigms | class-based, object-oriented | procedural, compile-time |
| Metaprogramming | reflection, annotations | macros, templates, generics |
| Memory management | Garbage collected | Multiple strategies: garbage collected, manual, automatic, traced and untraced pointers |
| Package manager | Ant + Ivy, Maven | Nimble |
| Library format |
.jar binaries |
Source code, unused code is not included in binary (dead code elimination), can also compile to a shared library |
| Style guide | Last one by Oracle from 1999, Google style guide, Twitter style guide | NEP-1 |
| IDE support | Eclipse, Android Studio, IntelliJ IDEA, almost universally supported | Most of the community uses VS Code, see editor support |
| Feature | Java | Nim |
|---|---|---|
| Blocks | Uses curly braces | Uses indents like Python, another option is statement list expression |
| Operators | Predefined set of symbols, 1+-1 easily parsed as 1 + (-1), no overloading |
Custom operators, overloading, subscripts, curly subscripts a{b}, experimental call and dot operators, first character based precedence, strong spaces when using command call syntax and prefix operators |
| If/else statement | if (a) { foo(); } else { bar(); } |
if a: foo() else: bar() |
| If/else expression | a ? b : c |
if a: b else: c |
| Switch/case expression/statement | switch (a) { case b -> c } |
case aof b: c
|
| Return statements | return x; |
Multiple options: implicit return at the end of a proc, result variable, explicit return statement |
| Try/catch/finally | try { foo(); } catch (Exception ex) { bar(); } finally { baz(); } |
try: foo() except Exception as ex: bar() finally: bar(), also possible to omit as ex or Exception as ex
|
| Throw exception | throw ex; |
raise ex, raise reraises last exception |
| Discarding method return values |
foo(); is a valid statement if foo() returns a value |
foo() is not a valid statement if foo() returns a value, you have to use the discard statement. |
| Procedures/methods | Defined in classes, static methods are qualified like Class.staticMethod(arg1, arg2), instance methods are called like obj.method(arg1, arg2). Instance methods are polymorphic on the instance. |
Defined in modules, order of declaration is important, forward declaration is sometimes needed. UFCS: foo(a) is the same as a.foo() and even a.foo. Multimethods are optional and polymorphic on all arguments. |
| String literals |
"str", """str""" as of Java 13 |
"str", """str""", foo"str" (raw string literals) |
| Collection literals | new int[] {1, 2, 3} |
array: [1, 2, 3], seq: @[1, 2, 3], bitset: {1, 2, 3}, tuple: (1, 2, 3), table constructor
|
| Feature | Java | Nim |
|---|---|---|
| Namespacing & importing |
public/private/package-scope modifiers, can import: single classes or all classes from a package, single or all static members from a class |
export/* postfix based, can import: exported symbols from modules with import mod, only import specific symbols from a module with from mod import foo, bar, force all symbols from a module to be qualified with from mod import nil, don't import specific symbols from a module with import mod except foo, bar, can alias imports for both symbols and modules with import mod as m. include file is also possible, embeds files inside modules |
| Typeclasses | Interfaces | Experimental concepts, intersection/union types, openarray, range
|
| Generics | Erased and for reference types (subject to change with Project Valhalla, uses angle brackets like C++ | Similar in implementation to C++ templates but uses square brackets like Scala |
| Variance in generics |
? extends T/? super T, generics invariant by default |
out T/in T, experimental, generics invariant by default |
| Type aliases | None | type Foo = Bar |
| Type inference |
var type for locals, diamond operator, lambda inference
|
let/const/var don't need type annotation if initialized, routine generics can be inferred from arguments, auto return type. No inference for anonymous procs or object constructor generics. Empty seq (@[]) needs type annotation |
| Effect/exception tracking | Forced explicit checked exceptions with throws
|
Inferred effect & exception tracking, can be explicitly written with raises and tags pragmas |
| FFI with C | JNI | Compiles to C, only needs some pragmas |
| Immutability |
final, getter and setter encapsulation |
let, getter and setter encapsulation, enforced by let for value types |
| Function pointers | Need seperate classes extending functional interfaces, have to define a new functional interface per function signature | Procs can be referenced directly, proc types are structural |
| Named, order agnostic parameters | No | Yes |
| Default parameters | No | Yes |
| Varargs | Yes | Yes, can also use a transformation proc |
| Constructor overloading | Yes, public Obj() {}
|
No, convention is to use proc newObj(): Obj
|
| Feature | Java | Nim |
|---|---|---|
| Number types | Signed integers of 8, 16, 32 and 64 bits (8 and 16 bits are actually 32 bits in bytecode), floats of 32 and 64 bits | Unsigned and signed integers with bitsize in type name e.g. int32, int has platform-dependent size, float is always float64, compatibility types like cint available and use C defined types. |
| Boolean type |
boolean, one of true or false, 32 bit integer |
bool, enum of true or false, 8 bit integer |
| Char type |
char, 32-bit integer, treated as unsigned 16-bit integer |
char, unsigned 8 bit integer, cchar and cuchar, cschar types for compatibilty with C |
| Enums | Implemented as ordered singleton instances of a class | 8 or 16 bit enumerations like C, can be used as array indices |
| Strings | Immutable wrapper around char[]
|
Similar to seq[char], mutable and growable, compatible with openarray[char]
|
| Collection types | Variable-length arrays in the core language, List, Set, Map interfaces in the standard library |
array[I, T] where I is a compile time integer or range type, UncheckedArray[T], seq[T], Pascal-style bitset type set[T], slice type with a..b, tuples and named tuples, standard library: tables, sets and more
|
| Structured types | Classes, reference type with extra data | Objects, nominal value type with optional inheritance, have no extra data without inheritance, named tuples have no inheritance but are structurally typed instead of nominal, any type can be made a reference or pointer (traced or untraced pointer) |
| Tagged unions | No, inheritance is used instead, enums can implement abstract methods/interfaces, Scala/Kotlin use sealed types | Object variants like Pascal and Ada |
| Pointer access | Incubating foreign memory access API | Yes, dereference operator is foo[], pointer arithmetic needs casting to uint
|
Intro
Getting Started
- Install
- Docs
- Curated Packages
- Editor Support
- Unofficial FAQ
- Nim for C programmers
- Nim for Python programmers
- Nim for TypeScript programmers
- Nim for D programmers
- Nim for Java programmers
- Nim for Haskell programmers
Developing
- Build
- Contribute
- Creating a release
- Compiler module reference
- Consts defined by the compiler
- Debugging the compiler
- GitHub Actions/Travis CI/Circle CI/Appveyor
- GitLab CI setup
- Standard library and the JavaScript backend
Misc